From 8674efefc7691e1df8226420a22f92b4408557ee Mon Sep 17 00:00:00 2001
From: zguiy <1415466602@qq.com>
Date: Wed, 13 May 2026 17:16:40 +0800
Subject: [PATCH] =?UTF-8?q?=E5=86=B2=E7=AA=81=E8=A7=A3=E5=86=B3?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
index.html | 6 ++--
src/babylonjs/AppDropZone.ts | 62 ++++++++++++++++++++++++------------
src/kernel/Adapter.ts | 6 ++++
3 files changed, 51 insertions(+), 23 deletions(-)
diff --git a/index.html b/index.html
index 9a09715..b4d0558 100644
--- a/index.html
+++ b/index.html
@@ -331,7 +331,7 @@
-
+
@@ -795,8 +795,8 @@
const placementWall = (divisions) => {
- // 先清除旧的放置区域
- kernel.dropZone.clearAll();
+ // 只清除旧的放置区域网格,不清除模型
+ kernel.dropZone.clearZones();
// 生成新的放置区域(使用新的墙面参数化API)
// 调整 baseY 来控制整体高度(正数向上,负数向下)
diff --git a/src/babylonjs/AppDropZone.ts b/src/babylonjs/AppDropZone.ts
index 9d38173..cf85319 100644
--- a/src/babylonjs/AppDropZone.ts
+++ b/src/babylonjs/AppDropZone.ts
@@ -26,6 +26,8 @@ export class AppDropZone {
private zoneModelMap: Map = new Map();
// 墙面 -> 当前分割数
private wallDivisionsMap: Map = new Map();
+ // 墙面 -> 该墙面模型对应的分割数(用于检测分割数变化)
+ private wallModelDivisionsMap: Map = new Map();
constructor(scene: Scene) {
this.scene = scene;
@@ -44,15 +46,8 @@ export class AppDropZone {
* @param config 配置参数
*/
generateDropZones(config: DropZoneConfig): PlacementZoneInfo[] {
- // 检查每个墙面的分割数是否改变,如果改变则卸载该墙面的所有模型
+ // 只记录分割数,不自动卸载模型
config.walls.forEach(wall => {
- const oldDivisions = this.wallDivisionsMap.get(wall.name);
- if (oldDivisions !== undefined && oldDivisions !== wall.divisions) {
- // 分割数改变,卸载该墙面的所有模型
- this.unloadWallModels(wall.name);
- console.log(`墙面 ${wall.name} 分割数从 ${oldDivisions} 改为 ${wall.divisions},已卸载所有模型`);
- }
- // 更新分割数记录
this.wallDivisionsMap.set(wall.name, wall.divisions);
});
@@ -77,14 +72,17 @@ export class AppDropZone {
// 卸载模型并清除映射
modelsToUnload.forEach(modelId => {
this.appModel!.removeByName(modelId);
- // 清除该模型的映射
- this.zoneModelMap.forEach((value, key) => {
- if (value === modelId) {
- this.zoneModelMap.delete(key);
- }
- });
});
+ // 清除该墙面的所有映射
+ const keysToDelete: string[] = [];
+ this.zoneModelMap.forEach((modelId, zoneKey) => {
+ if (zoneKey.startsWith(`${wallName}[`)) {
+ keysToDelete.push(zoneKey);
+ }
+ });
+ keysToDelete.forEach(key => this.zoneModelMap.delete(key));
+
if (modelsToUnload.length > 0) {
console.log(`已卸载墙面 ${wallName} 的 ${modelsToUnload.length} 个模型`);
}
@@ -95,17 +93,33 @@ export class AppDropZone {
*/
recordModelPlacement(wallName: string, index: number, modelId: string): void {
const zoneKey = `${wallName}[${index}]`;
+ const currentDivisions = this.wallDivisionsMap.get(wallName);
+ const modelDivisions = this.wallModelDivisionsMap.get(wallName);
- // 检查该区域是否已有模型
- const existingModelId = this.zoneModelMap.get(zoneKey);
- if (existingModelId && this.appModel) {
- // 卸载旧模型
- console.log(`区域 ${zoneKey} 已有模型 ${existingModelId},将替换为 ${modelId}`);
- this.appModel.removeByName(existingModelId);
+ // 检查分割数是否改变
+ if (modelDivisions !== undefined && currentDivisions !== undefined && modelDivisions !== currentDivisions) {
+ // 分割数改变了,清空该墙面的所有旧模型
+ console.log(`墙面 ${wallName} 分割数从 ${modelDivisions} 改为 ${currentDivisions},清空旧模型`);
+ this.unloadWallModels(wallName);
+ // 更新该墙面模型对应的分割数
+ this.wallModelDivisionsMap.set(wallName, currentDivisions);
+ } else {
+ // 分割数没变,检查该区域是否已有模型(替换逻辑)
+ const existingModelId = this.zoneModelMap.get(zoneKey);
+ if (existingModelId && this.appModel) {
+ console.log(`区域 ${zoneKey} 已有模型 ${existingModelId},将替换为 ${modelId}`);
+ this.appModel.removeByName(existingModelId);
+ }
+ }
+
+ // 如果是该墙面的第一个模型,记录分割数
+ if (modelDivisions === undefined && currentDivisions !== undefined) {
+ this.wallModelDivisionsMap.set(wallName, currentDivisions);
}
// 记录新模型
this.zoneModelMap.set(zoneKey, modelId);
+ console.log(`已记录模型 ${modelId} 到区域 ${zoneKey}`);
}
/**
@@ -150,6 +164,13 @@ export class AppDropZone {
this.placementWall.hide();
}
+ /**
+ * 清除所有放置区域(只清除网格,不清除模型)
+ */
+ clearZones(): void {
+ this.placementWall.clearAll();
+ }
+
/**
* 清除所有放置区域
*/
@@ -164,6 +185,7 @@ export class AppDropZone {
// 清除映射
this.zoneModelMap.clear();
this.wallDivisionsMap.clear();
+ this.wallModelDivisionsMap.clear();
this.placementWall.clearAll();
}
diff --git a/src/kernel/Adapter.ts b/src/kernel/Adapter.ts
index ef7c03d..0863c89 100644
--- a/src/kernel/Adapter.ts
+++ b/src/kernel/Adapter.ts
@@ -309,6 +309,12 @@ export class KernelAdapter {
zone.mesh.isVisible = false;
});
},
+ /**
+ * 清除所有放置区域(只清除网格,不清除模型)
+ */
+ clearZones: (): void => {
+ this.mainApp.appDropZone.clearZones();
+ },
/**
* 清除所有放置区域
*/