I keep getting the error links[i] is undefined.
I define it explicitly and yet it keeps giving me that error -- any ideas?
I am trying to do unobtrusive image rolovers on 5 links that I have.
function loadImages(){
path = 'uploads/Splash-4/nav/';
links = new Array();
for (i=1;i<=5;i++){
var id = "link-"+i;
var defaultState = '<img src="' +path+i+'.jpg" border="0" />';
links[i] = document.getElementById(id);
// Place all image linksinto anchor
links[i].innerHTML = defaultState;
// What to do on mouseover
links[i].onmouseover = function() {
links[i].innerHTML = '<img src="' +path+i+'a.jpg" border="0" />';
}
// What to do on mouse oUt
links[i].onmouseout = function() {
links[i].innerHTML = defaultState;
}
}
}
window.onload = loadImages;
HTML:
<a href="?page=Profile" id="link-1"></a>
<a href="?page=for-sale" id="link-2"></a><br />
<a href="?page=testimonials" id="link-3"></a><br />
<a href="?page=free-home-appraisal" id="link-4" /></a><br />
<a href="?page=contact-me" id="link-5"></a><br />
-
what line does it give you this error ? (use Chrome's developer console or firebug)Yanick Rochon– Yanick Rochon2010年08月30日 14:30:31 +00:00Commented Aug 30, 2010 at 14:30
-
When I do the mousover it give me the error: its complaining about this line: links[i].innerHTML = '<img src="' +path+i+'a.jpg" border="0" />';Andre– Andre2010年08月30日 14:32:40 +00:00Commented Aug 30, 2010 at 14:32
-
It's cleaner to instantiate an empty array using [] instead of "new Array()"Robusto– Robusto2010年08月30日 14:33:41 +00:00Commented Aug 30, 2010 at 14:33
3 Answers 3
First off, you should be saying:
var links = [];
It's generally discouraged to use the Array constructor itself, and by not specifying var, you're making the links variable reside in the global space, which is generally bad.
Now, as to your actual problem.
Your event handlers are carrying a reference to the path and i variables from the outer scope, but by the time they're actually encountered, the variable i has the value 6 -- not what you intended at all! In order to fix that, you can change:
// What to do on mouseover
links[i].onmouseover = function() {
links[i].innerHTML = '<img src="' +path+i+'a.jpg" border="0" />';
}
// What to do on mouse oUt
links[i].onmouseout = function() {
links[i].innerHTML = defaultState;
}
to
// What to do on mouseover
links[i].onmouseover = (function(path, i) {
return function () {
links[i].innerHTML = '<img src="' +path+i+'a.jpg" border="0" />';
};
})(path, i);
// What to do on mouseout
links[i].onmouseout = (function(i) {
return function () {
links[i].innerHTML = defaultState;
}
})(i);
This creates a new closure to hold the variables you want to capture. This way the inner i can still be, oh, 3 while the outer i goes to 6.
Comments
The problem is that when your onmouseover() function gets called, your variable i = 6 because your last iteration yielded i = 6, causing the loop to end. Therefore, you must protect i somewhere. For example :
function loadImages(){
path = 'uploads/Splash-4/nav/';
var links = [];
for (i=1;i<=5;i++){
(function(j) {
var id = "link-"+j;
var defaultState = '<img src="' +path+j+'.jpg" border="0" />';
links[j] = document.getElementById(id);
// Place all image linksinto anchor
links[j].innerHTML = defaultState;
// What to do on mouseover
links[j].onmouseover = function() {
links[j].innerHTML = '<img src="' +path+j+'a.jpg" border="0" />';
}
// What to do on mouse oUt
links[j].onmouseout = function() {
links[j].innerHTML = defaultState;
}
})(i); // call the anonymous function with i, thus protecting it's value for
// the mouseover/mouseout
}
}
4 Comments
undefined issue OP is having. He's using the for() loop as though the Array has a 1-based index.Your code snippet doesn't include a declaration of the variable links. If you haven't defined it elsewhere (i.e., if it's a local variable), you'll need to do it here:
Instead of
links = new Array();
You could do
var links = new Array();
One example can be found here.
If you have declared it elsewhere, it could be that this line
document.getElementById(id);
is returning null.
3 Comments
var keyword. It just means you're making it global. It is good practice to not use global variables, but it won't cause the undefined in this case.var. Definitely an important standard practice to adopt.