Google Maps Marker Icon Auto Changing - google-maps

I need to automatically change Google Maps marker icons based on the inner content of an automatically updating DOM element.
I've looked at the documentation for addListener and addDomListener, but it's all mouseovers and clicks and stuff. I need it to detect a change in the pure HTML content of the element in question, and if that value meets certain conditions, change the marker's icon based on it.
Here is the code I am using:
infowindow=new google.maps.InfoWindow();
for (i=0;i<buildings.length;i++){
marker=new google.maps.Marker({
position:new google.maps.LatLng(buildings[i][4],buildings[i][5]),
map:map,
shadow:shadow,
icon:greenIcon,
title:buildings[i][0]+" \n"+buildings[i][1],
zIndex:buildings[i][6]
});
}
I am thinking about adding a setInterval in conjunction with jQuery to force the buildings[i][7] array value (not included above) to equal the content of the div in question, and then running a few conditional statements to determine if it meets the right criteria for changing the icon of the marker.
But after that, I'm lost about how to get the marker to actually change based on the dynamically updating value.

To set the icon associated with the Marker, try out the Marker.setIcon function. It accepts one parameter, which may be either:
A string that contains the relative location of the icon image file (as in your code), OR -
A MarkerImage, which gives you more control (anchor, origin, size, etc.) over how the icon image is displayed

from the google api documentation
var beachMarker = new google.maps.Marker({
position: myLatLng,
map: map,
icon: image
});
map.addOverlay (beachMarker );

Related

Google Maps fitBounds into specific area

I want to achieve the following: "Place an array of markers that may be distributed across a large range of lat, lng into a fitbounds method that places the fitbounds inside a custom rectangle."
The image below should clarify what I'm trying to achieve. Basically I have an array of markers that I want to make sure always fits within a small box on the right hand side of my page.
The white box contains some information pertaining to the markers, which will always be present, so I don't want any markers hidden behind the white box, and I'd love if I could define that they live within the black box. (Note the black box is just a visual reference for this question).
You can use the containsLocation to ensure a point is inside of a polygon. See here.
As you go through each coordinate pair in your array, verify the location is within the polygon area, then add to the map accordingly. You can also set an attribute to those points to "define" what extent they are in.
var latlng = new google.maps.latLng(array[n]);
if (google.maps.geometry.poly.containsLocation(latlng, polygon)){
marker = new google.maps.Marker({
position: latlng,
map: map
});
marker.dataset.box = 'blackbox';
} else {
alert('Not inside black box');
}
If you're using HTML5, you can add a dataset attribute to markers that are within the polygon.
marker.dataset.box = 'blackbox';
If not, you can use setAttribute.
marker.setAttribute('data-box', 'blackbox');

panToBounds don't adjust zoom

I have following problem, i use autocomplete to get coordinates for needed places, i has use before Autocomplete.getPlace().geometry.location for map.setCenter() and have manual make maximum zoom. But i have found, that it given Autocomplete.getPlace().geometry.viewport, how i can it understand, it give me 4 X,Y points for corners, so i have put it inside of map.panToBounds(). I dont know how, but the map will slide to the right viewport, but with wrong zoom level . Before i start to type in autocomplete, the zoom is on 19, and after i fire action, the map slide to the right location, but position the map Bounds not exactly to autocomplete viewport, it zoom it on the center.
var autocomplete = new google.maps.places.Autocomplete(my_input,{types:['geocode']});
google.maps.event.addListener(autocomplete, 'place_changed', function()
{
my_map.panToBounds(this.getPlace().geometry.viewport);
});
Self fixed, i dont know for what is map.panToBounds(), but what i needed was map.fitBounds()

Markers With Fixed Real (not on-screen) Radius and MarkerClusterer

I'm attempting to create a map that contains markers of a fixed real radius in metres. I'm using the CIRCLE symbol style but attempting to change the size of the circle using the scale option doesn't appear to be much the right way to go because it stays the same size on-screen regardless of the zoom level.
So, for example, I might want a 500m radius circle at a specific point and use:
var markerOptions = {
icon: {
path: google.maps.SymbolPath.CIRCLE,
scale: 500
},
position: new google.maps.LatLng(0, 50)
};
marker = new google.maps.Marker(markerOptions);
But the marker size doesn't change size when I change zoom, staying the same number of pixels across regardless of zoom level.
I tried using google.maps.Circle as an alternative to google.maps.Marker, and although Circle has a radius option and that works just fine on the scaling side of things I can't use MarkerClusterer to group them together when there are lots of them on-screen at the same time, which is another requirement.
So how do I make both clustered marker groups and fixed-size markers work together?
Thanks to the suggestion from #geocodezip I took a look at the source code for MarkerClusterer and managed to get it working with circles with a few tweaks. In case anyone else needs to do something similar here are the changes that I made to markercluster.js:
Changed all occurrences of getPosition() to getCenter()
Changed MarkerClusterer.prototype.pushMarkerTo_() to the following:
MarkerClusterer.prototype.pushMarkerTo_ = function (marker) {
// If the marker is draggable add a listener so we can update the clusters on the dragend:
marker.isAdded = false;
this.markers_.push(marker);
};
And now everything works using google.maps.Circle and MarkerClusterer.

IndexSizeError using google maps v3: using google.maps.Marker

