PageSourceSearch

https://wildernessengland.com/wp-content/themes/wildernessuniversal/js/google-maps.js?v=2035

js wildernessengland.com collected 2026-09-26 10:05:57 UTC 14,729 bytes, 460 lines download raw bytes

1(function( $ ) {
2
3  // 1) Define available map style arrays
4  var mapStyles = {
5    default: null,
6
7    silver: [
8      { elementType: 'geometry', stylers: [{ color: '#f5f5f5' }] },
9      { elementType: 'labels.icon', stylers: [{ visibility: 'off' }] },
10      { elementType: 'labels.text.fill', stylers: [{ color: '#616161' }] },
11      { elementType: 'labels.text.stroke', stylers: [{ color: '#f5f5f5' }] },
12      {
13        featureType: 'administrative.land_parcel',
14        elementType: 'labels.text.fill',
15        stylers: [{ color: '#bdbdbd' }]
16      },
17      {
18        featureType: 'poi',
19        elementType: 'geometry',
20        stylers: [{ color: '#eeeeee' }]
21      },
22      {
23        featureType: 'poi',
24        elementType: 'labels.text.fill',
25        stylers: [{ color: '#757575' }]
26      },
27      {
28        featureType: 'road',
29        elementType: 'geometry',
30        stylers: [{ color: '#ffffff' }]
31      },
32      {
33        featureType: 'road.arterial',
34        elementType: 'labels.text.fill',
35        stylers: [{ color: '#757575' }]
36      },
37      {
38        featureType: 'road.highway',
39        elementType: 'geometry',
40        stylers: [{ color: '#dadada' }]
41      },
42      {
43        featureType: 'road.highway',
44        elementType: 'labels.text.fill',
45        stylers: [{ color: '#616161' }]
46      },
47      {
48        featureType: 'road.local',
49        elementType: 'labels.text.fill',
50        stylers: [{ color: '#9e9e9e' }]
51      },
52      {
53        featureType: 'transit.line',
54        elementType: 'geometry',
55        stylers: [{ color: '#e5e5e5' }]
56      },
57      {
58        featureType: 'transit.station',
59        elementType: 'geometry',
60        stylers: [{ color: '#eeeeee' }]
61      },
62      {
63        featureType: 'water',
64        elementType: 'geometry',
65        stylers: [{ color: '#c9c9c9' }]
66      },
67      {
68        featureType: 'water',
69        elementType: 'labels.text.fill',
70        stylers: [{ color: '#9e9e9e' }]
71      }
72    ],
73
74    darkContrast: [
75      { elementType: 'geometry', stylers: [{ color: '#212121' }] },
76      { elementType: 'labels.icon', stylers: [{ visibility: 'off' }] },
77      { elementType: 'labels.text.fill', stylers: [{ color: '#e0e0e0' }] },
78      { elementType: 'labels.text.stroke', stylers: [{ color: '#212121' }] },
79      {
80        featureType: 'landscape',
81        elementType: 'geometry',
82        stylers: [{ color: '#2e2e2e' }]
83      },
84      {
85        featureType: 'poi',
86        elementType: 'geometry',
87        stylers: [{ color: '#2e2e2e' }]
88      },
89      {
90        featureType: 'road',
91        elementType: 'geometry',
92        stylers: [{ color: '#383838' }]
93      },
94      {
95        featureType: 'road',
96        elementType: 'labels.text.fill',
97        stylers: [{ color: '#ffffff' }]
98      },
99      {
100        featureType: 'water',
101        elementType: 'geometry',
102        stylers: [{ color: '#000000' }]
103      }
104    ],
105
106    wilderness: [
107      {
108        featureType: 'landscape',
109        elementType: 'geometry.fill',
110        stylers: [{ color: '#f4f1e9' }]
111      },
112      {
113        featureType: 'water',
114        elementType: 'geometry.fill',
115        stylers: [{ color: '#a8d8e3' }]
116      },
117      {
118        featureType: 'road',
119        elementType: 'geometry',
120        stylers: [{ color: '#e3e3e3' }]
121      },
122      {
123        featureType: 'road.arterial',
124        elementType: 'geometry',
125        stylers: [{ color: '#d7d7d7' }]
126      },
127      {
128        featureType: 'road.highway',
129        elementType: 'geometry',
130        stylers: [{ color: '#cfcfcf' }]
131      },
132      {
133        featureType: 'poi.park',
134        elementType: 'geometry.fill',
135        stylers: [{ color: '#c7d7c1' }]
136      },
137      {
138        elementType: 'labels.text.fill',
139        stylers: [{ color: '#4a4a4a' }]
140      },
141      {
142        elementType: 'labels.icon',
143        stylers: [{ visibility: 'off' }]
144      },
145      {
146        featureType: 'poi',
147        elementType: 'labels.text.fill',
148        stylers: [{ color: '#6b6b6b' }]
149      },
150      {
151        featureType: 'transit.line',
152        elementType: 'geometry',
153        stylers: [{ color: '#e5e5e5' }]
154      }
155    ]
156  };
157
158  // 2) UK & Ireland bounds
159  var ukIrelandBounds = new google.maps.LatLngBounds(
160    { lat: 49.9,  lng: -10.5 },
161    { lat: 61.5,  lng:   2.1 }
162  );
163
164  // 3) Main initMap
165  function initMap($el) {
166    var styleKey      = $el.data('map-style') || 'default';
167    var appliedStyles = mapStyles[styleKey] || null;
168
169    var map = new google.maps.Map($el[0], {
170      zoom:        $el.data('zoom') || 8,
171      scrollwheel: false,
172      mapTypeId:   google.maps.MapTypeId.ROADMAP,
173      styles:      appliedStyles
174    });
175
176    // collect all infoWindows so we can close them together
177    var infoWindows = [];
178    google.maps.event.addListener(map, 'click', function(){
179      infoWindows.forEach(iw => iw.close());
180    });
181
182    // 4) Legacy markers (unchanged)
183    map.markers = [];
184    $el.find('.marker').each(function(){
185      initLegacyMarker($(this), map, infoWindows);
186    });
187
188    // 5) Parse JSON attrs
189    var repJSON = [], regJSON = [];
190    try { repJSON = JSON.parse($el.attr('data-repeater-markers') || '[]'); }
191    catch(e){ console.error('Invalid repeater JSON', e); }
192    try { regJSON = JSON.parse($el.attr('data-regions')          || '[]'); }
193    catch(e){ console.error('Invalid regions JSON', e); }
194
195    // 6) ACF repeater markers
196    var repIW      = new google.maps.InfoWindow({ maxWidth:400 }),
197        repHoverIW = new google.maps.InfoWindow({ disableAutoPan:true });
198    infoWindows.push(repIW, repHoverIW);
199
200    repJSON.forEach(function(m){
201      var normalIcon = m.icon
202        ? { url: m.icon, scaledSize: new google.maps.Size(50,50) }
203        : null;
204      var hoverIcon = m.icon
205        ? { url: m.icon, scaledSize: new google.maps.Size(55,55) }
206        : null;
207
208      var mk = new google.maps.Marker({
209        position: { lat: m.lat, lng: m.lng },
210        map:      map,
211        title:    m.title,
212        icon:     normalIcon
213      });
214
215      // ← **PUSH the repeater marker** so `map.markers` isn’t empty
216      map.markers.push(mk);
217
218      // --- click → full popup with carousel ---
219      mk.addListener('click', function(){
220        infoWindows.forEach(iw => iw.close());
221
222        // build carousel from m.gallery
223        var carouselHTML = '';
224        if (Array.isArray(m.gallery) && m.gallery.length) {
225          carouselHTML = '<div class="map-carousel">';
226          m.gallery.forEach(function(url, i){
227            carouselHTML +=
228              '<img src="' + url + '" class="map-carousel-img" ' +
229              'style="display:' + (i ? 'none' : 'block') + ';width:100%;">';
230          });
231          if (m.gallery.length > 1) {
232            carouselHTML +=
233              '<button class="map-carousel-prev">&#10094;</button>' +
234              '<button class="map-carousel-next">&#10095;</button>';
235          }
236          carouselHTML += '</div>';
237        }
238
239        var html =
240          '<div class="custom-iw">' +
241            carouselHTML +
242            '<button class="iw-close">&times;</button>' +
243            '<h3>' + m.title + '</h3>' +
244            '<div class="iw-desc">' + m.desc + '</div>' +
245          '</div>';
246
247        repIW.setContent(html);
248        repIW.open(map, mk);
249
250        google.maps.event.addListenerOnce(repIW, 'domready', function(){
251          var w = document.querySelector('.gm-style-iw-d');
252          if (w) {
253            w.style.padding    = '0';
254            w.style.marginLeft = '-12px';
255            w.style.overflow   = 'auto';
256          }
257          var btn = document.querySelector('.custom-iw .iw-close');
258          if (btn) btn.addEventListener('click', () => repIW.close());
259          initCarousel();
260        });
261      });
262
263      // --- hover → enlarge + title tooltip ---
264      mk.addListener('mouseover', function(){
265        infoWindows.forEach(iw => iw.close());
266        if (hoverIcon) mk.setIcon(hoverIcon);
267        repHoverIW.setContent(
268          '<div class="hover-title" style="padding:8px 12px;">'
269          + m.title + '</div>'
270        );
271        repHoverIW.open(map, mk);
272      });
273      mk.addListener('mouseout', function(){
274        if (normalIcon) mk.setIcon(normalIcon);
275        repHoverIW.close();
276      });
277    });
278
279    // 7) GeoJSON region overlays (carousel-enabled)
280    if (regJSON.length && google.maps.Data) {
281      var regionHoverIW = new google.maps.InfoWindow({ disableAutoPan:true }),
282          regionClickIW = new google.maps.InfoWindow({ maxWidth:400 });
283      infoWindows.push(regionHoverIW, regionClickIW);
284
285      var baseColors   = ['#3d5a40','#4a7d8c','#a86e3d','#8c7b6c','#5f5f64','#6b4c6c'];
286      var regionColors = regJSON.map(function(_, i){
287        return i < baseColors.length
288          ? baseColors[i]
289          : 'hsl(' + Math.round(360 * i / regJSON.length) + ',40%,60%)';
290      });
291
292      map.data.setStyle(function(feature){
293        var c = feature.getProperty('_color') || baseColors[0];
294        return { strokeColor: c, strokeWeight: 2, fillColor: c, fillOpacity: 0.3 };
295      });
296
297      regJSON.forEach(function(fc, idx){
298        var feats = map.data.addGeoJson(fc);
299        feats.forEach(function(f){
300          f.setProperty('_color', regionColors[idx]);
301        });
302      });
303
304      // hover tooltip
305      map.data.addListener('mouseover', function(e){
306        map.data.overrideStyle(e.feature, { fillOpacity: 0.6 });
307        var bounds = new google.maps.LatLngBounds();
308        e.feature.getGeometry().forEachLatLng(function(latlng){
309          bounds.extend(latlng);
310        });
311        regionHoverIW.setContent(
312          '<div class="hover-title" style="padding:8px 12px;">'
313            + e.feature.getProperty('name') +
314          '</div>'
315        );
316        regionHoverIW.setPosition(bounds.getCenter());
317        regionHoverIW.open(map);
318      });
319      map.data.addListener('mouseout', function(e){
320        map.data.revertStyle(e.feature);
321        regionHoverIW.close();
322      });
323
324      // click → open carousel popup
325      map.data.addListener('click', function(e){
326        infoWindows.forEach(iw => iw.close());
327        var p           = e.feature.getProperty.bind(e.feature),
328            gallery     = p('gallery') || [],
329            carouselHTML = '';
330
331        if (gallery.length) {
332          carouselHTML = '<div class="map-carousel">';
333          gallery.forEach(function(url, i){
334            carouselHTML +=
335              '<img src="' + url + '" class="map-carousel-img" ' +
336              'style="display:' + (i ? 'none' : 'block') + ';width:100%;">';
337          });
338          if (gallery.length > 1) {
339            carouselHTML +=
340              '<button class="map-carousel-prev">&#10094;</button>' +
341              '<button class="map-carousel-next">&#10095;</button>';
342          }
343          carouselHTML += '</div>';
344        }
345
346        var bounds = new google.maps.LatLngBounds();
347        e.feature.getGeometry().forEachLatLng(function(latlng){
348          bounds.extend(latlng);
349        });
350
351        var html =
352          '<div class="custom-iw">' +
353            carouselHTML +
354            '<h3>' + p('name') + '</h3>' +
355            '<div class="iw-desc">' + p('desc') + '</div>' +
356            '<button class="iw-close">&times;</button>' +
357          '</div>';
358
359        regionClickIW.setContent(html);
360        regionClickIW.setPosition(bounds.getCenter());
361        regionClickIW.open(map);
362
363        google.maps.event.addListenerOnce(regionClickIW, 'domready', function(){
364          var w = document.querySelector('.gm-style-iw-d');
365          if (w) {
366            w.style.padding    = '0';
367            w.style.marginLeft = '-12px';
368            w.style.overflow   = 'auto';
369          }
370          var btn = document.querySelector('.custom-iw .iw-close');
371          if (btn) btn.addEventListener('click', () => regionClickIW.close());
372          initCarousel();
373        });
374      });
375    }
376
377    // 8) Initial centering
378    if (regJSON.length) {
379      map.fitBounds(ukIrelandBounds);
380      google.maps.event.addListenerOnce(map, 'bounds_changed', function(){
381        map.setZoom(map.getZoom() + 1);
382      });
383    } else {
384      var allMk = map.markers;
385      if (allMk.length === 1) {
386        map.setCenter(allMk[0].getPosition());
387      } else if (allMk.length > 1) {
388        var bb = new google.maps.LatLngBounds();
389        allMk.forEach(function(mk){
390          bb.extend(mk.getPosition());
391        });
392        map.fitBounds(bb);
393      }
394    }
395
396    return map;
397  }
398
399  // 9) Legacy marker helper (unchanged)
400  function initLegacyMarker($m, map, infoWindows) {
401    var lat = parseFloat($m.data('lat')),
402        lng = parseFloat($m.data('lng'));
403    var mk = new google.maps.Marker({
404      position: { lat: lat, lng: lng },
405      map:      map,
406      icon:     "https://www.wildernessscotland.com/wp-content/themes/wilderness2018/images/new-marker.png"
407    });
408    map.markers.push(mk);
409
410    if ($m.html()) {
411      var iw = new google.maps.InfoWindow({ content: $m.html(), maxWidth: 400 });
412      infoWindows.push(iw);
413      mk.addListener('click', function(){
414        infoWindows.forEach(function(w){ w.close(); });
415        iw.open(map, mk);
416        google.maps.event.addListenerOnce(iw, 'domready', function(){
417          var w = document.querySelector('.gm-style-iw-d');
418          if (w) {
419            w.style.padding    = '0';
420            w.style.marginLeft = '-12px';
421            w.style.overflow   = 'auto';
422          }
423        });
424      });
425    }
426  }
427
428  // 10) Carousel initializer (unchanged)
429  function initCarousel() {
430    var ct   = document.querySelector('.gm-style-iw .map-carousel');
431    if (!ct) return;
432    var imgs = ct.querySelectorAll('.map-carousel-img'),
433        idx  = 0;
434    var next = ct.querySelector('.map-carousel-next'),
435        prev = ct.querySelector('.map-carousel-prev');
436
437    if (next) {
438      next.onclick = function() {
439        imgs[idx].style.display = 'none';
440        idx = (idx + 1) % imgs.length;
441        imgs[idx].style.display = 'block';
442      };
443    }
444    if (prev) {
445      prev.onclick = function() {
446        imgs[idx].style.display = 'none';
447        idx = (idx - 1 + imgs.length) % imgs.length;
448        imgs[idx].style.display = 'block';
449      };
450    }
451  }
452
453  // 11) On DOM ready
454  $(function(){
455    $('.custom-acf-map').each(function(){
456      initMap($(this));
457    });
458  });
459
460})(jQuery);

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.