OL3 - 无法检测到功能点击

时间:2016-01-05 08:44:04

标签: javascript openstreetmap openlayers-3

我的目标是在OpenLayers 3中创建一个包含多个图层的地图。一个从OpenStreetMaps获取基本提要。另一个是透明层,显示区域的轮廓(尚未完成)。第三个是我遇到问题的一个,它在地图上显示了一系列代表个人感兴趣的网站的图标。我从作为单独脚本文件包含的JS数据结构加载站点。我设法让我的代码添加出现在正确的纬度/经度上的功能。我的下一步是当他们点击图标(显示网站的详细信息)时,让HTML框(div)出现在地图前面。但是,我无法让这个工作。为我的noobish编码道歉,但它真的让我难过,我真的很感激任何帮助。

<!doctype html>
<html lang="en">
  <head>
    <meta charset="utf-8">
    <link rel="stylesheet" href="ol.css" type="text/css">
    <link rel="stylesheet" href="map.css" type="text/css">
    <script src="ol.js" type="text/javascript"></script>
    <script src="sites.js" type="text/javascript"></script>
<script type="text/javascript">


function buildLayerFromSites(allSites)
// allSites is just an array of data structures
{
  var count, site;
  // for each site in the array, make a feature
  for (count=0;count<allSites.length;count++)
  {
    geom = new ol.geom.Point(ol.proj.fromLonLat([allSites[count].longitude,allSites[count].latitude]));
    site = new ol.Feature(geom);
    site.Name = allSites[count].siteName; // <-- can I assign further details in the structure like this?


    var siteStyle = new ol.style.Style({
      image: new ol.style.Icon ({
        src: 'icon-blue.png',
        scale: 0.1,
        opacity: 0.9,
        })
      })
    site.setStyle(siteStyle);
    siteFeatures[count] = site;
  }
  siteSource = new ol.source.Vector ({
    features: siteFeatures
  })
  siteLayer = new ol.layer.Vector({
    source: siteSource
  });
  map.addLayer(siteLayer);
}

</script>
    <title>Map</title>
  </head><body>
...
<div id="map" class="map">
...

<script type="text/javascript">


var map = new ol.Map({
  target: 'map',
  layers: [
    new ol.layer.Tile({
      source: new ol.source.OSM()
    })
  ],
  view: new ol.View({
    center: ol.proj.fromLonLat([115.51, -31.57]),
    zoom: 8
  })
});
buildLayerFromSites(includeSites);  // adds the second layer with the sites


// click event handler, basically same as http://openlayers.org/en/v3.12.1/examples/icon.html
map.on('click', function(evt) {
  var feature = map.forEachFeatureAtPixel(evt.pixel,
    function(feature,layer) {
      return feature;
    });
  if (feature) {
    console.log("feature got clicked on"); // do stuff
  } else {
    console.log("didn't click a feature");
  }
});
</script>
</body>
</html>

地图和图标加载,但是当我点击图标时,无论我放大或缩小,它都没有检测到我点击的图标匹配。问题是,事件处理程序代码与官方示例中的相同,这使我认为这是我创建功能的方式。另一方面,功能显示为图标,它只是单击事件似乎不起作用。从示例中改变鼠标光标会发生类似的奇怪事情。我猜它是因为我不理解数据/函数在OL中的结构方式,我发现文档并没有完全解释它是如何工作的,所以我一直在编写这样的片段试图看看:

var myLayers = map.getLayers();
console.log("keys - " + myLayers.getKeys);  // prints out 'function (){return Object.keys(this.B)}' - what does that mean?
var mySource = myLayers.getSource;
console.log("source" + mySource.getProjection); // doesn't work
var features = mySource.getFeatures;  // says mySource is undefined

当然它完全失败了。

如何让它检测图标/功能的点击次数,以便我可以告诉div出现并在合适的时间显示我的数据?我这样做了吗?关于数据/功能的工作方式,我不了解什么?我是一个很棒的JS菜鸟,所以我希望我不会做一些愚蠢的事情,但这会给我带来很大的麻烦,我真的可以帮到你!谢谢大家!

4 个答案:

答案 0 :(得分:0)

  

console.log(“keys - ”+ myLayers.getKeys); //打印出'function(){return Object.keys(this.B)}' - 这是什么意思?

这意味着您正在尝试打印函数本身,而不是它的执行结果。应该是

console.log("keys - " + myLayers.getKeys())

相同
 mySource.getProjection();
 mySource.getFeatures();

通常,如果属性名称以“get”开头并且用camelCase编写 - 它就是一个函数。记住这个提示:)

答案 1 :(得分:0)

长时间盯着我的屏幕,把头撞到我的桌子上,我偶然发现了解决问题的方法。它有点模糊但令人头脑麻木的简单/愚蠢/愚蠢。我以为我会在这里为其他人发布解决方案。

我在页面加载时编写了几行代码来调整视口大小,并在调整窗口大小时再次调整视图大小,因此地图将调整为可用用户的浏览器窗口空间。不幸的是,据我所知,OL并不知道它,所以在调整大小后图标和功能不再在同一个地方。我不知道这一点,直到无数个小时后,我随机点击并调整大小,检测到功能点击。

幸运的是,一旦你发现这就是问题,有一种简单的方法可以解决它。基本上只需将 map.updateSize()添加到代码中调整视口大小的部分。到目前为止,这似乎解决了这个问题。

答案 2 :(得分:0)

如果其他人遇到此问题:我的解决方案是将功能图标 PNG图片更改为不透明(无颜色)。

如果您的图片是PNG且具有透明性,则在透明的地方将无法单击(我在OpenLayers v5上)。例如,我有一个圆形的图像,里面是透明的,外面是彩色的。 当我将图像更改为中间没有透明度的东西时(当然它仍然可以是PNG),一切都很好。看来这就是OpenLayers处理图像像素的方式-如果可以通过图像看到地图,则即使您位于Feature上,也不是“悬停”。

答案 3 :(得分:0)

该功能仅适用于要素像素,因此要解决此问题,您可以在图像中添加一些样式,例如rgb(255,0,0,0.001)属性。我已经尝试过,并且为我工作。