I am trying to download the entire contents of a div including the overflow using html2canvas, but the image is always cropped.
Here is a fiddle link with example code:
https://jsfiddle.net/50x2gfne/1/
function grab() {
const captureElement = document.querySelector('#capture')
html2canvas(captureElement)
.then(canvas => {
canvas.style.display = 'none'
document.body.appendChild(canvas)
return canvas
})
.then(canvas => {
const image = canvas.toDataURL('image/png').replace('image/png', 'image/octet-stream')
const a = document.createElement('a')
a.setAttribute('download', 'my-image.png')
a.setAttribute('href', image)
a.click()
canvas.remove()
})
capture.style.oveflow = 'scroll'
}
I have tried changing the width of the html and body to a wider size, setting the viewport wider, and changing the width of the canvas function.
I also tried the method in the following link for handling horizontal overflow with no luck:
https://blog.logrocket.com/export-react-components-as-images-html2canvas/
Related
I am using html2canvas to get the image of an html element(input[type='text']).
I have a control which increases the font size of the text field, and also the size of the field to accomodate the text in it.
Before changing the font, html2canvas gets the image of the field and its contents correctly. But when the font size increases, the image is not fully shown again.
I have put a red border around the canvas and the gray border is the one around the html element being snapped.
Here is the code that takes the snapshot:
function snapElem(el) {
function hiddenClone(element){
// Create clone of element
let clone = element.cloneNode(true);
// Position element relatively within the
// body but still out of the viewport
let style = clone.style;
style.position = 'relative';
style.top = window.innerHeight + 'px';
style.left = 0;
// Append clone to body and return the clone
document.body.appendChild(clone);
return clone;
}
// Clone element
let clone = hiddenClone(el);
clone.id = "za-clone-id-"+new Date().getTime();
// Use clone with htm2canvas and delete clone
html2canvas(clone, {
backgroundColor:null,
allowTaint: true,
useCORS: true
}).then(function (canvas) {
canvas.style.border = '2px solid red';
console.log(canvas.toDataURL());
canvas.id = "za-real-id-"+new Date().getTime();
document.body.removeChild(clone);
document.querySelector(".body-right").appendChild(canvas);
}).catch((e) => {
// Handle errors
console.log(e);
});
}
Here are the images obtained as the font size of the field changes
How can the content remain centered within the canvas when the font size changes.
The page has no scrolling.
I'm using html2canvas to create images from the DOM element.
The code looks like this.
const node = document.getElementById('domElement')
html2canvas(node, {
windowWidth: node.scrollWidth,
windowHeight: node.scrollHeight,
}).then(canvas => {
const image = canvas.toDataURL()
})
But its only rendering an image that is fully white. The image size (l*b) is accurate.
But when I try to render the image of the full body it shows the image but with blank white screen on top.
i.e. when,
const node = document.body
How will the elements be added properly and not the blank white screen on the image?
The code is inside an antd design modal.
This statement solved my problem.
window.scrollTo(0, 0)
The final code looks like
window.scrollTo(0, 0)
const node = document.getElementById('domElement')
html2canvas(node, {
windowWidth: node.scrollWidth,
windowHeight: node.scrollHeight,
}).then(canvas => {
const image = canvas.toDataURL()
})
I have a Vue component, in it I have an img, I need to get that image dimensions, preferably before showing the image (to fit in the container either by width or height).
this.img = new Image();
this.img.src = this.payload.src;
this.img.onload = () => {
let width = this.img.naturalWidth;
let height = this.img.naturalHeight;
}
That code might not work, the image src can return 401 (not sure yet), we use proxy and get that file from a storage bucket on the server. like /api/getStorageResource?blob=
What can I do?
Having the link, can I somehow fetch image through axios and set it as an element, instead of <img src=".." />
As an option I see that I can probably have the element as it is now <img src="/api/getStorageResource?blob=" /> and getElementById it and get the width and height... Not sure what my options here.
You can use a combination of async/await and the fetch api inside a try/catch block to get the image URL from your server and then you can proceed with creating the <img> element, assign the retrieved image URL to the img element src and finally set the width and height of the container equal to the img element's width and height.
In the following example Code Snippet, I have added a button which will add the image to the container on click so you can see how the container has the retrieved image dimensions even before the image is rendered on the DOM:
const imgDiv = document.querySelector('#imgDiv');
const btn = document.querySelector('#imgBtn');
//The fetchImg function will fetch the image URL from the server and log error to console if file not found
const fetchImg = async () => {
try {
// replace the following example url with "this.payload.src"
const imgURL = await fetch('https://picsum.photos/id/237/200/200');
return imgURL;
} catch (err) {
// do something here if image not found
console.log('Image not found!');
}
}
fetchImg().then((res) => {
// create a new image element with the URL as the src
const img = new Image();
img.src = res.url; // change ".url" according to how the data you get from your server is structured
// assign the retrieved width and height of img to container
img.addEventListener('load', () => {
imgDiv.style.width = img.naturalWidth + 'px';
imgDiv.style.height = img.naturalHeight + 'px';
});
btn.addEventListener('click', () => imgDiv.appendChild(img));
});
html, body {margin: 0;padding: 10px;width: 100%; height: 100%;text-align: center;}
#imgDiv {background-color: #222;margin: 0 auto;}
<button id="imgBtn">Add Image</button>
<div id="imgDiv"></div>
JSFiddle with above code: https://jsfiddle.net/AndrewL64/2hu3yxtq/104/
I'm using Trianglify to create backgrounds for a div element. I wanted to write the function to regenerate the background anytime the window is resized.
Here is the function that adds the generated png to the div.
const header = document.querySelector('#header');
const addBackground = target =>{
const dimensions = target.getClientRects()[0];
const pattern = Trianglify({
width: dimensions.width,
height: dimensions.height,
cell_size: Math.random()*200 + 40
});
target.style['background-image'] = 'url(' + pattern.png() + ')';
}
addBackground(header);
And here is the ResizeObserver
const ro = new ResizeObserver( () => {
addBackground(header);
});
ro.observe(header);
This works fine in chrome and edge but it creates an effect in FireFox where the background image isn't generated until the user is done resizing. This would be fine if it didn't clear the background during the resizing.
I've created a fiddle that recreates the issue.
Link to Fiddle
I want to be able to download the same image with different height and width according to parameters of the function. Here is my code :
function Download(name, QRsrc, height, width) {
if (name.length > 20) {
name = name.substring(0, 20);
}
var a = $("<a>")
.attr("href", QRsrc)
.height(height)
.width(width)
.attr("download", name)
.appendTo("body");
a[0].click();
a.remove();
}
And I am calling this function like this
Download('#survey.Name.Replace(" ","_")','#QRsrc','200','200')
But it does not work . The size of the downloaded image does not change with parameters. How can I solve this problem. Thanks for any help.
You need write the resize image method on the server.
Call your remote method
Maybe you can try the picture tag, currently few browser support this
Client side solution:
that height and width attributes are just css rules, they don't change the original image size.... you can use a new canvas based on the original image.
function downloadCanvas(link, canvasId, filename) {
link.href = document.getElementById(canvasId).toDataURL();
link.download = filename;
}
Create a canvas using this tutorial
Here an easy way to download your canvas by using the function above:
hope this help
Image resize can be possible using canvas(client side), I have created following code for resizing the Image.
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js"></script>
<script>
var resizeImage = function(src,width,height) {
var orig_src = new Image(),
resize_canvas = document.createElement('canvas');
orig_src.src = src;
resize_canvas.width = width;
resize_canvas.height = height;
resize_canvas.getContext('2d').drawImage(orig_src, 0, 0, width, height);
$(".resize-image").attr('src', resize_canvas.toDataURL("image/png"));
}
$(function(){
resizeImage('image.jpg',100,100); // Image path, width, height
});
</script>
<img class="resize-image" src="image.jpg" />