关于使用truf.js获取多边形中心线

245 阅读2分钟

前言

最近项目上需要做水路演变动画,我说用轨迹播放不就完事了。产品经理却说,我要的面不是线!!!我心想线段宽点不就是面了吗(无语.jpg)。

在我不懈的努力(能摸鱼就摸鱼.jpg)下,最终将需求变为下层是现存水路,上层添加线段并采取纹理发光的方式来表现动画。

实现思路

  1. 使用truf.js的truf.bbox方法获取多边形边界。
  2. 根据需求如需生成上下方向的中心线,则取上边界坐标,组成分割线。
  3. 使用truf.js的truf.polygonToLine方法将面转化为线。
  4. 使用truf.js的turf.lineIntersect方法获取线段交点。
  5. 使用truf.js的turf.midpoint方法获取两点间的中点。
  6. 将中点连成线。

具体实现

1、获取多边形坐标边界,并确认分割方向

// 将坐标转换为
const polygon = turf.polygon([
    [-5, 52],  
    [-4, 56],  
    [-2, 51],  
    [-7, 54],  
    [-5, 52]
]);
// 获取边界
const bbox = turf.bbox(polyons);
// 从上到下分割
const startLine = [
    [bbox[0], bbox[3]],
    [bbox[2], bbox[3]],
];
  1. 确认分割颗粒度
// 切割线段纬度差值
const Diff = bbox[3] - bbox[1];
// 将维度差值分为100份
const rang = Diff / 100;
  1. 进行循环切分,并生成中线
// centerLine 放置生成好的中点 i 记录循环次数
let centerLine = [],i = 0;
do {
    const LINE = turf.lineString([
      [bbox[0], bbox[3] - rang * i],
      [bbox[2], bbox[3] - rang * i],
    ], { name: "line" })
    i++;
    // 将面转化为线段并获取两线段交点
    const splitted = turf.lineIntersect(
      LINE.toGeoJSON(),
      turf.polygonToLine(polygon)
    );
    // 仅获取不多于3三个交点的数据
    if (splitted.features.length > 0 && splitted.features.length <= 2) {
      if (splitted.features.length % 2 !== 0) {
        centerLine.push(splitted.features[0].geometry.coordinates);
      } else {
        // 获取交点
        const intersect = splitted.features;
        // 计算交点的中点
        const midpoints = turf.midpoint(
          intersect[0].geometry.coordinates,
          intersect[1].geometry.coordinates
        );
        centerLine.push(midpoints.geometry.coordinates);
      }

      // 将中点转换为线串
      // const midline = turf.lineString(midpoints.coordinates);
      // maptalks.GeoJSON.toGeometry(midline).addTo(layerLine);
    } else if (splitted.features.length > 0 && splitted.features.length > 2 ) {
      // 两个以上交点处理
    }else if (i > 1 && splitted.features.length == 0) {
      // 无交点处理
    }
} while (bbox[3] - rang * i >= bbox[1]);
// 生成中心线
const cLINE = turf.lineString(centerLine, { name: "centerline" })

存在问题

目前还未解决关于两个以上的交点处理方法,仅仅有一个大致思路:

  1. 每两个相邻交点组成一段线。
  2. 获取上一次生成中点与线段之间的夹角与中心线角度进行对比,获取合适的线段计算中点。
  3. 怎么判断“合适”。

最后

jym如有其他的思路或者更好的解决方法,欢迎留言探讨。

欢迎留言加关注。

祝jym: 彩票发发发; 钓鱼中中中; 头发长长长;