2014-10-24 2 views
2

나는 이름과 그림, 그리고 물론 경도와 위도와 함께 많은 다른 위치의 배열을 가지고있다. 이것을지도에 직접 붙여 놓으면 혼란스러워집니다. 그래서 Clusters을 사용하려고합니다. features을 만드는OpenLayers의 클러스터에서 기능 가져 오기?

시작 :

var vSource = new ol.source.Vector({ features: features}); 

var vFeatures = vSource.getFeatures(); 

var clusterSource = new ol.source.Cluster({ 
        distance: 20, 
        source: vSource}); 

내가 다음 몇 가지 아이콘

var clusters = new ol.layer.Vector({ 
      source: clusterSource, 
      style : new ol.style.Style({ 
       image: new ol.style.Icon(({ 
       src: 'image/image.png'})), 
      text: new ol.style.Text({ 
       font: '18px Helvetica, Arial Bold, sans-serif', 
       text: size.toString(), 
       fill: new ol.style.Fill({ 
       color: '#fff' 
       }) 
}) 
map.add(clusters) 

I와 클러스터의 스타일 :

for(var i = 0; i < points.length; i++){ 
    features[i] = new ol.Feature({ 
    population: 4000, 
    name : points[i].name, 
    geometry: new ol.geom.Point(
    ol.proj.transform([ 
    points[i].long, 
    points[i].lat], 
    'EPSG:4326', oProjection)) 
    }); 
} 

그때 기능을 가진 벡터 클러스터를 채울 나중에 기능에서 "이름"을 가져와야하는 onclick 메소드가 있습니다. 그러나 그것이 인쇄 할 수있는 유일한 것은 기하학입니다, 그것은 개체의 이름이 클러스터에서 사라지는 것과 같습니다. 예를 들어 clusterSource.getFeatures()을 수행하면 [] 인 빈 벡터가 반환됩니다.

function addOverlays(points){ 
    for(var i = 0; i<points.length;i++){ 
     var element = document.getElementById(points[i].id); 
     var popup = new ol.Overlay({ 
      element: element, 
      positioning: 'bottom-center', 
      stopEvent: false 
     }); 
     map.addOverlay(popup); 
     // display popup on click 
    } 

    // display popup on click 
    map.on('click', function(evt) { 
     var feature = map.forEachFeatureAtPixel(evt.pixel, 
      function(feature, layer) { 
       console.log("feature on click: ",feature); 
       return feature; 
      }); 
     if (feature) { 
      var geometry = feature.getGeometry(); 
      var coord = geometry.getCoordinates(); 
      popup.setPosition(coord); 
      console.log(feature.get('name')); 
      $(element).popover({ 
       'placement': 'bottom', 
       'html': true, 
       'content': feature.get('name') //THIS IS THE TROUBLE 
      }); 
      $(element).popover('show'); 
     } else { 
      $(element).popover('destroy'); 
     } 
    }); 
} 

addOverlay 메서드는 기능의 이름을 가져올 수 없으며 매우 이상한 "undefined"를 반환합니다. 도움? 어떤 도움을 주시겠습니까? 이는 클러스터에 추가 될 때 기능이 중지 된 것과 같습니다.

답변

7

따라서 클러스터링을 통해 OL3은 클러스터 된 모든 기능을 그 아래에 래핑하는 새로운 기능을 만듭니다. 클러스터 된 기능을 보면 당신이 값에서이 참조는 속성 :

values_: Object 
    features: Array[19] 
    geometry: ol.geom.Point 

getFeatures()이 작동하지 않는 이유 클러스터 기능을 작업 할 때 만들어 질 때, 그들은 단지이 두 값을 가지고있다.

function isCluster(feature) { 
    if (!feature || !feature.get('features')) { 
     return false; 
    } 
    return feature.get('features').length > 1; 
} 

map.on('click', function(evt) { 
    var feature = map.forEachFeatureAtPixel(evt.pixel, 
        function(feature) { return feature; }); 
    if (isCluster(feature)) { 
    // is a cluster, so loop through all the underlying features 
    var features = feature.get('features'); 
    for(var i = 0; i < features.length; i++) { 
     // here you'll have access to your normal attributes: 
     console.log(features[i].get('name')); 
    } 
    } else { 
    // not a cluster 
    console.log(feature.get('name')); 
    } 
}); 
+0

아주 좋은 해결책이지만, 아직 클러스터되지 않은 단수 기능에 대해서는 문제가 있지만 결국에는 얻을 것입니다. – radhoo

+0

@radhoo 나는 이것이 오래되었다는 것을 알고 있지만 같은 문제를 발견하고'feature.get ('name')'을'feature.get ('features')로 대체하여 해결했다. get ('name')'in 그밖에. 도움이 되었기를 바랍니다. –

+0

Tim의 코드는 클러스터뿐만 아니라 단일 기능을 모두 지원하도록 이미 수정되었습니다. 의견은 올 바르고 게시 된 코드와 일치합니다. – radhoo

3

아직 댓글을 올릴 수 없습니다 (평판이 충분하지 않음).하지만 예를 들어 내 솔루션을 추가하고 싶습니다. 클러스터 된 및 클러스터되지 않은 기능에 대한 팝업이 표시됩니다. @Timh의 예와 같습니다.

그러나 줌 레벨이 낮고 클러스터링이 "해체"되면 클러스터에있는 기능을 클릭하면 팝업이 undefined으로 표시됩니다.

그래서, 당신은

if (typeof feature.get('features') === 'undefined') { 
    // feature.get('whatever'); 
} else { 
    var cfeatures = feature.get('features'); 
    for(var i = 0; i < cfeatures.length; i++) { 
    //like in the example of timh 
    } 
} 

순간에 (시각적 인 방법으로) 클러스터되지 않은 클러스터, 클러스터되지 않은 및의 기능에서 예 : 팝업을 받고와 동일한 기능을 수행 할 수 있습니다.

편집 : Example with Popups

0
나는 담당자가 없지만이 좋지만 radhoo가 아니라 하나의 기능에 문제가 이유입니다 (결함을 가지고 Timh의 솔루션에 대한 의견이기 때문에 제가 말씀 드릴 수 없습니다

그의 코멘트에서 기술했다).

그것은 하나 개의 기능이 포함 된 경우에도 여전히 클러스터이기 때문에 하나 개 이상의 기능이있는 경우 "isCluster"기능이 확인 안

function isCluster(feature) { 
    return !feature || !feature.get('features'); 
} 

그래서 같은 방식으로 모든 클러스터를 처리하기 위해 더 나은 및 선택적으로 피처 개체를 별도로 처리합니다.