I couldn't find the thread I was participating in from a couple years ago, so I thought I'd offer it here.
I was doing something similar but I had dozens of addresses that needed to be geocoded and doing it on the fly was timing out, so I'd only get about 10 pins on my map. So I decided I would geocode addresses when I saved the resource, then just read that when I generated the map. So I created a plugin to do this, and just listed the properties with ditto in a javascript section in the page head.
<script type="text/javascript">
//<![CDATA[
[!Ditto? &display=`all` &depth=`2` &hideFolders=`1` &tpl=`GAItem` &tplFirst=`GAFirst` !]
//]]>
</script>
Here are the two templates used by Ditto:
GAFirst:
var aProp = new Array(["[+address+],[+zip+]", "[+pagetitle+] ([+address+])", "[+pagetitle+]<br/>[+address+]<br/>[+citystate+] [+zip+]", "[+latlong+]"]);
GAItem:
aProp.push(["[+address+],[+zip+]", "[+pagetitle+] ([+address+])", "[+pagetitle+]<br/>[+address+]<br/>[+citystate+] [+zip+]", "[+latlong+]"]);
I add the Googlemap javascript right after:
<script type="text/javascript">
var map;
function showAddress(address) {
/* Parms:
address - array of project attributes:
0 real address
1 property description
2 map icon
3 property description HTML
4 latitude/longitude
*/
if (address[4] != '') {
var image = "/assets/site/images/stickpin_red.png";
var myLatLng = eval("new google.maps.LatLng("+address[3]+")");
var marker = new google.maps.Marker({
position: myLatLng,
map: map,
icon: image,
title: address[1]
});
var infowindow = new google.maps.InfoWindow(
{ content: address[2],
position: myLatLng
});
//infowindow.open(map);
google.maps.event.addListener(marker, 'click', function() {
infowindow.open(map,marker);
});
}
}
function initialize() {
var myOptions = {
zoom: [*zoom*],
center: new google.maps.LatLng([*latlong*]),
navigationControl: true,
scaleControl: true,
mapTypeControl: true,
mapTypeId: google.maps.MapTypeId.ROADMAP
}
map = new google.maps.Map(document.getElementById("map"), myOptions);
for (i=0; i<aProp.length; i++)
showAddress(aProp[i]);
}
function loadScript() {
var script = document.createElement("script");
script.type = "text/javascript";
script.src = "http://maps.googleapis.com/maps/api/js?sensor=false&callback=initialize";
document.body.appendChild(script);
}
window.onload = loadScript;
</script>
And the map element in the HTML:
<div id="map" style="height: 400px; border:1px inset; padding-bottom:30px;"></div>
Finally, here's the plugin I created, to be fired with OnDocFormSave event (your actual TV ID's will vary of course):
$e = $modx->Event;
$docid = $e->params['id'];
$latlongid = 21;
if ($e->name == 'OnDocFormSave') {
$address = $_POST['tv15'];
$loc = $_POST['tv16'];
$zip= $_POST['tv17'];
$latlng = $_POST['tv'.$latlongid];
// Only get Google Geocode if all parameters present and we don't already have Lat/Lng
if ($address != '' && ($loc != '' || $zip != '') && $latlng == '') {
define("MAPS_HOST", "maps.googleapis.com");
$q = 'address='. urlencode($address) .','. urlencode($loc) .','. urlencode($zip) .'&sensor=false';
// Initialize delay in geocode speed
$delay = 0;
$base_url = "http://" . MAPS_HOST . "/maps/api/geocode/xml";
$geocode_pending = true;
while ($geocode_pending) {
$request_url = $base_url . "?" . $q;
$xml = simplexml_load_file($request_url) or die("url not loading");
$status = $xml->status;
if (strcmp($status, "OK") == 0) {
// Successful geocode
$geocode_pending = false;
$lat = $xml->result->geometry->location->lat;
$lng = $xml->result->geometry->location->lng;
$fields = array(
"value" => $lat.",".$lng
,"tmplvarid" => $latlongid
,"contentid" => $docid
);
$table = $modx->getFullTableName('site_tmplvar_contentvalues');
// Insert record into database
$newid = $modx->db->insert($fields, $table);
// Generate an error if the DB was not updated
if (!$newid) {
$modx->Event->Alert("Google Geocode: An error occured when saving.");
}
} else if (strcmp($status, "620") == 0) {
// sent geocodes too fast
$delay += 100000;
} else {
// failure to geocode
$geocode_pending = false;
echo "Address " . $address . " failed to geocode. ";
echo "Received status " . $status . "
\n";
}
usleep($delay);
}
}
}