2016-03-18 17 views
5

ho trovato il seguente codice per mostrare e nascondere i livelli nella Mapbox GL:Visualizza e nascondere le caratteristiche di un livello in Mapbox GL JS

https://www.mapbox.com/mapbox-gl-js/example/toggle-layers/

Questo è utile, però, ho solo un .geojson strato (polilinee) con tutti i dati necessari e non è necessario creare livelli separati.

Mi piacerebbe fare la stessa identica funzione di poter mostrare e nascondere le caratteristiche di un livello nel menu mappa. Ci sono un totale di 12 diversi tipi di funzionalità, contenuti nella colonna denominata "Tipo". Vorrei attivare e disattivare i tipi, proprio come nell'esempio.

C'è un modo semplice per farlo in JS con lo set.Filter? https://github.com/mapbox/mapbox-gl-js/blob/e9386d2880cc2c33e9a5a16b9bcb58834026a078/js/ui/map.js#L559-L562

Non sono riuscito a trovare una soluzione.

mio strato .geojson è qui: https://iskandarblue.github.io/mapbox/data/simplify_prototype.geojson

<!DOCTYPE html> 
<html> 
<head> 
    <meta charset='utf-8' /> 
    <title></title> 
    <meta name='viewport' content='initial-scale=1,maximum-scale=1,user-scalable=no' /> 
    <script src='https://api.tiles.mapbox.com/mapbox-gl-js/v0.15.0/mapbox-gl.js'></script> 
    <link href='https://api.tiles.mapbox.com/mapbox-gl-js/v0.15.0/mapbox-gl.css' rel='stylesheet' /> 
    <style> 
     body { margin:0; padding:0; } 
     #map { position:absolute; top:0; bottom:0; width:100%; } 
    </style> 
</head> 
<body> 

<style> 
    #menu { 
     background: #fff; 
     position: absolute; 
     z-index: 1; 
     top: 10px; 
     right: 10px; 
     border-radius: 3px; 
     width: 120px; 
     border: 1px solid rgba(0,0,0,0.4); 
     font-family: 'Open Sans', sans-serif; 
    } 

    #menu a { 
     font-size: 13px; 
     color: #404040; 
     display: block; 
     margin: 0; 
     padding: 0; 
     padding: 10px; 
     text-decoration: none; 
     border-bottom: 1px solid rgba(0,0,0,0.25); 
     text-align: center; 
    } 

    #menu a:last-child { 
     border: none; 
    } 

    #menu a:hover { 
     background-color: #f8f8f8; 
     color: #404040; 
    } 

    #menu a.active { 
     background-color: #3887be; 
     color: #ffffff; 
    } 

    #menu a.active:hover { 
     background: #3074a4; 
    } 
</style> 

<nav id="menu"></nav> 
<div id="map"></div> 

<script> 
mapboxgl.accessToken = 'pk.eyJ1IjoiaXNrYW5kYXJibHVlIiwiYSI6ImNpazE3MTJldjAzYzZ1Nm0wdXZnMGU2MGMifQ.i3E1_b9QXJS8xXuPy3OTcg'; 
var map = new mapboxgl.Map({ 
    container: 'map', 
    style: 'mapbox://styles/mapbox/streets-v8', 
    zoom: 15, 
    center: [-71.97722138410576, -13.517379300798098] 
}); 

map.on('style.load', function() { 
    map.addSource('museums', { 
     type: 'vector', 
     url: 'mapbox://mapbox.2opop9hr' 
    }); 
    map.addLayer({ 
     'id': 'museums', 
     'type': 'circle', 
     'source': 'museums', 
     'paint': { 
      'circle-radius': 8, 
      'circle-color': 'rgba(55,148,179,1)' 
     }, 
     'source-layer': 'museum-cusco' 
    }); 

    map.addSource('contours', { 
     type: 'vector', 
     url: 'mapbox://mapbox.mapbox-terrain-v2' 
    }); 
    map.addLayer({ 
     'id': 'contours', 
     'type': 'line', 
     'source': 'contours', 
     'source-layer': 'contour', 
     'layout': { 
      'line-join': 'round', 
      'line-cap': 'round' 
     }, 
     'paint': { 
      'line-color': '#877b59', 
      'line-width': 1 
     } 
    }); 
}); 

addLayer('Contours', 'contours'); 
addLayer('Museums', 'museums'); 

function addLayer(name, id) { 
    var link = document.createElement('a'); 
    link.href = '#'; 
    link.className = 'active'; 
    link.textContent = name; 

    link.onclick = function (e) { 
     e.preventDefault(); 
     e.stopPropagation(); 

     var visibility = map.getLayoutProperty(id, 'visibility'); 

     if (visibility === 'visible') { 
      map.setLayoutProperty(id, 'visibility', 'none'); 
      this.className = ''; 
     } else { 
      this.className = 'active'; 
      map.setLayoutProperty(id, 'visibility', 'visible'); 
     } 
    }; 

    var layers = document.getElementById('menu'); 
    layers.appendChild(link); 
} 

</script> 

</body> 
</html> 
+0

Hai visto https://www.mapbox.com/mapbox-gl-js/example/filter-markers/? Questo esempio dimostra tale comportamento (nascondendo le funzionalità di visualizzazione tramite un filtro). – tristen

risposta

2

stavo cercando di fare la stessa cosa e finito per usare filtri combinati. Simile a voi, ho una mappa con una fonte GeoJSON:

map.addSource('routes', { 
    'type': 'geojson', 
    'data': geoJSON 
}); 

su quella mappa, ho un livello con tutti i miei percorsi:

map.addLayer({ 
    'id': 'route-no-hover', 
    'type': 'line', 
    'source': 'routes', 
    'layout': { 
     'line-join': 'round', 
     'line-cap': 'round' 
    }, 
    'paint': { 
     'line-color': '#333', 
     'line-opacity': 0.25, 
     'line-width': 4 
    } 
}); 

sto messa in vendita di tutti i miei percorsi e fornendo il utente con la disponibilità per attivarli e disattivarli. Sembra che il mio concetto di "percorsi" sia equivalente ai tuoi "tipi". Quando un utente fa clic su un nome di percorso per spegnerlo, spingo ID di quel percorso in un array chiamato 'nascosta' quindi creare una serie di filtri in base a tali ID:

let hiddenFilters = ['all']; 
_.forEach(mapMeta.hidden, (route) => { 
    hiddenFilters.push([ 
     '!=', 
     'id', 
     route.toString() 
    ]); 
}); 
map.setFilter('route-no-hover', hiddenFilters); 

Si noti che sto usando lodash ma si potrebbe utilizzare Array.forEach()

sto efficace creazione di un filtro che assomiglia this combining filter described in the filtering docs:

[ 
    "all", 
    ["!=", "id", "routeIDHere"], 
    ["!=", "id", "routeIDHere"], 
    ... 
] 

questo esclude tutti i percorsi con gli ID specificata. Nel tuo caso, penso che tu voglia avere qualcosa come

[ 
    "all", 
    ["!=", "type" "YourTypeNameHere"] 
    ... 
]