Introduction
Ce tutoriel va nous permettre d'afficher des marqueurs stockés en base de données sur la carte Google Maps. Nous verrons donc comment ouvrir une liaison Ajax avec notre serveur, comment interpréter la réponse envoyée par le serveur et comment construire cette réponse en PHP.
Initialisation
Reprendre la carte du tutoriel n°2.
Définition
Déclarons tout d'abord une fonction qui crée un marqueur sur la carte et qui ouvre une infobulle lorqu'on clique dessus :
function createMarker(point,nom,url) { var marker = new GMarker(point); var html = "<b><a href=\""+url+"\">"+nom+"</a></b>"; GEvent.addListener(marker, 'click', function() { marker.openInfoWindowHtml(html); }); return marker; }
Ajax
L'API Google Maps possède une méthode permettant une communication Ajax avec un script (ici le fichier ajax_mysql.php) :
var urlstr = "./ajax_mysql.php"; GDownloadUrl(urlstr, function(data) { var xml = GXml.parse(data); var markers = xml.documentElement.getElementsByTagName("marker"); for (var i = 0; i < markers.length; i++) { var nom = markers[i].getAttribute("nom"); var url = markers[i].getAttribute("url"); var point = new GLatLng(parseFloat(markers[i].getAttribute("lat")),parseFloat(markers[i].getAttribute("long"))); var marker = createMarker(point,nom,url); map.addOverlay(marker); }
Ici nous avons parsé le fichier XML envoyé par le script et nous avons appelé la fonction createMarker() pour chaque élément de type 'marker' du XML et en passant en paramètres le GPoint créé grâce aux attributs 'lat' et 'long', et les attributs 'nom' et 'url'.
Construction du XML côté serveur
Côté serveur, créer un fichier ajax_mysql.php qui ouvre une connexion vers la base de données contenant les enregistrements et qui édite un fichier XML grâce aux fonctions du DOM XML :
<?php
$user = "******";
$password = "*****";
$host = "******";
$bdd = "******";
mysql_connect($host,$user,$password);
mysql_select_db($bdd) or die("erreur de connexion à la base de données");
$sql = "select * from test_ajax_mysql";
$res = mysql_query($sql) or die(mysql_error());
$dom = new DomDocument('1.0', 'iso-8859-1');
$node = $dom->createElement("markers");
$parnode = $dom->appendChild($node);
while ($result = mysql_fetch_array($res)){
$node = $dom->createElement("marker");
$newnode = $parnode->appendChild($node);
$newnode->setAttribute("nom", $result['nom']);
$newnode->setAttribute("lat", $result['lat']);
$newnode->setAttribute("long", $result['long']);
$newnode->setAttribute("url", $result['url']);
}
$xmlfile = $dom->saveXML();
echo $xmlfile;
?>Code complet
<!DOCTYPE html "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <title> [Google Maps] 10. Utiliser Ajax, MySQL et PHP pour afficher des marqueurs </title> <style type="text/css"> html { overflow:hidden; height:100%; } body { height:100%; margin:0; } #map { width:100%; height:100%; } </style> <link rel="icon" type="image/png" href="./favicon.png"/> <script src="http://maps.google.com/maps?file=api&v=2&key=votre_clé_ici" type="text/javascript"></script> <script type="text/javascript"> function createMarker(point,nom,url) { var marker = new GMarker(point); var html = "<b><a href=\""+url+"\">"+nom+"</a></b>"; GEvent.addListener(marker, 'click', function() { marker.openInfoWindowHtml(html); }); return marker; } function initialize() { if (GBrowserIsCompatible()) { var map = new GMap2(document.getElementById('map')); map.setCenter(new GLatLng(43.57691664771851, 1.402451992034912),15); map.addControl(new GMapTypeControl()); map.removeMapType(G_HYBRID_MAP); map.addMapType(G_PHYSICAL_MAP); map.setMapType(G_PHYSICAL_MAP); map.addControl(new GOverviewMapControl()); map.addControl(new GScaleControl()); map.addControl(new GLargeMapControl()); map.enableScrollWheelZoom(); var urlstr = "./ajax_mysql.php"; GDownloadUrl(urlstr, function(data) { var xml = GXml.parse(data); var markers = xml.documentElement.getElementsByTagName("marker"); for (var i = 0; i < markers.length; i++) { var nom = markers[i].getAttribute("nom"); var url = markers[i].getAttribute("url"); var point = new GLatLng(parseFloat(markers[i].getAttribute("lat")),parseFloat(markers[i].getAttribute("long"))); var marker = createMarker(point,nom,url); map.addOverlay(marker); } }); } else{ alert('Désolé, mais votre navigateur n\'est pas compatible avec Google Maps'); } } </script> </head> <body onload="initialize()" onunload="GUnload()"> <div id="map"></div> </body> </html>
<?php
$user = "******";
$password = "*****";
$host = "******";
$bdd = "******";
mysql_connect($host,$user,$password);
mysql_select_db($bdd) or die("erreur de connexion à la base de données");
$sql = "select * from test_ajax_mysql";
$res = mysql_query($sql) or die(mysql_error());
$dom = new DomDocument('1.0', 'iso-8859-1');
$node = $dom->createElement("markers");
$parnode = $dom->appendChild($node);
while ($result = mysql_fetch_array($res)){
$node = $dom->createElement("marker");
$newnode = $parnode->appendChild($node);
$newnode->setAttribute("nom", $result['nom']);
$newnode->setAttribute("lat", $result['lat']);
$newnode->setAttribute("long", $result['long']);
$newnode->setAttribute("url", $result['url']);
}
$xmlfile = $dom->saveXML();
echo $xmlfile;
?>Démonstration
Remarques
Toujours se référer à l'API Google Maps - Google Maps API Reference pour les différentes classes, méthodes et options utilisées.
Cette méthode d'affichage de marqueur (on pourrait de la même manière afficher des polylignes ou des polygônes) n'est viable que pour un petit nombre d'enregistrements. En effet, à partir d'une centaine de points à afficher, cette méthode arrive à ses limites.
Dans ce cas, il devient obligatoire de 'fournir' des informations au script tels que l'extension géographique de la carte, d'utiliser une base de données avec une extension spatiale (par exemple PostgreSQL et PostGIS) et / ou de 'clusteriser' les enregistrements (cf. la carte des membres du forum Georezo)
Conclusion
Ce tutoriel décrit les étapes pour afficher des marqueurs via Ajax depuis un script PHP et une base de données MySQL.
Le manuel des fonctions DOM XML se trouve ici.
On peut imaginer une application de suivi de flotte de véhicules (ou de tortues marines ...) via cette méthode : les véhicules (ou les tortues) transmettant leurs coordonnées à la base de données, et de relancer la fonction GDownloadUrl() toutes les 30 secondes par exemple.
Auteur : Fabien - fabien.goblet [ at ] gmail.com

bonjour , super tuto mais mes
bonjour ,
super tuto mais mes markers ne s'affiche pas .
voici mon code
j ai crée une base :
- un fichier connexion.php
et un fichier test.php
<!DOCTYPE html "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <title> [Google Maps] 10. Utiliser Ajax, MySQL et PHP pour afficher des marqueurs </title> <style type="text/css"> html { overflow:hidden; height:100%; } body { height:100%; margin:0; } #map { width:100%; height:100%; } </style> <link rel="icon" type="image/png" href="./favicon.png"/> <script src="http://maps.google.com/maps?file=api&v=2&key=ABQIAAAAR0TWf73rulOP_SnETQPFKxRj5djmSsmVAgDaRb1psFcJlThRhxSjxifqM96NjrBsBn2XrZWSE-QQqQ" type="text/javascript"></script> <script type="text/javascript"> function createMarker(point,nom,url) { var marker = new GMarker(point); var html = "<b><a href=\""+url+"\">"+nom+"</a></b>"; GEvent.addListener(marker, 'click', function() { marker.openInfoWindowHtml(html); }); return marker; } function initialize() { if (GBrowserIsCompatible()) { var map = new GMap2(document.getElementById('map')); map.setCenter(new GLatLng(47.624561,-122.356445),15); map.addControl(new GMapTypeControl()); map.removeMapType(G_HYBRID_MAP); map.addMapType(G_PHYSICAL_MAP); map.setMapType(G_PHYSICAL_MAP); map.addControl(new GOverviewMapControl()); map.addControl(new GScaleControl()); map.addControl(new GLargeMapControl()); map.enableScrollWheelZoom(); var urlstr = "connexion.php"; GDownloadUrl(urlstr, function(data) { var xml = GXml.parse(data); var markers = xml.documentElement.getElementsByTagName("marker"); for (var i = 0; i < markers.length; i++) { var nom = markers[i].getAttribute("nom"); var url = markers[i].getAttribute("url"); var point = new GLatLng(parseFloat(markers[i].getAttribute("lat")),parseFloat(markers[i].getAttribute("long"))); var marker = createMarker(point,nom,url); map.addOverlay(marker); } }); } else{ alert('Désolé, mais votre navigateur n\'est pas compatible avec Google Maps'); } } </script> </head> <body onload="initialize()" onunload="GUnload()"> <div id="map"></div> </body> </html>merci pour votre aide
Bonjour, je vous invite à
Bonjour,
je vous invite à poser votre question sur le ForumSIG dans la rubrique 'Cartographie sur Internet' afin qu'un plus grand nombre puisse en profiter.
Essayez de créer un nouveau sujet en mentionnant bien le retour Firebug et en donnant une adresse éventuelle où l'on puisse tester la carto afin de voir ce qu'il ne va pas.
Cordialement et à bientôt sur le ForumSIG
En se basant sur ce tuto,
En se basant sur ce tuto, j'essaye en vain d'afficher une icone différente en fonction de chaque point repris dans la base. j'ai mis comme info dans un nouveau champs "iconurl" le chemin de l'icone dans le style http://..../img/ico1.png ....ico2.png etc
Mais bon rien ne fonctionne.
Quelqu'un aurait il déjà eu le problème
merci
Bonjour. Je tenais réellement
Bonjour.
Je tenais réellement à adresser mes félicitations sur cette série de tuto.
Super bien faits, clairs et efficaces..
C'est rare.. Bravo.
Il ne m'a fallu que quelques heures sans jamais avoir mis le nez dans cette api
pour faire une intégration complète d'une bdd avec adresse vers une map avec marqueur dynamique..
Encore merci
Merci ! C'est toujours sympa
Merci !
C'est toujours sympa les retours positifs :-)
Bonjour, Je vous remercie de
Bonjour,
Je vous remercie de ce tutoriel très bien fait. J'ai cependant une question à vous poser : comment peut on vérifier que le script php qui doit générer le XML s'exécute correctement?
En vous remerciant pour avance,
Apprenti
Bonjour, en utilisant Firebug
Bonjour,
en utilisant Firebug - extension de développement pour le navigateur Firefox - il est possible de voir les flux entre le client et le serveur.
Et du coup 'voir' le résultat du script php.
Fabien
Bonjour, Je vous remercie de
Bonjour,
Je vous remercie de votre réponse. J'ai utilisé l'extension firebug et le problème est le suivant. La page qui contient les données permettant de placer les marqueurs n'est pas trouvé ( erreur 404. J'ai vérifier plusieurs fois l'emplacement du fichier ainsi que le nom du fichier mais tout est ok.Je n'ai vérifié que ces éléments la car pour le test j'ai juste modifié le nom des variables à appeler, et je doute qu'il y ai une erreur dans votre code.
Avez-vous rencontré ce problème lors de votre développement?
Je vous remercie d'avoir répondu à ma précédente question.
Cordialement
Bonjour, il s'agit très
Bonjour,
il s'agit très probablement d'un problème d'url - erreur page 404.
Etes-vous certain de la variable : var url : "./mapagequifabriquelexml.php "?
Ou alors lancer tout simplement la page php dans le navigateur et regarder la réponse.
(Re)Bonjour, J'ai tapé
(Re)Bonjour,
J'ai tapé l'adresse entière dans l'URL et cette fois une erreur apparait dans le fichier qui doit transmettre les informations au 1er fichier.
L'erreur est la suivante : Fatal error: Cannot instantiate non-existent class: domdocument in /data/web/sites/www.xxxxxxxxxxxxxx.fr/zzzzzzzzzzz/php/ajax_mysql2.php on line 6
et la ligne 6 est $dom = new DomDocument('1.0', 'iso-8859-1');
et au cas ou voici le code complet qui est quasiment identique à votre exemple :
<?php include('config.php'); $sql = "select * FROM scene sc"; $res = mysql_query($sql) or die(mysql_error()); $dom = new DomDocument('1.0', 'iso-8859-1'); $node = $dom->createElement("markers"); $parnode = $dom->appendChild($node); while ($result = mysql_fetch_array($res)){ $node = $dom->createElement("marker"); $newnode = $parnode->appendChild($node); $newnode->setAttribute("nom", $result['id_scene']); $newnode->setAttribute("lat", $result['Y(coord_scene)']); $newnode->setAttribute("long", $result['X(coord_scene)']); //$newnode->setAttribute("lat", $result['Y(coord_scene)']); // $newnode->setAttribute("long", $result['X(coord_scene)']); $newnode->setAttribute("url", $result['angle_scene']); } $xmlfile = $dom->saveXML(); echo $xmlfile; ?>Je vais regarder à nouveau l'exemple que vous proposez pour voir si je n'ai pas manqué quelque chose.
Merci de vos réponses.
J'ai l'impression que le XML
J'ai l'impression que le XML n'est pas supporté par votre version de PHP.
Si ce n'est pas possible d'utiliser les foncions du Dom via PHP sur ta plateforme, essaie d'écrire le fichier XML 'à la main' :
Le format de fichier XML n'est pas obligatoire, on pourrait tout aussi bien utiliser du JSON ou n'importe quoi d'autre : c'est juste de la transmission d'informations entre le serveur (mysql + php) et le client (google maps en javascript). Si les deux parties connaissent ce format de fichier (le serveur pour l'écriture et le client pour la lecture et l'interprétation), il n'y a pas de problèmes. Cependant il est quand même préférable d'utiliser un format connu - c'est plus simple par la suite pour parser ce fichier contenant les informations (le XML ou le JSON sont faciles à parser en Javascript).
Après vérification, il
Après vérification, il s'avère que la version de PHP est de version 4. Apparemment il faut utiliser domxml_new_doc au lieu de DomDocument. Cependant j'ai encore une erreur fatal.
En tout cas je vais me renseigner sur le format JSON que vous citez.
Merci d'avoir pris le temps de répondre à mes questions.
Bonjour, Désolé de vous
Bonjour,
Désolé de vous embêter j'ai encore une question.
Après avoir fait des modifications j'ai pu quand même générer un fichier XML pour avoir les informations de la base. Je voulais savoir si avec ce tutoriel je peux afficher plusieurs marqueurs même si on change le zoom. Car au niveau du résultat j'ai demandé plusieurs marqueurs et ceux ci n'apparaissent pas. J'ai mis des alerts dans toute la partie du javascript qui doit générer les marqueurs mais ceux ci ne s'affichent pas.
Cordialement,
Apprenti
Ce code permet l'affichage de
Ce code permet l'affichage de plusieurs marqueurs.
Vérifiez avec Firebug que votre XML est bien formé.
Un zoom n'aura aucun effet sur l'affichage des marqueurs. Ici on demande les marqueurs au serveur une fois pour toute.
Il est évidemment possible de modifier ce comportement en jouant sur les events. Un exemple beaucoup plus complet se trouve ici. Il a été fait avec PostgreSQL et PostGIS, mais il est possible de l'adapter pour MySQL.
J'ai vérifier avec Firebug et
J'ai vérifier avec Firebug et il ne me dit pas que le XML est mal formé;
Le code que j'ai utilisé pour le xml est le suivant:
echo "<racine>"; $sql2 = "select Y(coord_scene),X(coord_scene),id_scene,trace_scene FROM scene sc LIMIT 10"; $resultats2 = mysql_query($sql2); while ($ligne2=mysql_fetch_array($resultats2)) { echo"<marker>"; // La balise racine echo "<lat>" . $ligne2['Y(coord_scene)'] . "</lat>"; // balise pour les latitude echo "<long>" . $ligne2['X(coord_scene)'] . "</long>"; //balise pour longitude echo "<nom>" . $ligne2['id_scene'] . "</nom>"; // balise pour le nom echo "<url>" . $ligne2['trace_scene'] . "</url>"; // pour l'url echo"</marker>"; } echo "</racine>";et le résultat de ce code est :
8.12
8.35
1001197620254
202
12.58
15.5
1001197921849
218
−
−
Il est possible que j'ai mal compris comment formé le xml.
En effet vous avez mal
En effet vous avez mal compris la formation du XML.
Celui-ci doit avoir la structure suivante - si vous utiliser le même code Javascript :
Bonjour, J'ai modifié le XML
Bonjour,
J'ai modifié le XML pour qu'il corresponde à l'exemple. Cependant le marqueur change de place selon le zoom. Par exemple un marqueur au frontiére de la France et de l'Italie va se retouver assez loin en Italie.
Le site sur lequel je travail est fait avec joomla. Est ce que ça à une incidence sur le résultat du code?
Cordialement,
Apprenti
Normalement non. Je confirme
Normalement non.
Je confirme que le code ne modifie pas la place du curseur selon le zoom.
Bonjour, Je vous remercie
Bonjour,
Je vous remercie avec les indications données plus haut j'ai réussi.
Cordialement,
Apprenti
Avec PHP5, vous devez
Avec PHP5, vous devez changez les signatures propre à DOM et la suite aussi, lien: http://www.php.net/manual/fr/domdocument.construct.php
En effet, merci beaucoup,
En effet, merci beaucoup, c'est corrigé dorénavant.
Merci pour ces infos
Merci pour ces infos Elles me seront certainement utiles. Projet : carte interactive de la ville (LE CREUSOT 71) avec affichages restos, hotels, administrations, tourisme...
Merci bien pour ces petits
Merci bien pour ces petits tutoriels !
Je cherchais justement comment suivre des tortues marines sur google map...
Longue vie à GeoTribu, bonne continuation.
Vince