fix: 修复多个已知问题
This commit is contained in:
@@ -1,3 +1,4 @@
|
||||
import { findObjectById } from "../utils/helper";
|
||||
import { Command } from "./Command";
|
||||
import { fabric } from "fabric-with-all";
|
||||
|
||||
@@ -129,14 +130,13 @@ export class UpdateBackgroundCommand extends Command {
|
||||
});
|
||||
this.canvas = options.canvas;
|
||||
this.layers = options.layers;
|
||||
this.backgroundColor = options.backgroundColor;
|
||||
this.backgroundColorValue = options.backgroundColorValue; // 使用.value获取实际值
|
||||
this.backgroundColor = options.backgroundColor; //
|
||||
this.historyManager = options.historyManager;
|
||||
|
||||
// 查找背景图层
|
||||
this.bgLayer = this.layers.value.find((layer) => layer.isBackground);
|
||||
this.oldBackgroundColor = this.bgLayer
|
||||
? this.bgLayer.backgroundColor
|
||||
: "#ffffff";
|
||||
this.oldBackgroundColor = this.bgLayer.backgroundColor;
|
||||
}
|
||||
|
||||
execute() {
|
||||
@@ -150,10 +150,14 @@ export class UpdateBackgroundCommand extends Command {
|
||||
|
||||
// 更新背景对象属性
|
||||
if (this.bgLayer.fabricObject) {
|
||||
this.bgLayer.fabricObject.set("fill", this.backgroundColor);
|
||||
const { object } = findObjectById(
|
||||
this.canvas,
|
||||
this.bgLayer.fabricObject.id
|
||||
);
|
||||
object.set("fill", this.backgroundColor);
|
||||
this.canvas.renderAll();
|
||||
}
|
||||
|
||||
this.backgroundColorValue.value = this.backgroundColor; // 设置背景颜色
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -167,10 +171,14 @@ export class UpdateBackgroundCommand extends Command {
|
||||
|
||||
// 恢复背景对象属性
|
||||
if (this.bgLayer.fabricObject) {
|
||||
this.bgLayer.fabricObject.set("fill", this.oldBackgroundColor);
|
||||
const { object } = findObjectById(
|
||||
this.canvas,
|
||||
this.bgLayer.fabricObject.id
|
||||
);
|
||||
object.set("fill", this.oldBackgroundColor);
|
||||
this.canvas.renderAll();
|
||||
}
|
||||
|
||||
this.backgroundColorValue.value = this.oldBackgroundColor; // 恢复背景颜色
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,3 +1,8 @@
|
||||
import {
|
||||
createLayer,
|
||||
findInChildLayers,
|
||||
LayerType,
|
||||
} from "../utils/layerHelper.js";
|
||||
import { createRasterizedImage } from "../utils/selectionToImage.js";
|
||||
import { CompositeCommand } from "./Command.js";
|
||||
import { CreateImageLayerCommand } from "./LayerCommands.js";
|
||||
@@ -27,6 +32,15 @@ export class LassoCutoutCommand extends CompositeCommand {
|
||||
// 高清截图选项
|
||||
this.highResolutionEnabled = options.highResolutionEnabled !== false; // 默认启用
|
||||
this.baseResolutionScale = options.baseResolutionScale || 2; // 基础分辨率倍数
|
||||
|
||||
this.groupId = options.groupId || `cutout-group-${Date.now()}`;
|
||||
this.groupName = options.groupName || `选区组`;
|
||||
this.groupLayer = null; // 新增:保存组图层的引用
|
||||
this.originalLayersLength = 0; // 新增:保存原始图层数量
|
||||
|
||||
// 序列化保存选区对象,用于重做时恢复
|
||||
this.serializedSelectionObject = null;
|
||||
this._serializeSelectionObject();
|
||||
}
|
||||
|
||||
async execute() {
|
||||
@@ -38,8 +52,11 @@ export class LassoCutoutCommand extends CompositeCommand {
|
||||
try {
|
||||
this.executedCommands = [];
|
||||
|
||||
// 保存原始图层数量,用于撤销时的验证
|
||||
this.originalLayersLength = this.layerManager.layers.value.length;
|
||||
|
||||
// 获取选区
|
||||
const selectionObject = this.selectionManager.getSelectionObject();
|
||||
const selectionObject = await this._getSelectionObject();
|
||||
if (!selectionObject) {
|
||||
console.error("无法执行套索抠图:当前没有选区");
|
||||
return false;
|
||||
@@ -112,10 +129,47 @@ export class LassoCutoutCommand extends CompositeCommand {
|
||||
await clearSelectionCmd.execute();
|
||||
this.executedCommands.push(clearSelectionCmd);
|
||||
|
||||
const topLayerIndex = this.layerManager.layers.value.findIndex(
|
||||
(layer) => layer.id === this.newLayerId
|
||||
);
|
||||
|
||||
const selectLayer = this.layerManager.layers.value[topLayerIndex];
|
||||
|
||||
// 创建新的组图层
|
||||
this.groupLayer = createLayer({
|
||||
id: this.groupId,
|
||||
name: this.groupName || `选区组`,
|
||||
type: LayerType.GROUP,
|
||||
visible: true,
|
||||
locked: false,
|
||||
opacity: 1.0,
|
||||
fabricObjects: [],
|
||||
children: [],
|
||||
});
|
||||
|
||||
this.fabricImage.set({
|
||||
selectable: true,
|
||||
evented: true,
|
||||
});
|
||||
|
||||
selectLayer.parentId = this.groupId; // 设置新图层的parentId为组图层ID
|
||||
selectLayer.fabricObjects = [
|
||||
this.fabricImage.toObject("id", "layerId", "layerName", "parentId"),
|
||||
];
|
||||
this.groupLayer.children.push(selectLayer);
|
||||
// 插入新组图层
|
||||
this.layerManager.layers.value.splice(topLayerIndex, 1, this.groupLayer);
|
||||
|
||||
this.layerManager.updateLayersObjectsInteractivity();
|
||||
this.canvas.discardActiveObject();
|
||||
this.canvas.setActiveObject(this.fabricImage);
|
||||
this.canvas.renderAll();
|
||||
console.log(`套索抠图完成,新图层ID: ${this.newLayerId}`);
|
||||
return {
|
||||
newLayerId: this.newLayerId,
|
||||
cutoutImageUrl: this.cutoutImageUrl,
|
||||
guroupId: this.groupId,
|
||||
groupName: this.groupName,
|
||||
};
|
||||
} catch (error) {
|
||||
console.error("套索抠图过程中出错:", error);
|
||||
@@ -129,32 +183,127 @@ export class LassoCutoutCommand extends CompositeCommand {
|
||||
}
|
||||
}
|
||||
|
||||
// 清理组图层(如果已创建)
|
||||
if (this.groupLayer && this.groupId) {
|
||||
try {
|
||||
const groupIndex = this.layerManager.layers.value.findIndex(
|
||||
(layer) => layer.id === this.groupId
|
||||
);
|
||||
if (groupIndex !== -1) {
|
||||
this.layerManager.layers.value.splice(groupIndex, 1);
|
||||
console.log(`清理了异常创建的组图层: ${this.groupId}`);
|
||||
}
|
||||
this.groupLayer = null;
|
||||
} catch (cleanupError) {
|
||||
console.warn("清理组图层失败:", cleanupError);
|
||||
}
|
||||
}
|
||||
|
||||
// 尝试回滚已执行的命令
|
||||
if (this.executedCommands.length > 0) {
|
||||
try {
|
||||
for (let i = this.executedCommands.length - 1; i >= 0; i--) {
|
||||
const command = this.executedCommands[i];
|
||||
if (command && typeof command.undo === "function") {
|
||||
await command.undo();
|
||||
}
|
||||
}
|
||||
this.executedCommands = [];
|
||||
} catch (rollbackError) {
|
||||
console.warn("回滚已执行命令失败:", rollbackError);
|
||||
}
|
||||
}
|
||||
|
||||
throw error;
|
||||
}
|
||||
}
|
||||
|
||||
async undo() {
|
||||
try {
|
||||
// 逆序撤销所有已执行的命令
|
||||
for (let i = this.executedCommands.length - 1; i >= 0; i--) {
|
||||
const command = this.executedCommands[i];
|
||||
if (command && typeof command.undo === "function") {
|
||||
await command.undo();
|
||||
console.log(`↩️ 开始撤销套索抠图操作`);
|
||||
|
||||
// 1. 首先移除组图层(如果存在)
|
||||
if (this.groupId) {
|
||||
const groupIndex = this.layerManager.layers.value.findIndex(
|
||||
(layer) => layer.id === this.groupId
|
||||
);
|
||||
|
||||
if (groupIndex !== -1) {
|
||||
console.log(`↩️ 移除组图层: ${this.groupId}`);
|
||||
// 从图层列表中移除组图层
|
||||
this.layerManager.layers.value.splice(groupIndex, 1);
|
||||
}
|
||||
}
|
||||
|
||||
if (this.fabricImage) {
|
||||
console.log(`↩️ 移除抠图图像: ${this.fabricImage.id}`);
|
||||
// 从画布中移除抠图图像
|
||||
this.canvas.remove(this.fabricImage);
|
||||
}
|
||||
|
||||
// 2. 逆序撤销所有已执行的子命令
|
||||
for (let i = this.executedCommands.length - 1; i >= 0; i--) {
|
||||
const command = this.executedCommands[i];
|
||||
if (command && typeof command.undo === "function") {
|
||||
try {
|
||||
console.log(`↩️ 撤销子命令: ${command.constructor.name}`);
|
||||
await command.undo();
|
||||
console.log(`✅ 子命令撤销成功: ${command.constructor.name}`);
|
||||
} catch (error) {
|
||||
console.error(
|
||||
`❌ 子命令撤销失败: ${command.constructor.name}`,
|
||||
error
|
||||
);
|
||||
// 子命令撤销失败不中断整个撤销过程
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 3. 清理状态
|
||||
this.executedCommands = [];
|
||||
this.newLayerId = null;
|
||||
this.cutoutImageUrl = null;
|
||||
this.fabricImage = null;
|
||||
this.groupLayer = null; // 清理组图层引用
|
||||
// 注意:不重置groupId,因为重做时可能需要使用相同的ID
|
||||
|
||||
// 4. 更新画布和图层交互性
|
||||
await this.layerManager.updateLayersObjectsInteractivity();
|
||||
|
||||
console.log(`✅ 套索抠图撤销完成`);
|
||||
return true;
|
||||
} catch (error) {
|
||||
console.error("撤销套索抠图失败:", error);
|
||||
console.error("❌ 撤销套索抠图失败:", error);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取命令信息
|
||||
* @returns {Object} 命令详细信息
|
||||
*/
|
||||
getInfo() {
|
||||
return {
|
||||
name: this.name,
|
||||
description: this.description,
|
||||
newLayerId: this.newLayerId,
|
||||
newLayerName: this.newLayerName,
|
||||
groupId: this.groupId,
|
||||
groupName: this.groupName,
|
||||
executedCommandsCount: this.executedCommands.length,
|
||||
hasGroupLayer: !!this.groupLayer,
|
||||
sourceLayerId: this.sourceLayerId,
|
||||
highResolutionEnabled: this.highResolutionEnabled,
|
||||
baseResolutionScale: this.baseResolutionScale,
|
||||
hasSerializedSelection: !!this.serializedSelectionObject,
|
||||
selectionType: this.serializedSelectionObject?.type || null,
|
||||
subCommands: this.executedCommands.map((cmd) => ({
|
||||
name: cmd.constructor.name,
|
||||
info: cmd.getInfo ? cmd.getInfo() : {},
|
||||
})),
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取图层的所有对象(包括子图层,从画布中查找真实对象)
|
||||
* @param {Object} layer 图层对象
|
||||
@@ -249,6 +398,7 @@ export class LassoCutoutCommand extends CompositeCommand {
|
||||
scaleFactor: scaleFactor,
|
||||
// isReturenDataURL: true, // 返回DataURL
|
||||
preserveOriginalQuality: true, // 启用高质量模式
|
||||
selectionManager: this.selectionManager, // 传递选区管理器,用于获取羽化值
|
||||
});
|
||||
|
||||
if (!rasterizedDataURL) {
|
||||
@@ -500,4 +650,129 @@ export class LassoCutoutCommand extends CompositeCommand {
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* 序列化选区对象
|
||||
* @private
|
||||
*/
|
||||
_serializeSelectionObject() {
|
||||
try {
|
||||
if (!this.selectionManager) {
|
||||
console.warn("选区管理器不存在,无法序列化选区对象");
|
||||
return;
|
||||
}
|
||||
|
||||
const selectionObject = this.selectionManager.getSelectionObject();
|
||||
if (!selectionObject) {
|
||||
console.warn("当前没有选区对象,无法序列化");
|
||||
return;
|
||||
}
|
||||
|
||||
// 将选区对象转换为可序列化的对象
|
||||
this.serializedSelectionObject = selectionObject.toObject([
|
||||
"id",
|
||||
"layerId",
|
||||
"layerName",
|
||||
"parentId",
|
||||
]);
|
||||
|
||||
console.log("选区对象已序列化保存");
|
||||
} catch (error) {
|
||||
console.error("序列化选区对象失败:", error);
|
||||
this.serializedSelectionObject = null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 反序列化选区对象
|
||||
* @returns {Promise<Object>} 选区对象
|
||||
* @private
|
||||
*/
|
||||
async _getSelectionObject() {
|
||||
try {
|
||||
// 首先尝试从选区管理器获取当前选区
|
||||
const currentSelection = this.selectionManager.getSelectionObject();
|
||||
if (currentSelection) {
|
||||
console.log("从选区管理器获取到当前选区");
|
||||
return currentSelection;
|
||||
}
|
||||
|
||||
// 如果当前没有选区,则从序列化数据恢复
|
||||
if (!this.serializedSelectionObject) {
|
||||
console.error("没有序列化的选区对象数据");
|
||||
return null;
|
||||
}
|
||||
|
||||
console.log("从序列化数据恢复选区对象");
|
||||
|
||||
// 根据选区对象类型进行反序列化
|
||||
return new Promise((resolve, reject) => {
|
||||
const objectType = this.serializedSelectionObject.type;
|
||||
|
||||
if (objectType === "path") {
|
||||
// 如果是路径类型(套索选区)
|
||||
fabric.Path.fromObject(this.serializedSelectionObject, (path) => {
|
||||
if (path) {
|
||||
console.log("路径选区对象反序列化成功");
|
||||
resolve(path);
|
||||
} else {
|
||||
reject(new Error("路径选区对象反序列化失败"));
|
||||
}
|
||||
});
|
||||
} else if (objectType === "polygon") {
|
||||
// 如果是多边形类型
|
||||
fabric.Polygon.fromObject(
|
||||
this.serializedSelectionObject,
|
||||
(polygon) => {
|
||||
if (polygon) {
|
||||
console.log("多边形选区对象反序列化成功");
|
||||
resolve(polygon);
|
||||
} else {
|
||||
reject(new Error("多边形选区对象反序列化失败"));
|
||||
}
|
||||
}
|
||||
);
|
||||
} else if (objectType === "rect") {
|
||||
// 如果是矩形选区
|
||||
fabric.Rect.fromObject(this.serializedSelectionObject, (rect) => {
|
||||
if (rect) {
|
||||
console.log("矩形选区对象反序列化成功");
|
||||
resolve(rect);
|
||||
} else {
|
||||
reject(new Error("矩形选区对象反序列化失败"));
|
||||
}
|
||||
});
|
||||
} else if (objectType === "ellipse" || objectType === "circle") {
|
||||
// 如果是椭圆/圆形选区
|
||||
fabric.Ellipse.fromObject(
|
||||
this.serializedSelectionObject,
|
||||
(ellipse) => {
|
||||
if (ellipse) {
|
||||
console.log("椭圆选区对象反序列化成功");
|
||||
resolve(ellipse);
|
||||
} else {
|
||||
reject(new Error("椭圆选区对象反序列化失败"));
|
||||
}
|
||||
}
|
||||
);
|
||||
} else {
|
||||
// 通用对象反序列化
|
||||
fabric.util.enlivenObjects(
|
||||
[this.serializedSelectionObject],
|
||||
(objects) => {
|
||||
if (objects && objects.length > 0) {
|
||||
console.log("通用选区对象反序列化成功");
|
||||
resolve(objects[0]);
|
||||
} else {
|
||||
reject(new Error("通用选区对象反序列化失败"));
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
});
|
||||
} catch (error) {
|
||||
console.error("获取选区对象失败:", error);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -490,6 +490,7 @@ export class LiquifyStateCommand extends Command {
|
||||
* @param {String} options.targetLayerId 目标图层ID
|
||||
* @param {ImageData} options.initialImageData 初始图像数据
|
||||
* @param {ImageData} options.finalImageData 最终图像数据
|
||||
* @param {Object} options.liquifyManager 液化管理器实例
|
||||
*/
|
||||
constructor(options) {
|
||||
super({
|
||||
@@ -502,6 +503,7 @@ export class LiquifyStateCommand extends Command {
|
||||
this.targetObject = options.targetObject;
|
||||
this.targetLayerId = options.targetLayerId;
|
||||
this.targetObjectId = options.targetObjectId;
|
||||
this.liquifyManager = options.liquifyManager; // 添加液化管理器引用
|
||||
|
||||
// 获取引用管理器实例
|
||||
this.refManager = getLiquifyReferenceManager();
|
||||
@@ -520,6 +522,10 @@ export class LiquifyStateCommand extends Command {
|
||||
this.initialImageData = options.initialImageData;
|
||||
this.finalImageData = options.finalImageData;
|
||||
|
||||
// 保存液化管理器的操作记录状态
|
||||
this.initialLiquifyState = null;
|
||||
this.finalLiquifyState = null;
|
||||
|
||||
this.currentState = "initial";
|
||||
|
||||
// 创建初始快照
|
||||
@@ -547,6 +553,19 @@ export class LiquifyStateCommand extends Command {
|
||||
this.finalImageData
|
||||
);
|
||||
|
||||
// 恢复液化管理器到最终状态
|
||||
if (this.liquifyManager && this.finalLiquifyState) {
|
||||
this._restoreLiquifyManagerState(this.finalLiquifyState);
|
||||
} else if (this.liquifyManager) {
|
||||
// 如果没有保存的最终状态,重新准备液化环境
|
||||
const currentTarget = this.refManager.getObjectRef(this.objectRefId);
|
||||
if (currentTarget) {
|
||||
await this.liquifyManager.prepareForLiquify(currentTarget);
|
||||
// 保存当前的液化管理器状态作为最终状态
|
||||
this.finalLiquifyState = this._captureLiquifyManagerState();
|
||||
}
|
||||
}
|
||||
|
||||
this.currentState = "final";
|
||||
this.canvas.renderAll();
|
||||
|
||||
@@ -568,6 +587,21 @@ export class LiquifyStateCommand extends Command {
|
||||
this.initialSnapshotId
|
||||
);
|
||||
|
||||
// 恢复液化管理器到初始状态
|
||||
if (this.liquifyManager) {
|
||||
if (this.initialLiquifyState) {
|
||||
this._restoreLiquifyManagerState(this.initialLiquifyState);
|
||||
} else {
|
||||
// 如果没有初始状态,重置液化管理器
|
||||
this.liquifyManager.reset();
|
||||
// 重新准备液化环境
|
||||
const currentTarget = this.refManager.getObjectRef(this.objectRefId);
|
||||
if (currentTarget) {
|
||||
await this.liquifyManager.prepareForLiquify(currentTarget);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
this.currentState = "initial";
|
||||
this.canvas.renderAll();
|
||||
|
||||
@@ -589,6 +623,11 @@ export class LiquifyStateCommand extends Command {
|
||||
setFinalImageData(finalImageData) {
|
||||
this.finalImageData = finalImageData;
|
||||
this.finalSnapshotId = null; // 重置快照ID,下次执行时重新创建
|
||||
|
||||
// 捕获当前液化管理器状态作为最终状态
|
||||
if (this.liquifyManager) {
|
||||
this.finalLiquifyState = this._captureLiquifyManagerState();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -672,6 +711,12 @@ export class LiquifyStateCommand extends Command {
|
||||
};
|
||||
|
||||
this.refManager.stateSnapshots.set(this.initialSnapshotId, snapshot);
|
||||
|
||||
// 捕获初始液化管理器状态
|
||||
if (this.liquifyManager) {
|
||||
this.initialLiquifyState = this._captureLiquifyManagerState();
|
||||
}
|
||||
|
||||
console.log(`📸 初始状态快照已创建: ${this.initialSnapshotId}`);
|
||||
}
|
||||
}
|
||||
@@ -697,27 +742,180 @@ export class LiquifyStateCommand extends Command {
|
||||
};
|
||||
|
||||
this.refManager.stateSnapshots.set(this.finalSnapshotId, snapshot);
|
||||
|
||||
// 捕获最终液化管理器状态
|
||||
if (this.liquifyManager) {
|
||||
this.finalLiquifyState = this._captureLiquifyManagerState();
|
||||
}
|
||||
|
||||
console.log(`📸 最终状态快照已创建: ${this.finalSnapshotId}`);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 计算命令本身的内存使用量
|
||||
* @returns {Number} 内存使用量(字节)
|
||||
* 捕获液化管理器的当前状态
|
||||
* @returns {Object} 液化管理器状态
|
||||
* @private
|
||||
*/
|
||||
_calculateCommandMemory() {
|
||||
let bytes = 0;
|
||||
_captureLiquifyManagerState() {
|
||||
if (!this.liquifyManager) return null;
|
||||
|
||||
// 计算ImageData内存使用
|
||||
if (this.initialImageData) {
|
||||
bytes += this.initialImageData.width * this.initialImageData.height * 4;
|
||||
}
|
||||
if (this.finalImageData) {
|
||||
bytes += this.finalImageData.width * this.finalImageData.height * 4;
|
||||
}
|
||||
try {
|
||||
const state = {
|
||||
// 捕获增强管理器状态
|
||||
enhancedManagerState: null,
|
||||
// 捕获当前渲染器状态
|
||||
activeRendererState: null,
|
||||
// 捕获目标对象引用
|
||||
targetObjectRef: this.liquifyManager.targetObject,
|
||||
// 捕获初始化状态
|
||||
initialized: this.liquifyManager.initialized || false,
|
||||
};
|
||||
|
||||
return bytes;
|
||||
// 如果有增强管理器,捕获其状态
|
||||
if (this.liquifyManager.enhancedManager) {
|
||||
const enhancedManager = this.liquifyManager.enhancedManager;
|
||||
state.enhancedManagerState = {
|
||||
initialized: enhancedManager.initialized,
|
||||
renderMode: enhancedManager.renderMode,
|
||||
targetObject: enhancedManager.targetObject,
|
||||
originalImageData: enhancedManager.originalImageData,
|
||||
currentImageData: enhancedManager.currentImageData,
|
||||
params: { ...enhancedManager.params },
|
||||
currentMode: enhancedManager.currentMode,
|
||||
};
|
||||
|
||||
// 如果有激活的渲染器,捕获其状态
|
||||
if (enhancedManager.activeRenderer) {
|
||||
const renderer = enhancedManager.activeRenderer;
|
||||
state.activeRendererState = {
|
||||
initialized: renderer.initialized,
|
||||
originalImageData: renderer.originalImageData,
|
||||
currentImageData: renderer.currentImageData,
|
||||
params: { ...renderer.params },
|
||||
currentMode: renderer.currentMode,
|
||||
// 对于CPU渲染器,还需要保存网格状态
|
||||
meshState: renderer.mesh
|
||||
? this._captureMeshState(renderer.mesh)
|
||||
: null,
|
||||
// 保存变形历史
|
||||
deformHistory: renderer.deformHistory
|
||||
? [...renderer.deformHistory]
|
||||
: [],
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
console.log(`💾 液化管理器状态已捕获:`, state);
|
||||
return state;
|
||||
} catch (error) {
|
||||
console.error("捕获液化管理器状态失败:", error);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 恢复液化管理器状态
|
||||
* @param {Object} state 要恢复的状态
|
||||
* @private
|
||||
*/
|
||||
_restoreLiquifyManagerState(state) {
|
||||
if (!this.liquifyManager || !state) return;
|
||||
|
||||
try {
|
||||
// 恢复基本状态
|
||||
this.liquifyManager.initialized = state.initialized;
|
||||
if (state.targetObjectRef) {
|
||||
this.liquifyManager.targetObject = state.targetObjectRef;
|
||||
}
|
||||
|
||||
// 恢复增强管理器状态
|
||||
if (state.enhancedManagerState && this.liquifyManager.enhancedManager) {
|
||||
const enhancedManager = this.liquifyManager.enhancedManager;
|
||||
const enhancedState = state.enhancedManagerState;
|
||||
|
||||
enhancedManager.initialized = enhancedState.initialized;
|
||||
enhancedManager.renderMode = enhancedState.renderMode;
|
||||
enhancedManager.targetObject = enhancedState.targetObject;
|
||||
enhancedManager.originalImageData = enhancedState.originalImageData;
|
||||
enhancedManager.currentImageData = enhancedState.currentImageData;
|
||||
enhancedManager.params = { ...enhancedState.params };
|
||||
enhancedManager.currentMode = enhancedState.currentMode;
|
||||
|
||||
// 恢复激活渲染器状态
|
||||
if (state.activeRendererState && enhancedManager.activeRenderer) {
|
||||
const renderer = enhancedManager.activeRenderer;
|
||||
const rendererState = state.activeRendererState;
|
||||
|
||||
renderer.initialized = rendererState.initialized;
|
||||
renderer.originalImageData = rendererState.originalImageData;
|
||||
renderer.currentImageData = rendererState.currentImageData;
|
||||
renderer.params = { ...rendererState.params };
|
||||
renderer.currentMode = rendererState.currentMode;
|
||||
|
||||
// 恢复网格状态(如果是CPU渲染器)
|
||||
if (rendererState.meshState && renderer.mesh) {
|
||||
this._restoreMeshState(renderer.mesh, rendererState.meshState);
|
||||
}
|
||||
|
||||
// 恢复变形历史
|
||||
if (rendererState.deformHistory) {
|
||||
renderer.deformHistory = [...rendererState.deformHistory];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
console.log(`🔄 液化管理器状态已恢复`);
|
||||
} catch (error) {
|
||||
console.error("恢复液化管理器状态失败:", error);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 捕获网格状态
|
||||
* @param {Array} mesh 网格数组
|
||||
* @returns {Array} 网格状态副本
|
||||
* @private
|
||||
*/
|
||||
_captureMeshState(mesh) {
|
||||
if (!mesh || !Array.isArray(mesh)) return null;
|
||||
|
||||
return mesh.map((row) =>
|
||||
row.map((point) => ({
|
||||
x: point.x,
|
||||
y: point.y,
|
||||
originalX: point.originalX,
|
||||
originalY: point.originalY,
|
||||
}))
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* 恢复网格状态
|
||||
* @param {Array} mesh 目标网格
|
||||
* @param {Array} meshState 要恢复的网格状态
|
||||
* @private
|
||||
*/
|
||||
_restoreMeshState(mesh, meshState) {
|
||||
if (
|
||||
!mesh ||
|
||||
!meshState ||
|
||||
!Array.isArray(mesh) ||
|
||||
!Array.isArray(meshState)
|
||||
)
|
||||
return;
|
||||
|
||||
for (let i = 0; i < Math.min(mesh.length, meshState.length); i++) {
|
||||
for (let j = 0; j < Math.min(mesh[i].length, meshState[i].length); j++) {
|
||||
const point = mesh[i][j];
|
||||
const statePoint = meshState[i][j];
|
||||
|
||||
point.x = statePoint.x;
|
||||
point.y = statePoint.y;
|
||||
point.originalX = statePoint.originalX;
|
||||
point.originalY = statePoint.originalY;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user