openlayers之地图测距测面

项目背景vue-cli3.0

public下html需要引入文件

<link rel="stylesheet" href="<%= BASE_URL %>./css/gr-ol.css" type="text/css">
<script src="<%= BASE_URL %>./js/ol.js" type="text/javascript"></script>

这里地图为公共组件,方法写在公共组件的init方法里,kpst._this为地图对象

调用

     //测距/面
      var draw = me.map._this.interactions.getArray()[10]
      me.map._this.removeInteraction(draw);
      if (data.name == '测距' || data.name == '测面') {
        me.map._this.interactions.array_ = arr.slice(0, 10)
        if (data.name == '测距') {
          me.mtype = 'LineString'
        } else {
          me.mtype = 'Polygon'
        }
        me.map._this.measure(me.mtype)   //map已挂载到vue原型Vue.prototype.map = map
      } else if (data.name == '清除') {
        me.map._this.clear()
      }

方法挂载

 // 测距、面
    //创建一个当前要绘制的对象
    var sketch
    //创建一个帮助提示框对象
    var helpTooltipElement;
    //创建一个帮助提示信息对象
    var helpTooltip;
    //创建一个测量提示框对象
    var measureTooltipElement;
    //创建一个测量提示信息对象
    var measureTooltip;
    //继续绘制多边形的提示信息
    var continuePolygonMsg
    //继续绘制线段的提示信息
    var continueLineMsg
    //帮助提示信息
    var helpMsg
    //定义矢量数据源
    var source = new ol.source.Vector();
    //定义矢量图层
    var vector = new ol.layer.Vector({
      source: source,
      style: new ol.style.Style({
        fill: new ol.style.Fill({
          color: 'rgba(255,255,255,0.2)'
        }),
        stroke: new ol.style.Stroke({
          color: '#e21e0a',
           2
        }),
        image: new ol.style.Circle({
          radius: 5,
          fill: new ol.style.Fill({
            color: '#ffcc33'
          })
        })
      })
    });
    //创建比例尺控件
    var scaleLineControl = new ol.control.ScaleLine({
      units: 'metric',
      target: 'scalebar',
      className: 'ol-scale-line'
    });
    function measure(mtype) {
      sketch = new ol.Feature();
      // continuePolygonMsg = 'Click to continue drawing the polygon';
      // continueLineMsg = 'Click to continue drawing the line';
      //将矢量图层添加到地图中
      kpst._this.removeLayer(vector);
      kpst._this.addLayer(vector);
      //添加比例尺控件
      kpst._this.removeControl(scaleLineControl);
      kpst._this.addControl(scaleLineControl);
      //鼠标移动触发的函数
      var pointerMoveHandler = function (evt) {
        //如果是平移地图则直接结束
        if (evt.dragging) {
          return;
        }
        //帮助提示信息
        helpMsg = 'Click to start drawing';
        if (sketch) {
          //获取绘图对象的几何要素
          var geom = sketch.getGeometry();
          //如果当前绘制的几何要素是多线段,则将绘制提示信息设置为多线段绘制提示信息
          // if (geom instanceof ol.geom.Polygon) {
          //   helpMsg = continuePolygonMsg;
          // } else if (geom instanceof ol.geom.LineString) {
          //   helpMsg = continueLineMsg;
          // }
        }
        //设置帮助提示要素的内标签为帮助提示信息
        // if (helpTooltipElement)
        // helpTooltipElement.innerHTML = helpMsg;
        //设置帮助提示信息的位置
        // if (helpTooltip)
        helpTooltip.setPosition(evt.coordinate);
        //移除帮助提示要素的隐藏样式
        // $(helpTooltipElement).removeClass('hidden');
        removeClass(document.getElementsByClassName('tooltip')[0], 'hidden')
      };

      //触发pointermove事件
      kpst._this.on('pointermove', pointerMoveHandler);

      //当鼠标移除地图视图的时为帮助提示要素添加隐藏样式
      document.querySelector('.ol-viewport').onmouseout = function () {
        addClass(document.getElementsByClassName('tooltip')[0], 'hidden')
      }
      // 判断class有无
      function hasClass(ele, cls) {
        if (ele) {
          cls = cls || '';
          if (cls.replace(/s/g, '').length == 0) return false; //当cls没有参数时,返回false
          return new RegExp(' ' + cls + ' ').test(' ' + ele.className + ' ');
        }
      }
      //添加class
      function addClass(ele, cls) {
        if (!hasClass(ele, cls) && ele) {
          ele.className = ele.className == '' ? cls : ele.className + ' ' + cls;
        }
      }
      // 去除class
      function removeClass(ele, cls) {
        if (hasClass(ele, cls) && ele) {
          var newClass = ' ' + ele.className.replace(/[	
]/g, '') + ' ';
          while (newClass.indexOf(' ' + cls + ' ') >= 0) {
            newClass = newClass.replace(' ' + cls + ' ', ' ');
          }
          ele.className = newClass.replace(/^s+|s+$/g, '');
        }
      }
      //定义一个交互式绘图对象
      var draw;
      //添加交互式绘图对象的函数
      function addInteraction() {
        //创建一个交互式绘图对象
        draw = new ol.interaction.Draw({
          //绘制的数据源
          source: source,
          //绘制类型
          type: mtype,
          //样式
          style: new ol.style.Style({
            fill: new ol.style.Fill({
              color: 'rgba(255,255,255,0.2)'
            }),
            stroke: new ol.style.Stroke({
              color: 'rgba(0,0,0,0.5)',
              lineDash: [10, 10],
               2
            }),
            image: new ol.style.Circle({
              radius: 5,
              stroke: new ol.style.Stroke({
                color: 'rgba(0,0,0,0.7)'
              }),
              fill: new ol.style.Fill({
                color: 'rgba(255,255,255,0.2)'
              })
            })
          })
        });
        //将交互绘图对象添加到地图中
        kpst._this.addInteraction(draw);
        //创建测量提示框
        createMeasureTooltip();
        //创建帮助提示框
        createHelpTooltip();
        //定义一个事件监听
        var listener;
        //定义一个控制鼠标点击次数的变量
        var count = 0;
        //绘制开始事件
        draw.on('drawstart', function (evt) {
          //The feature being drawn.
          sketch = evt.feature;
          //提示框的坐标
          var tooltipCoord = evt.coordinate;
          //监听几何要素的change事件
          //Increases the revision counter and dispatches a 'change' event.
          listener = sketch.getGeometry().on('change', function (evt) {
            //The event target.
            //获取绘制的几何对象
            var geom = evt.target;
            //定义一个输出对象,用于记录面积和长度
            var output;
            if (geom instanceof ol.geom.Polygon) {
              kpst._this.removeEventListener('singleclick');
              kpst._this.removeEventListener('dblclick');
              //输出多边形的面积
              output = formatArea(geom);
              //Return an interior point of the polygon.
              //获取多变形内部点的坐标
              tooltipCoord = geom.getInteriorPoint().getCoordinates();
            } else if (geom instanceof ol.geom.LineString) {
              //输出多线段的长度
              output = formatLength(geom);
              //Return the last coordinate of the geometry.
              //获取多线段的最后一个点的坐标
              tooltipCoord = geom.getLastCoordinate();
            }
            //设置测量提示框的内标签为最终输出结果
            // if (measureTooltipElement)
            measureTooltipElement.innerHTML = output;
            //设置测量提示信息的位置坐标
            // if (measureTooltip)
            measureTooltip.setPosition(tooltipCoord);
          });
          //地图单击事件
          kpst._this.on('singleclick', function (evt) {
            //设置测量提示信息的位置坐标,用来确定鼠标点击后测量提示框的位置
            // if (measureTooltip)
            measureTooltip.setPosition(evt.coordinate);
            //如果是第一次点击,则设置测量提示框的文本内容为起点
            if (count == 0 && measureTooltipElement) {
              measureTooltipElement.innerHTML = "起点";
            }
            //根据鼠标点击位置生成一个点
            var point = new ol.geom.Point(evt.coordinate);
            //将该点要素添加到矢量数据源中
            source.addFeature(new ol.Feature(point));
            //更改测量提示框的样式,使测量提示框可见
            measureTooltipElement.className = 'tooltip tooltip-static';
            //创建测量提示框
            createMeasureTooltip();
            //点击次数增加
            count++;
          });
          //地图双击事件
          kpst._this.on('dblclick', function (evt) {
            //根据
            var point = new ol.geom.Point(evt.coordinate);
            source.addFeature(new ol.Feature(point));
          });
        }, this);
        //绘制结束事件
        draw.on('drawend', function (evt) {
          count = 0;
          //设置测量提示框的样式
          measureTooltipElement.className = 'tooltip tooltip-static';
          //Set the offset for this overlay.
          //设置偏移量
          measureTooltip.setOffset([0, -7]);
          //清空绘制要素
          sketch = null;
          //清空测量提示要素
          measureTooltipElement = null;
          //创建测量提示框
          createMeasureTooltip();
          //Removes an event listener using the key returned by on() or once().
          //移除事件监听
          ol.Observable.unByKey(listener);
          //移除地图单击事件
          kpst._this.removeEventListener('singleclick');
        }, this);
      }
      //创建帮助提示框
      function createHelpTooltip() {
        //如果已经存在帮助提示框则移除
        if (helpTooltipElement) {
          helpTooltipElement.parentNode.removeChild(helpTooltipElement);
        }
        //创建帮助提示要素的div
        if (!helpTooltipElement)
          helpTooltipElement = document.createElement('div');
        //设置帮助提示要素的样式
        helpTooltipElement.className = 'tooltip hidden';
        //创建一个帮助提示的覆盖标注
        helpTooltip = new ol.Overlay({
          element: helpTooltipElement,
          offset: [15, 0],
          positioning: 'center-left'
        });
        //将帮助提示的覆盖标注添加到地图中
        kpst._this.addOverlay(helpTooltip);
      }
      //创建测量提示框
      function createMeasureTooltip() {
        //创建测量提示框的div
        // if (!measureTooltipElement)
        measureTooltipElement = document.createElement('div');
        measureTooltipElement.setAttribute('id', 'lengthLabel');
        //设置测量提示要素的样式
        measureTooltipElement.className = 'tooltip tooltip-measure';
        //创建一个测量提示的覆盖标注
        measureTooltip = new ol.Overlay({
          element: measureTooltipElement,
          offset: [0, -15],
          positioning: 'bottom-center'
        });
        //将测量提示的覆盖标注添加到地图中
        kpst._this.addOverlay(measureTooltip);
      }
      //格式化测量长度
      var formatLength = function (line) {
        //定义长度变量
        var length;
        //计算平面距离
        length = Math.round(line.getLength() * 100) / 100;
        //定义输出变量
        var output;
        //如果长度大于1000,则使用km单位,否则使用m单位
        if (length > 100) {
          output = (Math.round(length / 1000 * 100) / 100) + ' ' + 'km'; //换算成KM单位
        } else {
          output = (Math.round(length * 100) / 100) + ' ' + 'm'; //m为单位
        }
        return output;
      };
      //格式化测量面积
      var formatArea = function (polygon) {
        //定义面积变量
        var area;
        //获取平面面积
        area = polygon.getArea();
        // }
        //定义输出变量
        var output;
        //当面积大于10000时,转换为平方千米,否则为平方米
        if (area > 1000) {
          output = (Math.round(area / 1000000 * 100) / 100) + ' ' + 'km<sup>2</sup>';
        } else {
          output = (Math.round(area * 100) / 100) + ' ' + 'm<sup>2</sup>';
        }
        return output;
      };
      //添加交互绘图对象
      addInteraction();
    }
    // 清除提示对象
    function clear() {
      source.clear()
      kpst._this.getOverlays().clear();
      kpst._this.removeLayer(vector);
      kpst._this.removeControl(scaleLineControl);
    }
    kpst._this.measure = measure
    kpst._this.clear = clear
原文地址:https://www.cnblogs.com/wwj007/p/11526159.html