openlayer点击切换图标

一、项目介绍

在OpenLayers中,我们可以通过点击地图上的要素(Feature)来切换其图标。它的原理就是改变要素的样式(Style)就可以实现切换图标的效果。以下是实现的思路:

  1. 创建一个地图,并添加一个矢量图层(VectorLayer)来显示要素。
  2. 创建两个样式:一个用于默认图标,另一个用于点击后的图标。
  3. 为矢量图层添加点击事件,当点击要素时,检查该要素当前的样式,然后切换到另一个样式。

二、创建图标

js 复制代码
//矢量图层
this.source = new VectorSource({ wrapX: false });
this.vector = new VectorLayer({
    source: this.source,
    zIndex: 100,
    // declutter: true  // 避免图标重叠
});
//地图图层
this.raster = new TileLayer({
     source: new XYZ({
        url: "http://wprd0{1-4}.is.autonavi.com/appmaptile?x={x}&y={y}&z={z}&lang=zh_cn&size=1&scl=2&style=6",
      }),
 });
 
//创建地图
 this.map = new Map({
  layers: [this.raster, this.vector],
  target: id,
  view: new View({
    center: fromLonLat(this.center),
    zoom: 13,
    maxZoom: 22
  }),
  controls: [], // 不添加任何默认控件
});

//创建要素  
const iconFeature = new Feature({
  geometry: new Point(fromLonLat(item.lonlat)),
  name: item?.name,
  id: item?.id ,
  type: "icon",
  description:item.description,
});
//要素的字体样式
const textStyle = new Style({
  text: new Text({
    text: iconFeature.get("name"),
    textAlign: "center",
    textBaseline: "middle",
    offsetY: 45, // 文字向下偏移
    font: "bold 14px Calibri,sans-serif",
    fill: new Fill({
      color: "#333",
    }),
    stroke: new Stroke({
      color: "#fff",
      width: 1,
    }),
  }),
});

//要素的图标样式
const iconStyle = new Style({
  image: new Icon({
    anchor: [0.5, 0.5],
    scale: 0.8,
    src: url,
  }),
});

//添加样式
iconFeature.setStyle([iconStyle, textStyle]);

// 保存原始样式用于选择功能
iconFeature.set('originalStyle', [iconStyle, textStyle]);
iconFeature.set('textStyle', textStyle);

//添加到矢量图层
this.source.addFeature(iconFeature);

三、点击切换图标

我们使用OpenLayers的Select交互来选择地图上的要素。Select交互允许用户通过点击或悬停来选择矢量要素。我们可以通过配置选项来设置选择的方式(例如单击、悬停等),并且可以设置样式来高亮显示选中的要素。

Select的配置参数如下:

  1. condition : 定义触发选择的条件,默认为 ol/events/condition/singleClick。可以替换为其他条件,如 pointerMove 或自定义函数。
  2. style: 用于设置选中要素的样式。可以是一个样式对象、样式数组或一个返回样式的函数。
  3. layers: 指定在哪些图层上进行选择。可以是一个图层数组或一个过滤函数。
  4. filter : 一个过滤函数,用于确定哪些要素可以被选择。返回 true 表示要素可选择。
  5. features: 一个要素集合,用于管理选中的要素。如果不指定,交互会创建一个新的集合。
  6. hitTolerance: 选择要素时鼠标点击的容差范围,单位为像素。默认为0。
  7. multi : 是否允许多选。默认为 false。如果为 true,则可以通过按住某个键(如 shift)进行多选。
  8. toggleCondition : 定义在多选模式下切换要素选择状态的条件。默认为 ol/events/condition/shiftKeyOnly
  9. addCondition : 定义向当前选择中添加要素的条件。默认为 ol/events/condition/never,因为通常使用 toggleCondition
  10. removeCondition : 定义从当前选择中移除要素的条件。默认为 ol/events/condition/never
  11. wrapX : 是否在选择时考虑地图的重复(例如,在世界地图水平重复时)。默认为 true
js 复制代码
import Select from 'ol/interaction/Select'
//创建一个选择交互
 const select = new Select({
  layers: [this.vector,this.raster],
  multi: false 
})

//监听选择变化
select.on('select', (e)=>{
  console.log('select',e)
  //没有选中
  e.deselected.forEach(function(feature) {
    if(feature.values_?.type!=='icon'){
      return
    }
    const originalStyle = feature.get('originalStyle')
    feature.setStyle(originalStyle);
  });
  
  //选中
  e.selected.forEach(function(feature) {
    if(feature.values_?.type!=='icon'){
      return
    }
    const activeStyle = new Style({
      image: new Icon({
        anchor: [0.5, 0.5],
        scale: 0.8,
        src: `/images/index/active.png`,
      }),
    });
    const textStyle = feature.get('textStyle')
    feature.setStyle([activeStyle,textStyle]);
  });
})
//添加到地图
this.map.addInteraction(select)
相关推荐
青衫码上行15 分钟前
【Java Web学习 | 第三篇】CSS(2) - 元素显示模式
java·前端·学习
IT_陈寒23 分钟前
Redis性能翻倍的5个冷门技巧,90%的开发者都不知道第3个!
前端·人工智能·后端
柑橘乌云_27 分钟前
学习记录-package.json的scripts添加参数的方式有那些
前端·学习·node.js·json
清沫44 分钟前
规训 AI Agent 实践
前端·ai编程·cursor
明仔的阳光午后2 小时前
React 入门 02:从单页面应用到多页面应用
前端·react.js·前端框架
.生产的驴2 小时前
React 页面路由ReactRouter 路由跳转 参数传递 路由配置 嵌套路由
前端·javascript·react.js·前端框架·json·ecmascript·html5
非凡ghost2 小时前
批量转双层PDF(可识别各种语言) 中文绿色版
前端·windows·pdf·计算机外设·软件需求
苏卫苏卫苏卫2 小时前
【码源】智能无人仓库管理系统(详细码源下~基于React+TypeScript+Vite):
前端·react.js·typescript·vite·项目设计·智能无人仓库管理系统·码源
打小就很皮...2 小时前
PDF 下载弹窗 content 区域可行性方案
前端·javascript·pdf
Felicity_Gao5 小时前
uni-app VOD 与 COS 选型、开发笔记
前端·笔记·uni-app