feat(map): 滚轮缩放以光标为焦点并调整保存文案
This commit is contained in:
@@ -557,7 +557,7 @@ function markCurrentMapUploaded(payload: Partial<MapRecord>) {
|
|||||||
currentConfig.value.lastSyncedAt = nowString();
|
currentConfig.value.lastSyncedAt = nowString();
|
||||||
}
|
}
|
||||||
|
|
||||||
// 调用小车地图地址接口,在保存下发时单独保存 PGM 和 YAML 文件 URL
|
// 调用小车地图地址接口,在保存时单独保存 PGM 和 YAML 文件 URL
|
||||||
async function saveCurrentMapUrls() {
|
async function saveCurrentMapUrls() {
|
||||||
if (!currentConfiguredDevice.value || !currentConfig.value) {
|
if (!currentConfiguredDevice.value || !currentConfig.value) {
|
||||||
return;
|
return;
|
||||||
@@ -717,7 +717,7 @@ async function handleMapImageFileChange(event: Event) {
|
|||||||
|
|
||||||
rosMapMeta.imageUrl = uploadedUrl;
|
rosMapMeta.imageUrl = uploadedUrl;
|
||||||
markCurrentMapUploaded({ imageUrl: uploadedUrl, name: file.name });
|
markCurrentMapUploaded({ imageUrl: uploadedUrl, name: file.name });
|
||||||
mapUploadMessage.value = "地图 PGM 上传成功,保存下发后生效";
|
mapUploadMessage.value = "地图 PGM 上传成功,保存后生效";
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error(error);
|
console.error(error);
|
||||||
mapUploadMessage.value = "地图 PGM 解析或上传失败,请确认文件为 P5 格式";
|
mapUploadMessage.value = "地图 PGM 解析或上传失败,请确认文件为 P5 格式";
|
||||||
@@ -769,7 +769,7 @@ async function handleMapConfigFileChange(event: Event) {
|
|||||||
|
|
||||||
rosMapMeta.configUrl = uploadedUrl;
|
rosMapMeta.configUrl = uploadedUrl;
|
||||||
markCurrentMapUploaded({ configUrl: uploadedUrl });
|
markCurrentMapUploaded({ configUrl: uploadedUrl });
|
||||||
mapUploadMessage.value = "地图配置上传成功,保存下发后生效";
|
mapUploadMessage.value = "地图配置上传成功,保存后生效";
|
||||||
scheduleMapCanvasRender();
|
scheduleMapCanvasRender();
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error(error);
|
console.error(error);
|
||||||
@@ -1507,9 +1507,26 @@ function clampMapZoom(value: number) {
|
|||||||
return Math.min(maxMapZoom, Math.max(minMapZoom, Number(value.toFixed(2))));
|
return Math.min(maxMapZoom, Math.max(minMapZoom, Number(value.toFixed(2))));
|
||||||
}
|
}
|
||||||
|
|
||||||
// 设置地图缩放比例并触发画布重绘
|
// 设置地图缩放比例并触发画布重绘;传入 focusPoint(画布内坐标)时缩放保持该焦点下的地图点不动
|
||||||
function setMapZoom(value: number) {
|
function setMapZoom(value: number, focusPoint?: { x: number; y: number }) {
|
||||||
mapZoom.value = clampMapZoom(value);
|
const nextZoom = clampMapZoom(value);
|
||||||
|
|
||||||
|
if (focusPoint && nextZoom !== mapZoom.value) {
|
||||||
|
const rect = getMapStageRect();
|
||||||
|
|
||||||
|
if (rect && rect.width > 0 && rect.height > 0) {
|
||||||
|
const frame = getRosMapFrame(rect);
|
||||||
|
const pointerRatioX = (focusPoint.x - frame.left) / frame.width;
|
||||||
|
const pointerRatioY = (focusPoint.y - frame.top) / frame.height;
|
||||||
|
const nextWidth = frame.width * (nextZoom / mapZoom.value);
|
||||||
|
const nextHeight = frame.height * (nextZoom / mapZoom.value);
|
||||||
|
|
||||||
|
mapPan.x += (frame.width - nextWidth) * (pointerRatioX - 0.5);
|
||||||
|
mapPan.y += (frame.height - nextHeight) * (pointerRatioY - 0.5);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
mapZoom.value = nextZoom;
|
||||||
scheduleMapCanvasRender();
|
scheduleMapCanvasRender();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1531,10 +1548,12 @@ function resetMapView() {
|
|||||||
focusMapOnOrigin();
|
focusMapOnOrigin();
|
||||||
}
|
}
|
||||||
|
|
||||||
// 处理鼠标滚轮缩放地图
|
// 处理鼠标滚轮缩放地图,以光标位置为缩放中心
|
||||||
function handleMapWheel(event: WheelEvent) {
|
function handleMapWheel(event: WheelEvent) {
|
||||||
|
const rect = getMapStageRect();
|
||||||
const zoomFactor = event.deltaY > 0 ? 1 / 1.1 : 1.1;
|
const zoomFactor = event.deltaY > 0 ? 1 / 1.1 : 1.1;
|
||||||
setMapZoom(mapZoom.value * zoomFactor);
|
const focusPoint = rect ? { x: event.clientX - rect.left, y: event.clientY - rect.top } : undefined;
|
||||||
|
setMapZoom(mapZoom.value * zoomFactor, focusPoint);
|
||||||
}
|
}
|
||||||
|
|
||||||
// 根据地图宽高比计算默认缩放:常规比例地图保持完整显示,宽扁/高瘦地图放大让短边占满画布
|
// 根据地图宽高比计算默认缩放:常规比例地图保持完整显示,宽扁/高瘦地图放大让短边占满画布
|
||||||
@@ -2820,7 +2839,7 @@ watch(
|
|||||||
</button>
|
</button>
|
||||||
<button class="page-action-btn primary" :disabled="saveProgressVisible" type="button"
|
<button class="page-action-btn primary" :disabled="saveProgressVisible" type="button"
|
||||||
@click="saveConfigDialog">
|
@click="saveConfigDialog">
|
||||||
{{ saveProgressVisible ? "保存中..." : "保存下发" }}
|
{{ saveProgressVisible ? "保存中..." : "保存" }}
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@@ -3047,7 +3066,7 @@ watch(
|
|||||||
|
|
||||||
<div v-if="saveProgressVisible" class="save-progress-mask">
|
<div v-if="saveProgressVisible" class="save-progress-mask">
|
||||||
<div class="save-progress-card">
|
<div class="save-progress-card">
|
||||||
<div class="save-progress-title">保存下发</div>
|
<div class="save-progress-title">保存</div>
|
||||||
<div class="save-progress-text">{{ saveProgressMessage }}</div>
|
<div class="save-progress-text">{{ saveProgressMessage }}</div>
|
||||||
<div class="save-progress-track">
|
<div class="save-progress-track">
|
||||||
<div class="save-progress-fill" :style="{ width: `${saveProgressValue}%` }"></div>
|
<div class="save-progress-fill" :style="{ width: `${saveProgressValue}%` }"></div>
|
||||||
|
|||||||
Reference in New Issue
Block a user