{"id":848,"date":"2019-07-01T15:14:22","date_gmt":"2019-07-01T13:14:22","guid":{"rendered":"https:\/\/geekcommunicant.com\/blog\/?p=848"},"modified":"2019-07-01T15:16:01","modified_gmt":"2019-07-01T13:16:01","slug":"carte-interactive-rues-sans-megots-openlayers","status":"publish","type":"post","link":"https:\/\/geekcommunicant.com\/blog\/2019\/07\/01\/carte-interactive-rues-sans-megots-openlayers\/","title":{"rendered":"Carte interactive des rues sans m\u00e9gots avec OpenLayers"},"content":{"rendered":"\n<p><\/p>\n\n\n\n<p>Bon, je suppose que vous commencez \u00e0 avoir l\u2019habitude que je\nvous pr\u00e9sente la mani\u00e8re de cr\u00e9er une carte interactive \u00e0 l\u2019aide des deux\nlibrairies majeures OpenLayers et Leaflet.<\/p>\n\n\n\n<p>Apr\u00e8s avoir rapidement cr\u00e9\u00e9 la carte des rues et sections de rue concern\u00e9es par l\u2019op\u00e9ration \u00ab\u00a0Des rues sans m\u00e9gots\u00a0\u00bb avec <a href=\"https:\/\/geekcommunicant.com\/blog\/2019\/06\/24\/carte-interactive-rues-sans-megots-leaflet\/\">Leaflet<\/a>, j\u2019ai bien entendu cr\u00e9\u00e9 une version avec OpenLayers de cette carte.<\/p>\n\n\n\n<h1 class=\"wp-block-heading\">Sources des donn\u00e9es<\/h1>\n\n\n\n<p>Pour cette carte j\u2019utilise le m\u00eame fichier GeoJSON que pour\nla carte avec Leaflet&nbsp;:<\/p>\n\n\n\n<ul class=\"wp-block-list\"><li>La liste des rues ou sections de rue provient de la page d\u2019actualit\u00e9s de <a rel=\"noreferrer noopener\" aria-label=\"Paris.fr (opens in a new tab)\" href=\"https:\/\/www.paris.fr\/actualites\/rendez-vous-dans-des-rues-sans-megots-6746\" target=\"_blank\">Paris.fr<\/a><\/li><li>Le trac\u00e9 des rues a \u00e9t\u00e9 extrait des donn\u00e9es disponibles sur <a href=\"https:\/\/opendata.paris.fr\/explore\/dataset\/voie\/\" target=\"_blank\" rel=\"noreferrer noopener\" aria-label=\"Paris Data (opens in a new tab)\">Paris Data<\/a>.<\/li><\/ul>\n\n\n\n<!--more-->\n\n\n\n<h1 class=\"wp-block-heading\">Initialisation de la carte<\/h1>\n\n\n\n<p>Comme pour la carte du m\u00e9tro, la div principale est incluse dans la m\u00eame div que celle de l\u2019encart&nbsp;:<\/p>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: xml; gutter: false; title: ; notranslate\" title=\"\">\n&lt;div id=&quot;map-wrap&quot;&gt;\n\t&lt;div id=&quot;map&quot;&gt;&lt;\/div&gt;\n\t&lt;div id=&quot;info&quot;&gt;&lt;\/div&gt;\n&lt;\/div&gt;\n<\/pre><\/div>\n\n\n<p><br> Ensuite on initialise l\u2019encart&nbsp;:<\/p>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; gutter: false; title: ; notranslate\" title=\"\">\nvar info = document.getElementById(&#039;info&#039;);\n\ninfo.innerHTML = &#039;&lt;p&gt;Survoler un \u00e9l\u00e9ment&lt;\/p&gt;&#039;;\n<\/pre><\/div>\n\n\n<p>Puis on initialise la carte&nbsp;:<\/p>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; gutter: false; title: ; notranslate\" title=\"\">\nvar map = new ol.Map({\n\tlayers: &#x5B;\n\t\tnew ol.layer.Tile({\n\t\t\tsource: new ol.source.XYZ({\n\t\t\t\turl: &#039;https:\/\/server.arcgisonline.com\/ArcGIS\/rest\/services\/Canvas\/World_Light_Gray_Base\/MapServer\/tile\/{z}\/{y}\/{x}&#039;,\n\t\t\t\tattributions: &#039;Tiles \u00a9 &lt;a href=&quot;https:\/\/server.arcgisonline.com\/ArcGIS\/rest\/services\/Canvas\/World_Light_Gray_Base\/MapServer&quot;&gt;ArcGIS&lt;\/a&gt;&#039;\n\t\t\t})\n\t\t})\n\t],\n\ttarget: &#039;map&#039;,\n\tview: new ol.View({\n\t\tcenter: ol.proj.fromLonLat(&#x5B;2.3488, 48.8502]),\n\t\tzoom: 12,\n\t\tmaxZoom: 16\n\t})\n});\n<\/pre><\/div>\n\n\n<p>Et enfin on rajoute les rues&nbsp;:<\/p>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; gutter: false; title: ; notranslate\" title=\"\">\nvar streets = new ol.layer.Vector({\n\tsource: new ol.source.Vector({\n  \t\turl: &#039;\/assets\/files\/js\/rues_sans_megots.geojson&#039;,\n  \t\tformat: new ol.format.GeoJSON()\n\t}),\n\tstyle: function(feature) {\n\t\treturn styleStreet();\n\t}\n});\n<\/pre><\/div>\n\n\n<p>La fonction appel\u00e9e dans la fonction de style de la couche\ndes rues est la suivante&nbsp;(le param\u00e8tre d\u2019entr\u00e9e servira pour le surlignage\nau survol) :<\/p>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; gutter: false; title: ; notranslate\" title=\"\">\nfunction styleStreet(selected = false) {\n\treturn new ol.style.Style({\n\t\tstroke: new ol.style.Stroke({\n\t\t\tcolor: &#039;#f7364b&#039;,\n\t\t\twidth: selected ? 5 : 3\n\t\t})\n\t});\n}\n<\/pre><\/div>\n\n\n<!--nextpage-->\n\n\n\n<h1 class=\"wp-block-heading\">Ajout de l\u2019interactivit\u00e9<\/h1>\n\n\n\n<p>Pour cette carte, je suis pass\u00e9 par des interactions de\ns\u00e9lection de <em>features<\/em> vectorielles\n(voir la documentation officielle).<\/p>\n\n\n\n<p>L\u2019interaction de survol, est cr\u00e9\u00e9e comme suit&nbsp;:<\/p>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; gutter: false; title: ; notranslate\" title=\"\">\nvar hoverSelect = new ol.interaction.Select({\n\tcondition: ol.events.condition.pointerMove,\n\tlayers: &#x5B;streets],\n\tstyle: function(feature) {\n\t\treturn styleStreet(true);\n\t}\n});\n\nmap.addInteraction(hoverSelect);\n<\/pre><\/div>\n\n\n<p>Pour intercepter cette interaction, on utilise la m\u00e9thode <code>on()<\/code> (comme avec jQuery) sur l\u2019objet repr\u00e9sentant l\u2019interaction.<\/p>\n\n\n\n<p>Les <em>features<\/em> concern\u00e9es par l\u2019\u00e9v\u00e9nement peuvent \u00eatre r\u00e9cup\u00e9r\u00e9es dans l\u2019attribut \u00ab&nbsp;selected&nbsp;\u00bb (qui est un <em>array<\/em> d\u2019objets) de l\u2019objet en entr\u00e9e de la fonction appel\u00e9e via le <code>on()<\/code> sur l\u2019objet d\u2019interaction.<\/p>\n\n\n\n<p>Les propri\u00e9t\u00e9s sont ensuite r\u00e9cup\u00e9r\u00e9es avec la m\u00e9thode <code>get()<\/code> du premier objet de \u00ab&nbsp;selected&nbsp;\u00bb.<\/p>\n\n\n\n<p>Apr\u00e8s ces explications, voici venu, non pas le temps des\nrires et des chants, mais le temps de vous d\u00e9voiler le code correspondant&nbsp;:<\/p>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; gutter: false; title: ; notranslate\" title=\"\">\nhoverSelect.on(&#039;select&#039;, function(e){\n\tif(e.selected.length &gt; 0) {\n\t\tvar infoTxt = &#039;&lt;p&gt;&#039; + e.selected&#x5B;0].get(&#039;name&#039;);\n\t    \n\t    if(e.selected&#x5B;0].get(&#039;between&#039;)) infoTxt += &#039;, &#039; + e.selected&#x5B;0].get(&#039;between&#039;);\n\t    \n\t    infoTxt += &#039;&lt;\/p&gt;&#039;;\n\t    \n\t    info.innerHTML = infoTxt;\n\t} else {\n\t\tinfo.innerHTML = &#039;&lt;p&gt;Survoler un \u00e9l\u00e9ment&lt;\/p&gt;&#039;;\n\t}\n});\n<\/pre><\/div>\n\n\n<p>L\u2019interaction pour le click se cr\u00e9\u00e9 de la m\u00eame mani\u00e8re&nbsp;:<\/p>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; gutter: false; title: ; notranslate\" title=\"\">\nvar clickSelect = new ol.interaction.Select({\n\tcondition: ol.events.condition.click,\n\tlayers: &#x5B;streets],\n\tstyle: function(feature) {\n\t\treturn styleStreet();\n\t}\n});\n\nmap.addInteraction(clickSelect);\n<\/pre><\/div>\n\n\n<p>Pour r\u00e9cup\u00e9rer les coordonn\u00e9es de la bo\u00eete englobante de l\u2019objet cliqu\u00e9, on utilise le chainage<code> getGeometry().getExtent()<\/code>.<\/p>\n\n\n\n<p>Et pour zoomer la carte, on utilise le chainage <code>getView().fit()<\/code>.<\/p>\n\n\n\n<p>Pour \u00e9viter que l\u2019objet pr\u00e9c\u00e9demment survol\u00e9 par la souris\nsoit toujours consid\u00e9r\u00e9 comme s\u00e9lectionn\u00e9 (et donc surlign\u00e9) il faut \u00ab&nbsp;vider&nbsp;\u00bb\nl\u2019interaction \u00ab&nbsp;hoverSelect&nbsp;\u00bb.<\/p>\n\n\n\n<p>Tout cela nous donne le code suivant&nbsp;:<\/p>\n\n\n<div class=\"wp-block-syntaxhighlighter-code \"><pre class=\"brush: jscript; gutter: false; title: ; notranslate\" title=\"\">\nclickSelect.on(&#039;select&#039;, function(e){\n\tif(e.selected.length &gt; 0) {\n\t\tinfo.innerHTML = &#039;&lt;p&gt;Survoler un \u00e9l\u00e9ment&lt;\/p&gt;&#039;;\n        \t\n    \tmap.getView().fit(e.selected&#x5B;0].getGeometry().getExtent(), {nearest: true});\n\n    \thoverSelect.getFeatures().clear();\n\t}\n});\n<\/pre><\/div>\n\n\n<hr class=\"wp-block-separator\"\/>\n\n\n\n<p>La version compl\u00e8te de cette carte est, comme toujours, disponible sur <a href=\"https:\/\/geekcommunicant.com\/demos\/carte-interactive-rues-sans-megots-paris-openlayers.html\" target=\"_blank\" rel=\"noreferrer noopener\" aria-label=\"mon site (opens in a new tab)\">mon site<\/a>.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Bon, je suppose que vous commencez \u00e0 avoir l\u2019habitude que je vous pr\u00e9sente la mani\u00e8re de cr\u00e9er une carte interactive \u00e0 l\u2019aide des deux librairies majeures OpenLayers et Leaflet. Apr\u00e8s avoir rapidement cr\u00e9\u00e9 la carte des rues et sections de &hellip; <a href=\"https:\/\/geekcommunicant.com\/blog\/2019\/07\/01\/carte-interactive-rues-sans-megots-openlayers\/\">Continuer la lecture <span class=\"meta-nav\">&rarr;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"jetpack_post_was_ever_published":false,"_jetpack_newsletter_access":"","_jetpack_dont_email_post_to_subs":false,"_jetpack_newsletter_tier_id":0,"_jetpack_memberships_contains_paywalled_content":false,"_jetpack_memberships_contains_paid_content":false,"footnotes":"","jetpack_publicize_message":"","jetpack_publicize_feature_enabled":true,"jetpack_social_post_already_shared":true,"jetpack_social_options":{"image_generator_settings":{"template":"highway","default_image_id":0,"font":"","enabled":false},"version":2}},"categories":[19],"tags":[14,40],"class_list":["post-848","post","type-post","status-publish","format-standard","hentry","category-javascript","tag-carte-interactive","tag-openlayers"],"jetpack_publicize_connections":[],"jetpack_featured_media_url":"","jetpack_shortlink":"https:\/\/wp.me\/p2IoOb-dG","jetpack_sharing_enabled":true,"jetpack_likes_enabled":true,"jetpack-related-posts":[{"id":835,"url":"https:\/\/geekcommunicant.com\/blog\/2019\/06\/24\/carte-interactive-rues-sans-megots-leaflet\/","url_meta":{"origin":848,"position":0},"title":"Carte interactive des rues sans m\u00e9gots avec Leaflet","author":"geekc","date":"24\/06\/2019","format":false,"excerpt":"Cette carte interactive des rues sans m\u00e9gots de Paris a \u00e9t\u00e9 r\u00e9alis\u00e9e suite \u00e0 la suite de la consultation de la page d\u2019actualit\u00e9s de la ville de Paris concernant cette action de propret\u00e9, qui ne contenait qu\u2019une image pour pr\u00e9senter la cartographie des diff\u00e9rentes rues concern\u00e9es par cette op\u00e9ration. Sources\u2026","rel":"","context":"Dans &quot;JavaScript&quot;","block_context":{"text":"JavaScript","link":"https:\/\/geekcommunicant.com\/blog\/category\/javascript\/"},"img":{"alt_text":"","src":"","width":0,"height":0},"classes":[]},{"id":860,"url":"https:\/\/geekcommunicant.com\/blog\/2019\/07\/15\/carte-interactive-openlayers-controle-calques\/","url_meta":{"origin":848,"position":1},"title":"Carte interactive OpenLayers avec contr\u00f4le de calques","author":"geekc","date":"15\/07\/2019","format":false,"excerpt":"Apr\u00e8s avoir r\u00e9alis\u00e9 une carte historique de la ligne 2 du tramway d\u2019\u00cele-de-France avec Leaflet (voir le tutoriel), je me suis attaqu\u00e9 \u00e0 la cr\u00e9ation de cette m\u00eame carte avec OpenLayers. Bien que plus complet sur certains points, OpenLayers n\u2019inclus pas nativement deux fonctionnalit\u00e9s utilis\u00e9es dans la carte\u00a0: Le contr\u00f4le\u2026","rel":"","context":"Dans &quot;JavaScript&quot;","block_context":{"text":"JavaScript","link":"https:\/\/geekcommunicant.com\/blog\/category\/javascript\/"},"img":{"alt_text":"","src":"","width":0,"height":0},"classes":[]},{"id":832,"url":"https:\/\/geekcommunicant.com\/blog\/2019\/06\/17\/carte-interactive-metro-paris-openlayers\/","url_meta":{"origin":848,"position":2},"title":"Carte interactive du m\u00e9tro de Paris avec OpenLayers","author":"geekc","date":"17\/06\/2019","format":false,"excerpt":"Apr\u00e8s vous avoir cr\u00e9\u00e9 une carte interactive du m\u00e9tro de Paris avec la librairie Leaflet (voir mon pr\u00e9c\u00e9dent article), j\u2019ai d\u00e9cid\u00e9 de recr\u00e9er cette carte avec l\u2019autre libraire majeure de cartographie en ligne\u00a0: OpenLayers (que j\u2019ai d\u00e9j\u00e0 utilis\u00e9e pour ma carte utilisant un fond statique). Donn\u00e9es utilis\u00e9es Les donn\u00e9es utilis\u00e9es\u2026","rel":"","context":"Dans &quot;JavaScript&quot;","block_context":{"text":"JavaScript","link":"https:\/\/geekcommunicant.com\/blog\/category\/javascript\/"},"img":{"alt_text":"","src":"","width":0,"height":0},"classes":[]},{"id":1271,"url":"https:\/\/geekcommunicant.com\/blog\/2024\/11\/11\/marqueur-personnalise-leaflet\/","url_meta":{"origin":848,"position":3},"title":"Un marqueur personnalis\u00e9 avec Leaflet","author":"geekc","date":"11\/11\/2024","format":false,"excerpt":"Lors de mon tutoriel sur la carte du m\u00e9tro de Paris avec Leaflet, j\u2019ai d\u00e9j\u00e0 personnalis\u00e9 les marqueurs de cette carte, mais comme dans le cadre du tutoriel c\u2019\u00e9tait assez secondaire, je n\u2019ai pas d\u00e9taill\u00e9 ce point. Aujourd\u2019hui est venu le temps de revenir sur la mani\u00e8re d\u2019utiliser nos propres\u2026","rel":"","context":"Dans &quot;JavaScript&quot;","block_context":{"text":"JavaScript","link":"https:\/\/geekcommunicant.com\/blog\/category\/javascript\/"},"img":{"alt_text":"","src":"","width":0,"height":0},"classes":[]},{"id":1261,"url":"https:\/\/geekcommunicant.com\/blog\/2024\/11\/04\/personnaliser-marqueur-carte-openlayers\/","url_meta":{"origin":848,"position":4},"title":"Personnaliser le marqueur d&rsquo;une carte OpenLayers","author":"geekc","date":"04\/11\/2024","format":false,"excerpt":"Dans un tuto pr\u00e9c\u00e9dent sur la r\u00e9alisation d\u2019une carte \u00e0 l\u2019aide d\u2019OpenLayers (carte du m\u00e9tro), j\u2019ai utilis\u00e9 des marqueurs personnalis\u00e9s, mais comme ce n\u2019\u00e9tait pas l\u2019int\u00e9r\u00eat majeur du tuto, ne me suis pas attard\u00e9 sur ce point. Et c\u2019est justement sur ce point, la personnalisation des marqueurs d\u2019une carte OpenLayers,\u2026","rel":"","context":"Dans &quot;JavaScript&quot;","block_context":{"text":"JavaScript","link":"https:\/\/geekcommunicant.com\/blog\/category\/javascript\/"},"img":{"alt_text":"","src":"","width":0,"height":0},"classes":[]},{"id":808,"url":"https:\/\/geekcommunicant.com\/blog\/2019\/06\/11\/carte-interactive-metro-paris-leaflet\/","url_meta":{"origin":848,"position":5},"title":"Carte interactive du m\u00e9tro de Paris avec Leaflet","author":"geekc","date":"11\/06\/2019","format":false,"excerpt":"Si on vous parle de solution pour int\u00e9grer une carte sur votre site, la premi\u00e8re qui vous vient \u00e0 l\u2019esprit est surement Google Maps. Mais il existe plusieurs solutions open-source et gratuites. Je vous ai d\u00e9j\u00e0 parl\u00e9 d\u2019OpenLayers, avec laquelle j\u2019ai d\u00e9j\u00e0 refait une carte r\u00e9alis\u00e9e pr\u00e9c\u00e9demment avec jQuery. Mais\u2026","rel":"","context":"Dans &quot;JavaScript&quot;","block_context":{"text":"JavaScript","link":"https:\/\/geekcommunicant.com\/blog\/category\/javascript\/"},"img":{"alt_text":"","src":"","width":0,"height":0},"classes":[]}],"_links":{"self":[{"href":"https:\/\/geekcommunicant.com\/blog\/wp-json\/wp\/v2\/posts\/848","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/geekcommunicant.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/geekcommunicant.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/geekcommunicant.com\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/geekcommunicant.com\/blog\/wp-json\/wp\/v2\/comments?post=848"}],"version-history":[{"count":0,"href":"https:\/\/geekcommunicant.com\/blog\/wp-json\/wp\/v2\/posts\/848\/revisions"}],"wp:attachment":[{"href":"https:\/\/geekcommunicant.com\/blog\/wp-json\/wp\/v2\/media?parent=848"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/geekcommunicant.com\/blog\/wp-json\/wp\/v2\/categories?post=848"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/geekcommunicant.com\/blog\/wp-json\/wp\/v2\/tags?post=848"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}