1jQuery(document).ready(function($) { 2 const toolsetLeaflet = window.WPViews?.view_addon_maps?.leaflet; 3 4 if (typeof L === 'undefined') { 5 if (toolsetLeaflet) { 6 window.L = toolsetLeaflet; 7 } else { 8 return; 9 } 10 } 11 12 initializeAllMaps($); 13 14 $(document).on("js_event_wpv_parametric_search_results_updated js_event_wpv_pagination_completed", function() { 15 setTimeout(function() { initializeAllMaps($); }, 1500); 16 }); 17}); 18 19function initializeAllMaps($) { 20 if (typeof L === 'undefined' && window.WPViews?.view_addon_maps?.leaflet) { 21 window.L = window.WPViews.view_addon_maps.leaflet; 22 } 23 24 if (typeof L === 'undefined') return; 25 26 for (let key in window) { 27 if (key.startsWith('aotmSettings_')) { 28 const settings = window[key]; 29 if (settings && settings.mapId) setupMapCustomizations($, settings); 30 } 31 } 32} 33 34function setupMapCustomizations($, settings) { 35 let attempts = 0; 36 const checkMapInterval = setInterval(function() { 37 attempts++; 38 const map = WPViews?.view_addon_maps?.maps?.[settings.mapId]; 39 if (!map) { 40 if (attempts > 60) clearInterval(checkMapInterval); 41 return; 42 } 43 clearInterval(checkMapInterval); 44 45 aotmLoadPaths(map, settings); 46 47 const layers = { 48 sat: L.tileLayer('https://server.arcgisonline.com/ArcGIS/rest/services/World_Imagery/MapServer/tile/{z}/{y}/{x}', { attribution: 'Esri' }), 49 topo: L.tileLayer('https://{s}.tile.opentopomap.org/{z}/{x}/{y}.png', { attribution: 'OpenTopoMap', maxZoom: 17 }), 50 roads: L.tileLayer('https://services.arcgisonline.com/ArcGIS/rest/services/Reference/World_Transportation/MapServer/tile/{z}/{y}/{x}', { attribution: 'Esri', pane: 'overlayPane', zIndex: 200 }), 51 labels: L.tileLayer('https://services.arcgisonline.com/ArcGIS/rest/services/Reference/World_Boundaries_and_Places/MapServer/tile/{z}/{y}/{x}', { attribution: 'Esri', pane: 'overlayPane', zIndex: 300 }) 52 }; 53 54 if (settings.satelliteLayer === 'on') { 55 layers.sat.addTo(map); 56 if (settings.mapRoads === 'on') layers.roads.addTo(map); 57 if (settings.mapLabels === 'on') layers.labels.addTo(map); 58 } else if (settings.topoLayerDefault === 'on') { 59 layers.topo.addTo(map); 60 } 61 62 if (settings.grayscale > 0 && !map.hasLayer(layers.sat)) { 63 $('#js-wpv-addon-maps-render-' + settings.mapId + ' .leaflet-tile-pane').css('filter', 'grayscale(' + settings.grayscale + ')'); 64 } 65 66 setupLayerButtons($, map, settings, layers); 67 68 if (settings.markerCluster === 'on') setupMarkerClusters($, map, settings); 69 if (settings.zoomLevel !== null && settings.zoomLevel !== '') map.setZoom(settings.zoomLevel); 70 71 }, 200); 72} 73 74function setupLayerButtons($, map, settings, layers) { 75 const $container = $('#js-wpv-addon-maps-render-' + settings.mapId); 76 if (!$container.length) return; 77 78 const imgPath = settings.pluginUrl + 'assets/images/'; 79 const hasSatBtn = settings.satelliteButton !== 'off'; 80 const hasTopoBtn = settings.topoButton !== 'off'; 81 82 const updateGrayscale = () => { 83 const grayscale = (settings.grayscale > 0 && !map.hasLayer(layers.sat)) ? `grayscale(${settings.grayscale})` : 'none'; 84 $('#js-wpv-addon-maps-render-' + settings.mapId + ' .leaflet-tile-pane').css('filter', grayscale); 85 }; 86 87 if (hasSatBtn) { 88 const btnId = 'btn-sat-' + settings.mapId; 89 if (!$('#' + btnId).length) { 90 $container.append(`<div class="aotm-map-btn" id="${btnId}" style="left:10px; background-image:url(${imgPath}satellite.png);"></div>`); 91 const $btn = $('#' + btnId); 92 if (map.hasLayer(layers.sat)) $btn.addClass('active'); 93 94 $btn.on('click', function() { 95 const isSatActive = map.hasLayer(layers.sat); 96 map.removeLayer(layers.sat); 97 map.removeLayer(layers.topo); 98 map.removeLayer(layers.roads); 99 map.removeLayer(layers.labels); 100 $('.aotm-map-btn').removeClass('active'); 101 102 if (!isSatActive) { 103 layers.sat.addTo(map); 104 if (settings.mapRoads === 'on') layers.roads.addTo(map); 105 if (settings.mapLabels === 'on') layers.labels.addTo(map); 106 $btn.addClass('active'); 107 } 108 updateGrayscale(); 109 }); 110 } 111 } 112 113 if (hasTopoBtn) { 114 const btnId = 'btn-topo-' + settings.mapId; 115 const leftPos = (hasSatBtn) ? '95px' : '10px'; 116 if (!$('#' + btnId).length) { 117 $container.append(`<div class="aotm-map-btn" id="${btnId}" style="left:${leftPos}; background-image:url(${imgPath}topo.png);"></div>`); 118 const $btn = $('#' + btnId); 119 120 if (map.hasLayer(layers.topo)) $btn.addClass('active'); 121 122 $btn.on('click', function() { 123 const isTopoActive = map.hasLayer(layers.topo); 124 map.removeLayer(layers.sat); 125 map.removeLayer(layers.topo); 126 map.removeLayer(layers.roads); 127 map.removeLayer(layers.labels); 128 $('.aotm-map-btn').removeClass('active'); 129 130 if (!isTopoActive) { 131 layers.topo.addTo(map); 132 $btn.addClass('active'); 133 } 134 updateGrayscale(); 135 }); 136 } 137 } 138} 139 140function aotmLoadPaths(map, settings) { 141 let allPaths = settings.paths ? [...settings.paths] : []; 142 if (window.AOTM_MARKERS?.[settings.mapId]) {
143 window.AOTM_MARKERS[settings.mapId].forEach(item => { if (item.paths) allPaths.push(...item.paths); }); 144 } 145 const markers = WPViews?.view_addon_maps?.markers?.[settings.mapId] || {}; 146 const hasMarkers = Object.keys(markers).length > 0; 147 148 allPaths.forEach(function (url) { 149 const ext = url.split('.').pop().toLowerCase(); 150 if (ext === 'kml' && typeof L.KML === 'function') { 151 fetch(url).then(r => r.text()).then(txt => { 152 const kml = new L.KML(new DOMParser().parseFromString(txt, 'text/xml')); 153 map.addLayer(kml); 154 if (!hasMarkers && kml.getBounds && kml.getBounds().isValid()) map.fitBounds(kml.getBounds()); 155 }); 156 } 157 if (ext === 'gpx' && typeof L.GPX === 'function') { 158 new L.GPX(url, { async: true, marker_options: { startIconUrl: null, endIconUrl: null, shadowUrl: null } }) 159 .on('loaded', function(e) { 160 if (!hasMarkers && e.target.getBounds().isValid()) map.fitBounds(e.target.getBounds()); 161 }).addTo(map); 162 } 163 }); 164} 165 166function setupMarkerClusters($, map, settings) { 167 const markers = Object.values(WPViews?.view_addon_maps?.markers?.[settings.mapId] || {}); 168 if (markers.length === 0) return; 169 const hexToRgba = (hex, a) => `rgba(${parseInt(hex.slice(1,3),16)},${parseInt(hex.slice(3,5),16)},${parseInt(hex.slice(5,7),16)},${a})`; 170 const color = settings.clusterColor || '#ff5b00'; 171 const bg = hexToRgba(color, 0.6); 172 const clusterGroup = L.markerClusterGroup({ 173 disableClusteringAtZoom: settings.zoomCluster, 174 iconCreateFunction: c => { 175 const count = c.getChildCount(); 176 return new L.DivIcon({ 177 html: `<div style=\"background-color:${bg}\"><span style=\"color:white\">${count}</span></div>`, 178 className: 'marker-cluster marker-cluster-small', 179 iconSize: new L.Point(40, 40) 180 }); 181 } 182 }); 183 clusterGroup.addLayers(markers); 184 const update = () => { 185 if (map.getZoom() >= settings.zoomCluster) { 186 if (map.hasLayer(clusterGroup)) map.removeLayer(clusterGroup); 187 markers.forEach(m => { if (!map.hasLayer(m)) map.addLayer(m); }); 188 } else { 189 markers.forEach(m => map.removeLayer(m)); 190 if (!map.hasLayer(clusterGroup)) map.addLayer(clusterGroup); 191 } 192 }; 193 map.on('zoomend', update); 194 update(); 195}
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.