feat: add native road marking semantics

This commit is contained in:
2026-08-17 16:08:56 +08:00
parent bd38aa55d3
commit 9bb97d4507
13 changed files with 209 additions and 17 deletions

View File

@@ -43,7 +43,25 @@ const centerLineOverride = validateOverrides({ schema: "native-road-overrides/v1
const styledCenterLines = compileGeometry(model, centerLineOverride).centerLines.features.filter((feature) => feature.properties.segment_id === target.segmentId);
assert.ok(styledCenterLines.length > 0);
assert.ok(styledCenterLines.every((feature) => feature.properties.color === "white" && feature.properties.pattern === "solid" && feature.properties.effective_style === "white-solid" && feature.properties.dash_gap_m === 0));
const doubleCenterOverride = validateOverrides({ schema: "native-road-overrides/v1", overrides: [{ id: "center-double-yellow", kind: "center-line-style", segmentId: target.segmentId, color: "yellow", pattern: "solid", double: true }] }, model);
const doubleCenterLines = compileGeometry(model, doubleCenterOverride).centerLines.features.filter((feature) => feature.properties.segment_id === target.segmentId);
assert.equal(doubleCenterLines.length, styledCenterLines.length * 2);
assert.ok(doubleCenterLines.every((feature) => feature.properties.double === true && feature.properties.effective_style === "double-yellow-solid"));
assert.equal(new Set(doubleCenterLines.map((feature) => feature.properties.dash_index)).size, styledCenterLines.length);
for (const dashIndex of new Set(doubleCenterLines.map((feature) => feature.properties.dash_index))) {
const pair = doubleCenterLines.filter((feature) => feature.properties.dash_index === dashIndex);
const centers = pair.map((feature) => feature.geometry.coordinates[0].slice(0, 4).reduce((sum, point) => [sum[0] + point[0] / 4, sum[1] + point[1] / 4], [0, 0]));
assert.ok(Math.hypot((centers[0][0] - centers[1][0]) * 96400, (centers[0][1] - centers[1][1]) * 111320) > .25);
}
assert.throws(() => validateOverrides({ schema: "native-road-overrides/v1", overrides: [{ id: "bad-double-center", kind: "center-line-style", segmentId: target.segmentId, color: "white", pattern: "solid", double: true }] }, model), /Invalid center line style override/);
assert.throws(() => validateOverrides({ schema: "native-road-overrides/v1", overrides: [{ id: "bad-center", kind: "center-line-style", segmentId: target.segmentId, color: "blue", pattern: "solid" }] }, model), /Invalid center line style override/);
const edgeLine = geometry.edgeLines.features[0];
assert.ok(edgeLine && edgeLine.properties.effective_style === "white-solid");
const edgeOverride = validateOverrides({ schema: "native-road-overrides/v1", overrides: [{ id: "edge-yellow-dashed", kind: "edge-line-style", roadId: edgeLine.properties.road_id, side: edgeLine.properties.side, color: "yellow", pattern: "dashed" }] }, model);
const styledEdgeLines = compileGeometry(model, edgeOverride).edgeLines.features.filter((feature) => feature.properties.road_id === edgeLine.properties.road_id && feature.properties.side === edgeLine.properties.side);
assert.ok(styledEdgeLines.length > 1 && styledEdgeLines.every((feature) => feature.properties.effective_style === "yellow-dashed"));
assert.throws(() => validateOverrides({ schema: "native-road-overrides/v1", overrides: [{ id: "bad-edge", kind: "edge-line-style", roadId: edgeLine.properties.road_id, side: "middle", color: "yellow", pattern: "solid" }] }, model), /Invalid edge line style override/);
assert.throws(() => validateOverrides({ schema: "native-road-overrides/v1", overrides: [{ id: "missing-edge-road", kind: "edge-line-style", roadId: "road:way/missing:forward", side: "left", color: "yellow", pattern: "solid" }] }, model), /Invalid edge line style override/);
assert.ok(geometry.directionArrows.features.every((feature) => feature.geometry.type === "Polygon" && feature.properties.provenance === "native-road-direction-arrow/v1" && feature.properties.placement_interval_meters === 32));
assert.ok(geometry.turnArrows.features.every((feature) => feature.geometry.type === "Polygon" && feature.properties.provenance === "native-road-turn-arrow/v1"));
assert.ok(geometry.connectors.features.length > 0);