I'm learning canvas in html 5 and I want to manipulate an image in the canvas. However, I'm facing a roadblock in the first step itself. I am not able to display the image on the canvas.
Please look at this fiddle I created - http://jsfiddle.net/XsP76/
specifically, this is my javascript function.
$( document ).ready( function() {
var c = document.getElementById("myCanvas");
var ctx = c.getContext("2d");
var img = document.getElementById("carice");
ctx.drawImage(img, 10, 10);
});
The image is displayed in the fiddle, in firefox but not in chrome. What is going going wrong. Thanks for the help!
Works fine here in Chrome / Canary.
I noticed you insert <body> tags in your fiddle; that makes double body tags as jsfiddle do this for you.
If you go to the source for that frame you will see:
...
</head>
<body>
<body>
....
Try this update:
http://jsfiddle.net/AbdiasSoftware/XsP76/2/
Related
When drawImage() is used to draw something on to a canvas element, can the canvas be treated as an image?
When I right click on the drawn canvas element it dosent show the "Save image as" option.
This is the right click menu I see:
What should be done to have the "save image as" option available?
So, this depends a lot on the browser and how it works and in general I wouldn't advise messing with this, but if you have to get this working for one reason or another there is a way: You can 'simply' convert the canvas to an <img> element after each draw and show the <img> element instead.
var canvas = document.getElementById('exampleCanvas'); //Hidden <canvas> element
var imageFoo = document.getElementById('exampleImg'); //Visible <img> element
And then after each draw is finished:
imageFoo.src = canvas.toDataURL();
The disadvantage here is that you will lose a lot of speed, so do not use this for animated canvases or anything like that.
The "Save as image.." is something some browsers (incl. Chrome and Firefox) includes in the context menu for convenience. It's not a standard in any way though.
You could emulate the right-click and provide a custom context menu with the option of save as, however, here is the caveat:
For this to work you need to have the download attribute in the A-tag supported as well. The problem is that for example IE, which does not provide the "Save as image.." option in the menu, neither support the download attribute.
The better option is probably to insert an actual image instead of or on top of the canvas when completed (depending on how the alpha channel is used). This may not always be feasible if the content is dynamic and constantly updating, and there is CORS restrictions at play as well for images loaded from external sources.
In conclusion: There is little one can do to make a solid workaround for this. It is and will be a browser feature pretty much (and being selective about which browser to support is already the case with the feature itself, so no gain here...).
You can do this if you want to download the picuture on the canvas:
<!doctype html>
<html lang="gb">
<head>
</head>
<body>
<canvas id="test"></canvas>
<script>
var canvas = document.getElementById('test');
var ctx = canvas.getContext("2d");
ctx.font = "30px Arial";
ctx.fillText("Noel Rocks",10, 50);
canvas.addEventListener("contextmenu", function(ev){
ev.preventDefault();
var image_png = canvas.toDataURL("image/png");
var download = document.createElement('a');
download.href = image_png;
download.download = "canvas.png";
var evObj = document.createEvent('MouseEvents');
evObj.initEvent( "click", true, false );
download.dispatchEvent(evObj)
}, false);
</script>
</body>
</html>
Basically it overwrites the context menu, sets up a link with the canvas as a png and then sends the click event to the link. I have used the Download attribute which isn't available in any version of IE or Safari so might not really be fit for general use.
Here is my code
javascript: (function() {
var canvas = document.getElementById("app-view").children[1];
var img = canvas.toDataURL("image/png");
window.open(img);
})();
and here is the app element where I wish to target the second canvas element "children1" but it's not working for some reason and always gets stuck at the first element. A solution will be much appreciated, thanks in advance!
In the picture it always targets the first canvas in yellow but I need the one displayed in blue. You can test the code by saving the script as a bookmark in your browser.
Haven't worked out why toDataURL gets the data of the left canvas, but if you wanted to save the canvas, you can isolate it with
var can = document.getElementById("app-view").children[1];
jQuery("body > *").remove();
jQuery("body").append(can) ;
and then now you can right click and save the canvas
This works for me:
document.getElementById('app-view').childNodes[1]
I have an image and I want to draw on it. To do that, I use jQuery to hide the image:
$("img").hide();
And then I create a canvas and put it in the same div with id drawing in the html. I then set the background of the canvas to be the same as the img src for the image I hid. This makes it look like an image but now it is actually a canvas with the image as it's background. I do this by:
$('#drawing > canvas').css('background-image','url('+$(".image img").attr('src')+')');
context.canvas.width = $("img").width();
context.canvas.height = $("img").height();
The issue I am having is that sometimes, the image isn't displayed in the canvas and the canvas is not the size of the image. I think it's probably because of some loading issue. How can I wait for the canvas to have the image displayed in the background for sure? Thank you
Edit: Note that in the DOM, the canvas always has the right src. It just doesn't display it
Edit 2: Here's the JSfiddle. Here, everything seems fine but I have a lot more going on in my code including fetching stuff from the server so it's slower there. Hope this helps you guys to understand the problem: http://jsfiddle.net/wL3ezLke/2/
Thanks again
You need to use:
$(function(){
// Code executed once the DOM is loaded.
});
Official documentation:
https://api.jquery.com/ready/
If I understand correctly your problem is knowing when the image loaded (from what you describe it could be a lot of other problems though).
To test if an image has loaded it's pretty simple.
var $img = $('#hiddenImg');
if ($img[0].complete) doCanvasStuff();
else {
$img.on('load', function(e) {
var $canvas = $('#drawCanvas');
$canvas.css({width: $img.width(), height: $img.height()});
//you can go ahead with the background image, but this is preferable
var ctx = $canvas[0].getContext("2d");
ctx.drawImage(img,0,0);
}
}
This should make sure you canvas loads an image only after it was loaded, or do canvas stuff right away if image was loaded, fiddle
Change
$('#drawing > canvas').css('background-image','url('+$(".image img").attr('src')+')');
context.canvas.width = $("img").width();
context.canvas.height = $("img").height();
to
context.canvas.width = $("img").width();
context.canvas.height = $("img").height();
$('#drawing > canvas').css('background-image','url('+$(".image img").attr('src')+')');
so the height and width are set before the image goes into the background.
I'm taking a screenshot of my webpage using the html2canvas plugin and it works really well.
However, one of the divs on the page can be zoomed, which seems to cause problems when the screenshot is taken.
This is the code which takes the screenshot.
function screenshot(fileName){
html2canvas(document.body, {
onrendered: function(canvas) {
var myImage = canvas.toDataURL("image/png");
var image = myImage.replace('data:image/png;base64','');
window.open(myImage);
}
});
Is there an easy way to update the dom so that when the div is zoomed, html2canvas takes a screenshot of the latest webpage, or is this not possible.
Does anybody have any experience of working with any other plugins which may be a good alternative?
Thanks for any help!
Try to write below lines of code just below your code to zoom div / image in javascript
html2canvas(document.body, {
onrendered: function(canvas) {
var myImage = canvas.toDataURL("image/png");
var image = myImage.replace('data:image/png;base64','');
window.open(myImage);
}
});
So, I am currently working on an HTML5 game that uses a canvas element as a "point bucket", a visual gauge to the number of points the user has gained. But, something strange happens to the canvas when I add an element to the HTML document body
So, when writing to the body with javascript (document.body.innerHTML = "whatever";), the canvas will erase everything within itself and reset. Here is a quick and dirty example that I have whipped up to show you what I mean:
<!DOCTYPE HTML>
<html>
<body>
<canvas id="a"></canvas>
<script type = "text/javascript">
function addToBody()
{
document.body.innerHTML += "<p>I am adding to the body</p>";
}
var can = document.getElementById("a");
var con = can.getContext("2d");
//Draw rectangle on canvas
con.fillRect(0,50,100,100);
//Add text to body after 5 seconds
setTimeout("addToBody()",5000);
</script>
</body>
</html>
I know the traditional way to reset a canvas is to assign the canvas width like so:
canvas.width = canvas.width;
Is this another way to achieve the same effect or just a bug? Can someone give me some insight about this? Thanks.
Doing innerHTML += something means that the contents are retrieved as a string, something is added to that string, then the whole lot is assigned to the body, whereupon (the layout of) it is all recalculated. (and event listeners are dropped - unless they're inline handlers)
You should use the object-oriented functions to do achieve the same.
I.e
var newElem = document.createElement('p');
newElem.appendChild( document.createTextNode('I am adding to the body') );
document.body.appendChild(newElem);
This will leave your canvas untouched.