I use a very simple piece of code (but then obviously with my image instead of Image.png). I am trying to give my canvas a background image.
var canvas = document.getElementById("canvas");
ctx = canvas.getContext("2d");
var img = new Image();
img.onload=start;
img.src="Image.png";
function start(){
ctx.drawImage(img,0,0);
}
But I receive this error:
ERROR: 'Image' is not defined. [no-undef] about the part:
var img = new Image().
I tried to replace this with
var img = document.createElement("img");
Then the error is gone, but nothing displays, no image whatsoever, its just empty.
Has anybody any idea what I am doing wrong?
Thanks in advance!
FULL CODE
var document;
var ctx;
var window;
window.onload = function () {
start();
}
function start(){
var canvas = document.getElementById("canvas");
ctx = canvas.getContext("2d");
var img = document.createElement("img");
img.src="image.png";
img.onload=start;
function start(){
ctx.drawImage(img,0,0,400,400);
}
}
You need to attach the image you have created to the DOM.
document.getElementById("image-container").appendChild(img);
Edit: I apologize, I see you are drawing it to a canvas object. In that case I would suspect that your image is failing to load properly.
A couple ideas: you could add some debugging output within the start() function or set a breakpoint, then look at what the 'img' contains at that point in time. Or you could check the status code on the 'Network' tab of the devtools console. Or you could replace the image with one that is known to work, such as www.google.com/images/logo.png. This all should hepl you narrow down the issue.
Note: window is a global variable so you shouldn't declare it, and names that are properties of window such as window.document are also globals - can be referenced as document without declaring it. Occasionally JS frameworks complain, but there are framework-specific ways to solve this. Duplicate declaration of these variables is not a good path to go down.
If you're adding these in response to ESlint errors, you should add eslintrc.json to your project root (if you don't have it already), and give it the following property so it doesn't complain for browser globals:
{
"env": {
"browser": true
}
}
As to why Image is not defined, this would not happen on a modern browser environment. It has to be something with your environment setup. Is there any information you could provide about how you are running this code?
Try setting the onload callback before you set the image's src.
var img = document.createElement("img");
img.onload=start;
img.src="image.png";
If the image is cached, then onload would be fired as soon as src is set, i.e. before it is assigned to start see this question.
Related
I'm working on a project in game development in Javascript and HTML5 canvas. I have this common code I use for loading sprites:
var sprite = new Image();
sprite.src = "sprite.png";
I was wondering if there was a simpler way to do this, which I first thought by function, but not sure how I should do so. I would think to do so like this:
function loadSprite(src) {
this.src = src;
}
var loadSprite(sprite.png);
However I don't think this is the right way to do it. Could someone correct my code and/or give a simpler way of loading an image like this? (I am also using a ctx.drawImage(..., sprite) in order to change coordinates on the canvas so it needs an x,y,width,and height parameters in one way or another)
Why not use as below:
function loadSprite(src) {
var sprite = new Image();
sprite.src = src;
return sprite
}
var _local_var = loadSprite('sprite.png');
I am new to javascript and I'm learning about it. While doing so I encountered this problem which I can't figure out and I'm here for your help.
This is the page that I was on, http://www.w3schools.com/html/tryit.asp?filename=tryhtml5_canvas_empty
Now I when I run the following on the console(firebug) it returned null.
document.getElementById("myCanvas");
Why I'm I not getting the expected result here?
The DOM has already been loaded when the draw-function is called, that is correct.
But the var canvas = document.getElementById('control');-line is evaluated before that, because it is not in the draw-function. It is executed immediately in the of the document BEFORE the elements have been rendered.
I would suggest you change your init function to something like that
var canvas = document.getElementById('myCanvas');
var context = canvas.getContext('2d');
I want to track changes that are made to the src property of an HTMLImageElement while it is not yet attached to the document. My goal is to modify the image URL to force the usage of a certain proxy server using an inserted script. The scripts that use the Image object mainly for preloading are external (3rd party) ones, so I cannot just search & replace any occurence of instance.src = value to anything else. I can control the document the scripts are embedded in, but cannot control the scripts themselves.
I already tried to define getter/setter on the Image element
Object.defineProperty(
Image.prototype,
"src",
{ get : function(){...}, set : function(val){...}}
);
But this does not seem to have any effect at all. When creating a new Image just like
var img = new Image();
img.src = "foo.png";
alert(img.src);
neither the setter nor the getter is called.
Do you have any idea what else I might try to get notified when the src property is modified without modifying the original source where the property is set?
Thanks in advance!
I retested my previous answer with your example code - no dice. So, I'll go with Andrei's suggestion instead - don't do this :P Instead, work with methods attached to the prototype through more "conventional" means:
Image.prototype.setSrc = function(src) {
// your code affecting this.src
// from what I can tell in your use-case, you only need this setter
};
Image.prototype.getImage = function() {
// but, in case you want to do anything before getting the image
// you can call this method
};
var img = new Image();
img.setSrc("foo.png");
// snip
document.body.appendChild(img.getImage());
this may be an odd one to explain:
I want to create dynamically a collection of canvas that will have a single image in it. And this displays (after much hassle and getting rid of the onload event) but when I try to refresh the page I sometimees get nothing on the screen.
And when I was using thee onload event (to wait until the image is loaded) it would not display or display everything in the last canvas.
Here is a snippet of the code:
var sources = []//the array that contains the images
var divCanvas = document.getElementById('showcase-wrapper')
for(var i=0; i<sources.length; i++){
img = new Image()
img.src = sources[i]
canvas = document.createElement('canvas')
$(canvas).attr('id', i)
canvas.height=300
canvas.width=200
var context = canvas.getContext('2d');
//onload commented out allows expected display
//img.onload = function() {
context.drawImage(img, 0, 0);
//}
divCanvas.appendChild(canvas)
}
I have seen many posts that seemed to look like mine and tried quite a few but to no avail.
I think the issue is that var context is overwritten before the img.onload event is triggered. The img.onload event only has a reference to global scope. This is why only the last image shows up. You need to find the correct context inside the event.
I can't test your code directly, but I think it should be something like this:
var sources = []//the array that contains the images
var divCanvas = document.getElementById('showcase-wrapper')
for(var i=0; i<sources.length; i++){
img = new Image();
img.src = sources[i];
img.id = i; //Allow img to remember its corresponding canvas/context
canvas = document.createElement('canvas');
$(canvas).attr('id', i);
canvas.height=300;
canvas.width=200;
var context = canvas.getContext('2d');
divCanvas.appendChild(canvas);
img.onload = function() {
//Use the image id to get the correct context
var canvas = document.getElementById(this.id);
var context = canvas.getContext('2d');
context.drawImage(this, 0, 0);
}
}
For consistent behavior, you must use onload. If you don't the canvas drawing code may execute before the image is loaded and the desired image will not be drawn.
It might be that the onloads that would draw to the other canvases are not being called because the Images are getting garbage collected before the event can fire.
Try adding
var images = [];
At the start of your code and
images.push(img);
After the img = new Image() line.
If that doesn't work, try adding those images to the DOM tree-- img.setAttribute('style', 'display: none') first so you don't see them and they don't interfere with the document structure.
I found the fix here:
https://developer.mozilla.org/docs/Web/Guide/HTML/Canvas_tutorial/Using_images#Drawing_images
Apparently they have dropped img.onload to have the function called when the body has finished loaded.
Though, I still do not understand why my script or, ellisbben solution was not working.
If anyone as an answer for it, it would be very welcomed...
function loader(img) {
var imgH = img.height;
var imgW = img.width;
console.log(imgH, imgW);
};
img = new Image();
img.src ='../images/pic1.jpeg';
img.onLoad = loader(img);
So, It is exepeted, that I'll get image's size, but I got "0 0" in console. And size of image is 500X700. What's wrong with this code?
This makes no sense:
img.onLoad = loader(img);
you want to pass the actual function to the event:
img.onload = loader;
and use this instead of img within the function.
Also you need to assign the event before changing the image's src property.
Also note that there are numerous problems with the load event on images. From the jQuery manual on load():
Caveats of the load event when used with images
A common challenge developers attempt to solve using the .load() shortcut is to execute a function when an image (or collection of images) have completely loaded. There are several known caveats with this that should be noted. These are:
It doesn't work consistently nor reliably cross-browser
It doesn't fire correctly in WebKit if the image src is set to the same src as before
It doesn't correctly bubble up the DOM tree
Try this:
function loader(){
var imgH = this.height;
var imgW = this.width;
console.log(imgH, imgW);
}
var img = new Image();
img.onload = loader;
img.src ='../images/pic1.jpeg';
I used this way:
img.onload = function(){//here wrote everything from loader};
And it was the only working solution I have found.
I found the best way is to let the computer do the scaling first.
and declaring the onload = "some_function()" in the body.
<body onload="some_function()">
and then getting the sizing afterward in the script.
some_function(){
var image1 = document.getElementsByClassName('main')[0];
var computedStyle_image1 = window.getComputedStyle(image1);
var image_width = computedStyle_image1.getPropertyValue('width');
}
I noticed with google chrome you need to make sure you call the onload="function" within the body div otherwise the image values arn't set and it pulls in 0px for width and height.