Change Icon On Mouseover/out Fails
Solution 1:
Closure problem: there is error reported:
UncaughtTypeError: Cannot read property 'setIcon'ofundefined
Code has to be changed to:
(function(i) {
google.maps.event.addListener(markers[i], 'mouseover', function() {
markers[i].setIcon(gif);
});
google.maps.event.addListener(markers[i], 'mouseout', function() {
markers[i].setIcon(null);
});
})(i);
Solution 2:
Basically the problem is in here:
for (i = 0; i<locations.length; i++){
var marker = new google.maps.Marker({
position: locations[i],
draggable: true,
map: map,
});
markers.push(marker);
google.maps.event.addListener(markers[i], 'mouseover', function() {
markers[i].setIcon(gif);
});
google.maps.event.addListener(markers[i], 'mouseout', function() {
markers[i].setIcon(null);
});
};
This code looks innocent, but the problem comes from the part that, once the loop has finished executing and our event listeners are called, the variable i
is already equal to locations.length
.
So whenever the event listener is called, i
is already changed to locations.length
, and markers[i]
will return undefined, because the last push index was i = locations.length - 1
since the loop condition is i<locations.length
.
Since markers[i]
is undefined when the event listener is called, then it will throw the following error as it doesn't have setIcon
method anymore: TypeError: Cannot read property 'setIcon' of undefined
.
To fix this, you should capture value of i
, in a closure(as Anto Jurkovićdescribed above, don't forget to upvote him):
(function(i) {
google.maps.event.addListener(markers[i], 'mouseover', function() {
markers[i].setIcon(gif);
});
google.maps.event.addListener(markers[i], 'mouseout', function() {
markers[i].setIcon(null);
});
})(i);
Here we create a function on each loop and call it with i
immediately so the value of i
is captured in the closure, and since javascript functions have block scope(loops don't), the variable i
will be the same for each iteration of loop.
The problem and it's solution is also described in the following question: Javascript closure inside loops - simple practical example
Solution 3:
After further experimenting with the code that Anto and Farid recommended I found another solution. For this solution a function is created outside the initialize function to add listeners to the markers, and then called when each marker is created in the for loop. If you have any thoughts on this, please comment below. I have no clue if this is a good way to do this, I just know it works :)
for (i = 0; i<locations.length; i++){
var marker = new google.maps.Marker({
position: locations[i],
draggable: true,
map: map,
});
animateit(marker);
markers.push(marker);
};
};
functionanimateit(marker) {
google.maps.event.addListener(marker, 'mouseover', function() {
marker.setIcon(gif);
});
google.maps.event.addListener(marker, 'mouseout', function() {
marker.setIcon(null);
});
Post a Comment for "Change Icon On Mouseover/out Fails"