vue2+Ts中openLayer绘图工具组件封装

vue2+Ts中openLayer绘图工具组件封装

效果:
在这里插入图片描述
封装组件代码:

<!-- openLayer绘图工具 -->
<template><a-button-group v-show="isShow"><a-button v-if="shouldShowButton('point')" @click="draw('Point')">绘点<a-icon type="dot-chart" /></a-button><a-button v-if="shouldShowButton('line')" @click="draw('LineString')">绘线<a-icon type="line-chart" /></a-button><a-button v-if="shouldShowButton('polygon')" @click="draw('Polygon')">绘面<a-icon type="border" /></a-button><a-button v-if="shouldShowButton('edit')" @click="edit()">编辑<a-icon type="edit" /></a-button><a-button v-if="shouldShowButton('undo')" @click="undo()">撤销<a-icon type="undo" /></a-button><a-button v-if="shouldShowButton('redo')" @click="redo()">重做<a-icon type="redo" /></a-button><a-button v-if="shouldShowButton('save')" @click="save()">保存<a-icon type="save" /></a-button></a-button-group>
</template><script lang="ts">
import abpbase from '@/libs/abpbase';
import VectorSource from 'ol/source/Vector';
import Map from 'ol/Map';
import { Component, Emit, Prop } from 'vue-property-decorator';
import ol from 'ol';
import VectorLayer from 'ol/layer/Vector';
import Draw, { createRegularPolygon } from 'ol/interaction/Draw';
import Modify from 'ol/interaction/Modify';
import {singleClick, doubleClick, pointerMove, never,
} from 'ol/events/condition';
import Select from 'ol/interaction/Select';
import Translate from 'ol/interaction/Translate';
import Snap from 'ol/interaction/Snap';
// eslint-disable-next-line import/no-unresolved
import * as jsts_io from 'jsts/org/locationtech/jts/io';
import {Style, Fill, Stroke, Circle,
} from 'ol/style';
import {LinearRing,LineString,MultiLineString,MultiPoint,MultiPolygon,Point,Polygon,
} from 'ol/geom.js';
import MapBrowserEventType from 'ol/MapBrowserEventType';@Component({name: 'OpenLayerDrawTool',components: {},
})
export default class OpenLayerDrawTool extends abpbase {/*** 最大可绘制要素数量*/@Prop({type:Number, default:1})maxFeatures@Prop({ type: Array, default: () => ["point", "line", "polygon", "undo", "redo", "save", "edit"] })buttonsToShow: string[];/*** 编辑操作*/editOperation: Modify;shouldShowButton(buttonName: string): boolean {return this.buttonsToShow.includes(buttonName);}/*** 绘制的矢量图层*/drawVectorLayer: VectorLayer<any>;/*** 绘制的数据源*/drawSource: VectorSource;/*** 传入的openLayer地图*/map: Map = null;/*** 绘制操作*/drawOperation: Draw;/*** 绘制的图形堆栈*/drawStack = []/*** 重做的图形堆栈*/redoStack = []selectOperation: SelecttranslateOperation: TranslatesnapOperation: Snapget isShow() {return this.map != null;}/*** 初始化地图控件,需要在父组件调用;* @param map openLayer地图对象* @param requestDataId 请求的数据参数*/initCtrl(map: Map) {this.map = map;this.drawSource = new VectorSource();const createCustomStyle = () => (feature) => {const geometryType = feature.getGeometry().getType();let style;switch (geometryType) {case 'Point':style = new Style({image: new Circle({radius: 6,fill: new Fill({ color: 'rgba(255, 0, 0, 0.5)' }),stroke: new Stroke({ color: 'red', width: 2 }),}),});break;case 'LineString':style = new Style({stroke: new Stroke({color: 'blue',width: 4,}),});break;case 'Polygon':style = new Style({fill: new Fill({ color: 'rgba(0, 255, 0, 0.2)' }),stroke: new Stroke({ color: 'green', width: 3 }),});break;default: {break;}}return style;};this.drawVectorLayer = new VectorLayer<any>({source: this.drawSource,style: createCustomStyle(),zIndex: 999,});this.map.addLayer(this.drawVectorLayer);this.$forceUpdate();}draw(type) {this.map.removeInteraction(this.drawOperation);this.drawOperation = new Draw({source: this.drawSource,type,condition: (event) => event.type === MapBrowserEventType.POINTERDOWN && event.originalEvent.button === 0,});this.map.addInteraction(this.drawOperation);this.drawOperation.on('drawend', (e) => {// 为要素分配一个唯一的 IDe.feature.set('id', Date.now());this.drawStack.push(e.feature);// 如果绘制的图形数量超过最大限制,移除最早添加的图形if (this.drawStack.length > this.maxFeatures) {const firstFeature = this.drawStack.shift();this.drawSource.removeFeature(firstFeature);}this.map.removeInteraction(this.drawOperation);});}undo() {const lastFeature = this.drawStack.pop();if (lastFeature) {this.drawSource.removeFeature(lastFeature);this.redoStack.push(lastFeature);}}redo() {const lastFeature = this.redoStack.pop();if (lastFeature) {// 如果绘制的图形数量达到最大限制,移除最早添加的图形并将其从重做堆栈中移除if (this.drawStack.length >= this.maxFeatures) {const firstFeature = this.drawStack.shift();this.drawSource.removeFeature(firstFeature);}this.drawSource.addFeature(lastFeature);this.drawStack.push(lastFeature);}}save() {const parser = new jsts_io.OL3Parser();parser.inject(Point,LineString,LinearRing,Polygon,MultiPoint,MultiLineString,MultiPolygon,);const format = new jsts_io.WKTWriter();const features = this.drawSource.getFeatures();const wkts = features.map((feature) => {const olGeom = feature.getGeometry();const jstsGeom = parser.read(olGeom);return format.write(jstsGeom);});console.log(JSON.stringify(wkts));}mounted() {}edit() {// 移除 drawOperation 交互this.map.removeInteraction(this.drawOperation);// // 创建 selectOperation 交互对象this.selectOperation = new Select({condition: singleClick,});this.map.addInteraction(this.selectOperation);// 创建 translateOperation 交互对象this.translateOperation = new Translate({features: this.selectOperation.getFeatures(),});this.map.addInteraction(this.translateOperation);// 创建 modifyOperation 交互对象this.editOperation = new Modify({features: this.selectOperation.getFeatures(),});this.editOperation.setActive(false);this.map.addInteraction(this.editOperation);this.editOperation.on('modifyend', (e) => {// 更新 drawStack 中的要素const updatedFeature = e.features.getArray()[0];const featureIndex = this.drawStack.findIndex((feature) => feature.get('id') === updatedFeature.get('id'),);if (featureIndex >= 0) {this.drawStack.splice(featureIndex, 1, updatedFeature);}});// 为地图添加双击事件侦听器this.map.on('dblclick', (event) => {const features = this.map.getFeaturesAtPixel(event.pixel);if (features && features.length > 0) {this.editOperation.setActive(true);this.snapOperation.setActive(true);this.translateOperation.setActive(false);} else {this.editOperation.setActive(false);this.snapOperation.setActive(false);this.translateOperation.setActive(true);}});// 为地图添加 pointermove 事件侦听器// this.map.on('pointermove', (event) => {//   const features = this.map.getFeaturesAtPixel(event.pixel);//   if (features && features.length > 0) {//     this.editOperation.setActive(true);//   } else {//     this.editOperation.setActive(false);//   }// });}// 初始化// init() {// }// created() {// }
}
</script><style lang="less" scoped>
.home-wrap {min-width: 1280px;overflow: auto;
}
</style>

父组件使用:

<div class="absolute right-4 top-4"><open-layer-draw-tool ref="drawTool"></open-layer-draw-tool>
</div>initDrawTool() {this.$nextTick(() => {(this.$refs.drawTool as any).initCtrl(this.map);});}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/700968.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Optional用法

说明&#xff1a;Optional和Stream一样&#xff0c;是Java8引入的特性&#xff0c;本文介绍Optional的几个实际用法。Steam流使用&#xff0c;参考下面这篇文章&#xff1a; Stream流使用 使用 1.保证值存在 // 1.保证值存在&#xff0c;pageNumber&#xff0c;pageSizeInte…

汇聚荣电商:拼多多开店需要多少费用?

想要在拼多多这个巨大的电商平台上开一家属于自己的店铺&#xff0c;很多创业者都会关心一个问题&#xff1a;开店需要多少费用?答案并不复杂&#xff0c;但背后的经营哲学和策略却值得深究。接下来&#xff0c;让我们从四个不同的方面来详细探讨这个问题。 一、开店成本分析 …

Linux/ubuntu build编译make时出现has modification time int the future的问题解决方法

针对Linux由于双系统之间的时间冲突导致linux时间经常变化&#xff0c;出现执行make命令时出现“make[2]: Warning: File xxx.c’ has modification time 1.6e05 s in the future “警告的问题&#xff0c;亦或者虚拟机出现相同的问题。 由于时钟同步问题&#xff0c;出现 warn…

1.基于python的单细胞数据预处理-特征选择

文章目录 特征选择背景基于基因离散度基于基因归一化方差基于基因皮尔森近似残差特征选择总结 参考&#xff1a; [1] https://github.com/Starlitnightly/single_cell_tutorial [2] https://github.com/theislab/single-cell-best-practices 特征选择背景 现在已经获得了经过…

C语言中的混合运算

1 混合运算 类型强制转换场景 整型数进行除法运算时&#xff0c;如果运算结果为小数&#xff0c;那么存储浮点数时一定要进行强制转换。例子&#xff1a; #include <stdio.h> //运算强制转换 int main(void) {int i5;//整型float ji/2;//这里做的是整型运算&#xff0…

【STM32】状态机实现定时器按键消抖,处理单击、双击、三击、长按事件

目录 一、简单介绍 二、模块与接线 三、cubemx配置 四、驱动编写 状态图 按键类型定义 参数初始化/复位 按键扫描 串口重定向 主函数 五、效果展示 六、驱动附录 key.c key.h 一、简单介绍 众所周知&#xff0c;普通的机械按键会产生抖动&#xff0c;可以采取硬件…

JavaScript的综合案例

案例要求&#xff1a; 实现一个表单验证 1.当输入框失去焦点时&#xff0c;验证输入的内容是否符合要求 2.当点击注册按钮时&#xff0c;判断所有输入框的内容是否都符合要求&#xff0c;如果不符合要求阻止表单提交 简单的页面实现 <!DOCTYPE html> <html lang&…

【Node.js】事件循环

Node.js 中的事件循环是基于单线程的异步非阻塞模型。它是 Node.js 的核心机制&#xff0c;用于处理非阻塞的 I/O 操作和异步事件。 1. Node.js 事件循环介绍 Node.js 的事件循环是一个 Event Loop&#xff0c;通过异步回调函数的方式实现非阻塞的处理。事件循环会在主线程上…

港股大反攻结束了吗?

‘港股长线见顶了吗&#xff1f;今天开盘就是最高点&#xff0c;然后一路跳水&#xff0c;市场又是一片恐慌。到底是健康的技术性回调&#xff0c;还是市场已经见顶&#xff1f; 港股此轮“大反攻”中&#xff0c;科网股表现十分亮眼。今日港股盘后&#xff0c;阿里巴巴、腾讯…

【Shell】Shell编程之函数

目录 1.Shell函数定义 2.Shell函数的作用 3.函数返回值 4.函数传参 5.函数变量的作用范围 案例 1.Shell函数定义 格式1 function 函数名 { 命令序列 } 格式2 函数名() { 命令序列 } 2.Shell函数的作用 使用函数可以避免代码重复 使用函数可以将大的工程分割为若…

DeepSort / Sort 区别

推荐两篇博文,详细介绍了deepsort的流程及代码大致讲解: https://blog.csdn.net/qq_48764574/article/details/138816891 https://zhuanlan.zhihu.com/p/196622890 DeepSort与Sort区别: 1、Sort 算法利用卡尔曼滤波算法预测检测框在下一帧的状态,将该状态与下一帧的检测结…

什么是工具? 从语言模型视角的综述

24年3月CMU和上海交大的论文“What Are Tools Anyway? A Survey from the Language Model Perspective”。 到底什么是工具&#xff1f; 接下来&#xff0c;工具在哪里以及如何帮助语言模型&#xff1f; 在综述中&#xff0c;对语言模型使用的外部程序工具进行了统一定义&…