zoukankan      html  css  js  c++  java
  • 一种在地图中处理曲线的通用方法

    本文分享一种可以用于处理曲线的算法,是本人在百度地图开源库基础上改造的,可以用于其他地图场景中处理点数据,只要两个以上的点,就可以得到平滑的曲线。例如小程序,将处理后得到的点赋值给polyline的points即可。

    function getCurveByTwoPoints(obj1, obj2) {
        if (!obj1 || !obj2) {
            return null
        }
        var B1 = function (x) {
            return 1 - 2 * x + x * x
        };
        var B2 = function (x) {
            return 2 * x - 2 * x * x
        };
        var B3 = function (x) {
            return x * x
        };
        curveCoordinates = [];
        var count = 30;
        var isFuture = false;
        var t, h, h2, lat3, lng3, j, t2;
        var LnArray = [];
        var i = 0;
        var inc = 0;
        if (typeof(obj2) == "undefined") {
            if (typeof(curveCoordinates) != "undefined") {
                curveCoordinates = []
            }
            return
        }
        var lat1 = parseFloat(obj1.lat);
        var lat2 = parseFloat(obj2.lat);
        var lng1 = parseFloat(obj1.lng);
        var lng2 = parseFloat(obj2.lng);
        if (lng2 > lng1) {
            if (parseFloat(lng2 - lng1) > 180) {
                if (lng1 < 0) {
                    lng1 = parseFloat(180 + 180 + lng1)
                }
            }
        }
        if (lng1 > lng2) {
            if (parseFloat(lng1 - lng2) > 180) {
                if (lng2 < 0) {
                    lng2 = parseFloat(180 + 180 + lng2)
                }
            }
        }
        j = 0;
        t2 = 0;
        if (lat2 == lat1) {
            t = 0;
            h = lng1 - lng2
        } else {
            if (lng2 == lng1) {
                t = Math.PI / 2;
                h = lat1 - lat2
            } else {
                t = Math.atan((lat2 - lat1) / (lng2 - lng1));
                h = (lat2 - lat1) / Math.sin(t)
            }
        }
        if (t2 == 0) {
            t2 = (t + (Math.PI / 5))
        }
        h2 = h / 2;
        lng3 = h2 * Math.cos(t2) + lng1;
        lat3 = h2 * Math.sin(t2) + lat1;
        for (i = 0; i < count + 1; i++) {
            curveCoordinates.push(
                {
                    lng: (lng1 * B1(inc) + lng3 * B2(inc)) + lng2 * B3(inc),
                    lat: (lat1 * B1(inc) + lat3 * B2(inc) + lat2 * B3(inc))
                }
            );
            inc = inc + (1 / count)
        }
        return curveCoordinates
    }
    
    function getCurvePoints(points) {
        var curvePoints = [];
        for (var i = 0; i < points.length - 1; i++) {
            var p = getCurveByTwoPoints(points[i], points[i + 1]);
            if (p && p.length > 0) {
                curvePoints = curvePoints.concat(p)
            }
        }
        return curvePoints
    }
    
    let trackPoints = [{lng:113.281, lat:29.203}, {lng:113.567, lat:29.301}]
    
    let convertPoints = getCurvePoints(trackPoints)
    
    console.log(convertPoints)
    

    最后再给一个微信小程序应用实例

    map.wxml

    // 举个小程序应用的例子
    <map id="map" longitude="113.324520" latitude="23.099994" scale="14" controls="{{controls}}" bindcontroltap="controltap" markers="{{markers}}" bindmarkertap="markertap" polyline="{{polyline}}" bindregionchange="regionchange" show-location style="100vw;height:100vh;"></map>
    

    map.js

    Page({
      data: {
        markers: [{
          iconPath: "/resources/marker.png",
          id: 0,
          latitude: 23.099994,
          longitude: 113.324520,
           50,
          height: 50
        }],
        polyline: [],
        controls: [{
          id: 1,
          iconPath: '/resources/location.png',
          position: {
            left: 0,
            top: 300 - 50,
             50,
            height: 50
          },
          clickable: true
        }]
      },
      onLoad() {
        this.setData({
          polyline:[{
            points: this.getCurvePoints([{ lng: 113.3245211, lat: 23.10229 }, { lng: 113.324520, lat: 23.21229 }]),
            color: "#FF0000DD",
             2
          }]
        })
      },
      regionchange(e) {
        console.log(e.type)
      },
      markertap(e) {
        console.log(e.markerId)
      },
      controltap(e) {
        console.log(e.controlId)
      },
      getCurveByTwoPoints(obj1, obj2) {
        if (!obj1 || !obj2) {
          return null
        }
        var B1 = function (x) {
          return 1 - 2 * x + x * x
        };
        var B2 = function (x) {
          return 2 * x - 2 * x * x
        };
        var B3 = function (x) {
          return x * x
        };
        var curveCoordinates = [];
        var count = 30;
        var isFuture = false;
        var t, h, h2, lat3, lng3, j, t2;
        var LnArray = [];
        var i = 0;
        var inc = 0;
        if (typeof (obj2) == "undefined") {
          if (typeof (curveCoordinates) != "undefined") {
            curveCoordinates = []
          }
          return
        }
        var lat1 = parseFloat(obj1.lat);
        var lat2 = parseFloat(obj2.lat);
        var lng1 = parseFloat(obj1.lng);
        var lng2 = parseFloat(obj2.lng);
        if (lng2 > lng1) {
          if (parseFloat(lng2 - lng1) > 180) {
            if (lng1 < 0) {
              lng1 = parseFloat(180 + 180 + lng1)
            }
          }
        }
        if (lng1 > lng2) {
          if (parseFloat(lng1 - lng2) > 180) {
            if (lng2 < 0) {
              lng2 = parseFloat(180 + 180 + lng2)
            }
          }
        }
        j = 0;
        t2 = 0;
        if (lat2 == lat1) {
          t = 0;
          h = lng1 - lng2
        } else {
          if (lng2 == lng1) {
            t = Math.PI / 2;
            h = lat1 - lat2
          } else {
            t = Math.atan((lat2 - lat1) / (lng2 - lng1));
            h = (lat2 - lat1) / Math.sin(t)
          }
        }
        if (t2 == 0) {
          t2 = (t + (Math.PI / 5))
        }
        h2 = h / 2;
        lng3 = h2 * Math.cos(t2) + lng1;
        lat3 = h2 * Math.sin(t2) + lat1;
        for (i = 0; i < count + 1; i++) {
          curveCoordinates.push(
            {
              longitude: (lng1 * B1(inc) + lng3 * B2(inc)) + lng2 * B3(inc),
              latitude: (lat1 * B1(inc) + lat3 * B2(inc) + lat2 * B3(inc))
            }
          );
          inc = inc + (1 / count)
        }
        return curveCoordinates
      },
      getCurvePoints(points) {
        var curvePoints = [];
        for (var i = 0; i < points.length - 1; i++) {
          var p = this.getCurveByTwoPoints(points[i], points[i + 1]);
          if (p && p.length > 0) {
            curvePoints = curvePoints.concat(p)
          }
        }
        return curvePoints
      }
    })
    

    献上效果图:

    小程序地图曲线)

    首发链接

  • 相关阅读:
    监控里的主码流和子码流是什么意思
    监控硬盘容量计算
    一个能让你了解所有函数调用顺序的Android库
    电工选线
    oracle linux dtrace
    list all of the Oracle 12c hidden undocumented parameters
    Oracle Extended Tracing
    window 驱动开发
    win7 x64 dtrace
    How to Use Dtrace Tracing Ruby Executing
  • 原文地址:https://www.cnblogs.com/wenbinjiang/p/11175956.html
Copyright © 2011-2022 走看看