diff --git a/starpilot/system/the_galaxy/assets/components/tools/v_asm.js b/starpilot/system/the_galaxy/assets/components/tools/v_asm.js index 9c1200c5d..3d18d5f07 100644 --- a/starpilot/system/the_galaxy/assets/components/tools/v_asm.js +++ b/starpilot/system/the_galaxy/assets/components/tools/v_asm.js @@ -2,6 +2,18 @@ import { html, reactive } from "/assets/vendor/arrow-core.js"; const CANVAS_W = 640; const CANVAS_H = 480; +const VEHICLE_SIDE_LABELS = { + left: { + canvas: "LEFT SIDE OF VEHICLE - LEFT HERE", + button: "Annotate Left Side of Vehicle - Left Here", + active: "Annotating Left Side of Vehicle - Left Here...", + }, + right: { + canvas: "RIGHT SIDE OF VEHICLE - RIGHT HERE", + button: "Annotate Right Side of Vehicle - Right Here", + active: "Annotating Right Side of Vehicle - Right Here...", + }, +}; let pollInterval = null; let pollHasBeenActive = false; let initialLoadTriggered = false; @@ -55,7 +67,20 @@ function redraw() { const img = _loadedImage; if (img) { canvas._img = img; + ctx.save(); + ctx.translate(canvas.width, 0); + ctx.scale(-1, 1); ctx.drawImage(img, 0, 0, canvas.width, canvas.height); + ctx.restore(); + + ctx.font = "bold 14px sans-serif"; + ctx.textAlign = "center"; + ctx.fillStyle = "rgba(0, 0, 0, 0.65)"; + ctx.fillRect(0, 0, canvas.width / 2, 34); + ctx.fillRect(canvas.width / 2, 0, canvas.width / 2, 34); + ctx.fillStyle = "#fff"; + ctx.fillText(VEHICLE_SIDE_LABELS.left.canvas, canvas.width / 4, 22); + ctx.fillText(VEHICLE_SIDE_LABELS.right.canvas, canvas.width * 3 / 4, 22); } else { ctx.fillStyle = "#222"; ctx.fillRect(0, 0, canvas.width, canvas.height); @@ -67,8 +92,8 @@ function redraw() { } const sides = [ - { key: "left", points: state.leftPoints, fillColor: "rgba(13, 110, 253, 0.25)", borderColor: "#0d6efd", label: "LEFT OF IMAGE" }, - { key: "right", points: state.rightPoints, fillColor: "rgba(253, 126, 20, 0.25)", borderColor: "#fd7e14", label: "RIGHT OF IMAGE" }, + { key: "left", points: state.leftPoints, fillColor: "rgba(13, 110, 253, 0.25)", borderColor: "#0d6efd", label: VEHICLE_SIDE_LABELS.left.canvas }, + { key: "right", points: state.rightPoints, fillColor: "rgba(253, 126, 20, 0.25)", borderColor: "#fd7e14", label: VEHICLE_SIDE_LABELS.right.canvas }, ]; for (const side of sides) { @@ -280,8 +305,11 @@ async function saveConfig() { const cw = canvas ? canvas.width : nativeW; const ch = canvas ? canvas.height : nativeH; + // The preview is mirrored for vehicle-side clarity; the daemon still stores + // raw camera coordinates, so un-mirror X when writing back. The LEFT side of + // the vehicle (raw image RIGHT) is saved as poly_right and vice versa. function scalePoints(pts) { - return pts.map(([x, y]) => [Math.round(x * nativeW / cw), Math.round(y * nativeH / ch)]); + return pts.map(([x, y]) => [Math.round((cw - x) * nativeW / cw), Math.round(y * nativeH / ch)]); } const config = { @@ -289,15 +317,15 @@ async function saveConfig() { height: nativeH, }; if (state.leftPoints.length >= 3) { - config.poly_left = scalePoints(state.leftPoints); - } else { - config.poly_left = []; - } - if (state.rightPoints.length >= 3) { - config.poly_right = scalePoints(state.rightPoints); + config.poly_right = scalePoints(state.leftPoints); } else { config.poly_right = []; } + if (state.rightPoints.length >= 3) { + config.poly_left = scalePoints(state.rightPoints); + } else { + config.poly_left = []; + } state.loading = true; state.error = ""; @@ -350,11 +378,18 @@ function applyConfigToCanvas() { const scaleX = cw / nativeW; const scaleY = ch / nativeH; - const left = Array.isArray(config.poly_left) && config.poly_left.length >= 3 - ? config.poly_left.map(([x, y]) => [Math.round(x * scaleX), Math.round(y * scaleY)]) + function toCanvas(pts) { + return pts.map(([x, y]) => [Math.round(cw - x * scaleX), Math.round(y * scaleY)]); + } + + // poly_left is raw image-LEFT (the vehicle's right side) and poly_right is + // raw image-RIGHT (the vehicle's left side). Mirror X so each polygon lands + // on the correct vehicle side of the flipped preview. + const left = Array.isArray(config.poly_right) && config.poly_right.length >= 3 + ? toCanvas(config.poly_right) : []; - const right = Array.isArray(config.poly_right) && config.poly_right.length >= 3 - ? config.poly_right.map(([x, y]) => [Math.round(x * scaleX), Math.round(y * scaleY)]) + const right = Array.isArray(config.poly_left) && config.poly_left.length >= 3 + ? toCanvas(config.poly_left) : []; state.leftPoints = left; @@ -419,7 +454,7 @@ export function VASMAnnotations() {