circle-arc
本文回答:圆 / 椭圆 / 圆弧 / 椭圆弧 / 贝塞尔曲线 ——
vjmap.CircleFill/EllipseFill/ 路径辅助函数。
一、分两类
| 类型 | 表现 | API |
|---|---|---|
| 填充 | 有内部填色的实心几何 | vjmap.CircleFill / vjmap.EllipseFill |
| 路径 | 只有边线,没有填色 | vjmap.Polyline + 辅助函数生成 coordinate |
二、圆填充 CircleFill
const mapBounds = map.getGeoBounds(0.2);
const circle = new vjmap.CircleFill({
center: mapBounds.center(), // CAD 坐标
radius: mapBounds.width() / 4, // CAD 单位
fillColor: "yellow",
fillOpacity: 0.8,
fillOutlineColor: "#f00"
});
circle.addTo(map);
参数:
| 参数 | 说明 |
|---|---|
center |
圆心坐标(CAD) |
radius |
半径(CAD 单位) |
startAngle |
起始角(度)—— 弧时必填 |
endAngle |
终止角(度)—— 弧时必填 |
fillColor / fillOpacity / fillOutlineColor |
同 Polygon |
三、圆弧填充
new vjmap.CircleFill({
center, radius,
startAngle: 120, // 从 120° 逆时针扫到 60°+360°
endAngle: 60, // → 300° 的大扇形;要 60°~120° 小扇形写 startAngle: 60, endAngle: 120
fillColor: "yellow"
}).addTo(map);
四、椭圆填充 EllipseFill
new vjmap.EllipseFill({
center,
majorAxisRadius,
minorAxisRadius,
fillColor: "yellow",
fillOpacity: 0.6
}).addTo(map);
椭圆弧:加 startAngle + endAngle。
五、圆 / 椭圆路径(只有线)
vjmap 提供辅助函数把圆/椭圆采样成坐标串,再用 Polyline 画:
// 圆路径
const circlePath = vjmap.getCirclePolygonCoordinates(
mapExtent.center(), // 圆心
mapExtent.width() / 10, // 半径
120, // 采样段数
0, // 起始角
360, // 终止角
false // 弧时是否包含圆心(true → 扇形 wedge)
);
new vjmap.Polyline({
data: map.toLngLat(circlePath),
lineColor: "#FFA0FD",
lineWidth: 3
}).addTo(map);
椭圆路径:
const ellipsePath = vjmap.getEllipsePolygonCoordinates(
mapExtent.center(),
majorAxisRadius,
minorAxisRadius,
360, // 采样段数
0, 360, // 起始 / 终止角
false
);
六、贝塞尔曲线
vjmap 提供 polylineToBezierCurve + bezierCurveToPolyline 两步:
// 1) 把控制点转 B 样条参数
const curvePoints = [
mapBounds.min.toArray(),
mapBounds.center().toArray(),
vjmap.geoPoint([mapBounds.max.x, mapBounds.min.y]).toArray(),
mapBounds.max.toArray()
];
const c = vjmap.polylineToBezierCurve(curvePoints);
// 2) 离散成线
const curvePath = vjmap.bezierCurveToPolyline(c);
// 3) 用 Polyline 或 Polygon 渲染
new vjmap.Polyline({
data: map.toLngLat(curvePath),
lineColor: "#FFA0FD",
lineWidth: 3
}).addTo(map);
做成闭合曲线填充:
const c = vjmap.polylineToBezierCurve(pts, true); // close 参数闭合曲线
const curvePath = vjmap.bezierCurveToPolyline(c);
new vjmap.Polygon({
data: map.toLngLat(curvePath),
fillColor: "yellow",
fillOpacity: 0.6
}).addTo(map);
七、圆/椭圆参数表
| 函数 | 参数顺序 |
|---|---|
getCirclePolygonCoordinates |
center, radius, points?, startAngle?, endAngle?, includeCenterWhenArc? |
getEllipsePolygonCoordinates |
center, majorR, minorR, points?, startAngle?, endAngle?, includeCenterWhenArc? |
polylineToBezierCurve |
polyline[], close?, offsetA?, offsetB? |
bezierCurveToPolyline |
bezierCurve, precision?, recursiveCount? |
includeCenterWhenArc=true时弧的末点被替换/追加为圆心(扇形闭合用法);⚠️ 全圆(不传起止角)的首尾点并不相同(不闭环)——要闭合环请自行补首点。另注意顶层vjmap.isPoint(v):只认{x,y}/{x,y,z}对象——[x,y]数组、{lng,lat}都返回 false,且isPoint(null)直接抛 TypeError(无 null 防护)。
八、修改几何
CircleFill / EllipseFill 内部会生成 GeoJSON polygon;要改半径 → 重新 setData 或删除重建。
⚠️ 勿用 setCenter / setRadius / setMajorAxisRadius / setMinorAxisRadius / setStartAngle / setEndAngle / setPoints 改几何:CircleFill / EllipseFill 的内部 updateData 把 (startAngle, endAngle, points) 传进了 (points, startAngle, endAngle) 的位置,自定义了 points 或起止角时几何错乱(如 points: 64 的整圆变成 64° 扇形);CircleEdge 的 setter 引用了未导入的函数,直接抛 ReferenceError。改几何请删除重建或 setData。
circle.remove();
circle = new vjmap.CircleFill({ center, radius: newR, ... }); // addTo 无返回值,不能链尾赋值
circle.addTo(map);
或直接用辅助函数 + Polygon:
const coords = vjmap.getCirclePolygonCoordinates(center, radius, 64, 0, 360, true);
polygon.setData({ type: "Feature", geometry: { type: "Polygon", coordinates: [map.toLngLat(coords)] }});
九、常见坑
- 圆看起来椭圆了 → 地图倾斜或高纬度投影失真;用
turf.circle+ LngLat 可避免。 - 弧方向搞反 →
startAngle/endAngle按数学正向(逆时针为正);测试时交换即可。 - 贝塞尔离散点太少 →
bezierCurveToPolyline(c, precision)第二参传精度数值(如100),或增采样控制点。 - 椭圆旋转角 → 目前
EllipseFill无 rotation;要斜椭圆就手算 + Polygon。