I'm creating a page with jquery and google maps v3 and I'm trying to show a marker on a google maps. For some reason I'm getting an error with Firefox (and the marker isn't showing on the map):
Error: IndexSizeError: Index or size is negative or greater than the allowed amount Source
File: http://maps.gstatic.com/intl/en_us/mapfiles/api-3/9/17/main.js
Line: 96
Facts:
* It works in Safari
* It works if I change the MarkerImage url
Code that I'm using to add the marker is the following:
var marker = new google.maps.Marker({
map: map,
icon: new google.maps.MarkerImage(
"/gfx/icons/poi.png",
new google.maps.Size(22,22),
new google.maps.Point(0,0),
new google.maps.Point(11,11),
new google.maps.Size(22,22)),
position: point
});
My test can be visible here:
http://geoape.com/_wp.php
It seems that the problem is in the google.maps.MarkerImage object, in the fifth (scaledSize) parameter to be exact in cases where the actual size of the image is not as defined in the code. For some reason Firefox cannot handle scaling if the image size is incorrectly defined and scaledSize matches actual size but doesn't match the image size.
to be more precise: image /gfx/icons/poi.png is not 22 x 22px but 30 x 30px. So to overcome this problem there are three solutions:
a) change the second parameter accordingly (size to
google.maps.Size(30,30));
b) change the fifth parameter accordingly
(scaledSize to google.maps.Size(30,30));
c) remove the fifth
parameter (new google.maps.Size(22,22)) that would resize the marker
image.
in case of a) the markerImage will be scaled to the defined size (22x22), in case of b) and c) the 22x22 would be cropped out of the original 30x30 size.

the interactive inside the map tiles of google map

I have asked this question in stackoverflow,however I do not get the final answer what I wanted.
So I want to post it again,and give more details.
The orignal post can be found here
When the mosue over a feature in the map tiles(img),the cursor will be changed to "pointer",and you can click the right place,then you will get the informatin window. This is what I mean the "interactive".
In my opinion,when we drag or zoom the map,google will make a request to the server to get the features inside the current map view. Then when the mouse move inside the Bound of one feature,the effect will occur.
But what I wonder is that how can it be so precise?
Take this tile as exmaple:
The area of the feature "Ridley...." is not a regular rect,if your mouse is not in the area of this feature,the cursor will not change.
But once your mouse come to the right place(inside the area of this feature),the effect will come out,check this:
Since the mouse's position is precisly inside the area of the feature,so I can click it and get the information window.
I just want to know how to implement this?
Update:
The effect only come out when the mouse over the certain area,check this:
The effect come out only if the mouse move inside the hightlighted rect area,very precisly.
This uses javascript and the actual content to show is already populated from the available server in a div element with display none style property. Each 256 x 256 image at zoom level 16 contains information about x and y as well as server. When viewing google maps use firebug to look at what changes the code and you will notice many div elements with class "css-3d-bug-fix-hack" at the bottom of image list. One of these elements will have childrens as well. First child is hidden. Simply remove display none off that child and it will appear.
To implement such functionality you need to know how to obtain cursor position using javascript, how to find out if cursor is in a div element using javascript or you can use JQuery Selectors to test current hovered element of certain type. You also need to understand absolute positioning in CSS. Then use javascript to hide and show elements at cusrsor position.
Is it possible they are using a polygon-based AREA tag: http://www.w3.org/TR/html4/struct/objects.html#edef-AREA?
By definition, these tags do not need to be rectangles. They could use something like <area shape='poly' coords='...'> where the coordinates could be as precise as they desire.
UPDATE: I didn't have a chance to check http://maps.google.com before answering, but I can now tell they aren't using image maps, and therefore, the functionality is not based on AREA tags. However, if you desire the functionality of non-rectangular image map overlays, my initial response still stands.
A google.maps.Marker object can listen to the following user events, for example:
'click' 'dblclick' 'mouseup' 'mousedown' 'mouseover' 'mouseout'
http://code.google.com/apis/maps/documentation/javascript/events.html
GoogleMap uses InfoWindows to overlay the description of data over Marker.
InfoWindows displays content in a floating window above the map. The
info window looks a little like a comic-book word balloon; it has a
content area and a tapered stem, where the tip of the stem is at a
specified location on the map. You can see the info window in action
by clicking business markers on Google Maps. The InfoWindow
constructor takes an InfoWindow options object, which specifies a set
of initial parameters for display of the info window. Upon creation,
an info window is not added to the map. To make the info window
visible, you need to call the open() method on the InfoWindow, passing
it the Map on which to open, and optionally, the Marker with which to
anchor it. (If no marker is provided, the info window will open at its
position property.)
http://code.google.com/apis/maps/documentation/javascript/overlays.html#InfoWindows
Create a Marker and attach the infowindow with a mouseover event
var myLatlng = new google.maps.LatLng(-25.363882,131.044922);
var myOptions = {
zoom: 4,
center: myLatlng,
mapTypeId: google.maps.MapTypeId.ROADMAP
}
var map = new google.maps.Map(document.getElementById("map_canvas"), myOptions);
var contentString = '<div id="content">'+
'<div id="siteNotice">'+
'</div>'+
'<h1 id="firstHeading" class="firstHeading">Uluru</h1>'+
'<div id="bodyContent">'+
'<p><b>Uluru</b>, Test
'</div>'+
'</div>';
var infowindow = new google.maps.InfoWindow({
content: contentString
});
var marker = new google.maps.Marker({
position: myLatlng,
map: map,
title:"Uluru (Ayers Rock)"
});
google.maps.event.addListener(marker, 'mouseover', function() {
infowindow.open(map,marker);
});
EDITED after looking at your comment
Google Maps uses JavaScript extensively. As the user drags the map, the grid squares are downloaded from the server and inserted into the page. When a user searches for a business, the results are downloaded in the background for insertion into the side panel and map; the page is not reloaded. Locations are drawn dynamically by positioning a red pin (composed of several partially-transparent PNGs) on top of the map images.
A hidden IFrame with form submission is used because it preserves browser history. The site also uses JSON for data transfer rather than XML, for performance reasons. These techniques both fall under the broad Ajax umbrella. [From Wikipedia]