404 lines
10 KiB
JavaScript
404 lines
10 KiB
JavaScript
/**
|
|
* 液化面板状态管理器
|
|
* 负责管理液化操作的状态、性能优化和用户反馈
|
|
*/
|
|
export class LiquifyStateManager {
|
|
constructor(canvas, realtimeUpdater) {
|
|
this.canvas = canvas;
|
|
this.realtimeUpdater = realtimeUpdater;
|
|
|
|
// 状态管理
|
|
this.isOperating = false;
|
|
this.isDragging = false;
|
|
this.operationCount = 0;
|
|
this.startTime = null;
|
|
|
|
// 性能监控
|
|
this.performanceMetrics = {
|
|
totalOperations: 0,
|
|
totalTime: 0,
|
|
averageTime: 0,
|
|
maxTime: 0,
|
|
minTime: Infinity,
|
|
lastOperationTime: 0,
|
|
};
|
|
|
|
// 用户反馈
|
|
this.feedbackEnabled = true;
|
|
this.cursorCache = new Map();
|
|
|
|
// 设备性能检测
|
|
this.devicePerformance = this._detectDevicePerformance();
|
|
|
|
// console.log("🎯 液化状态管理器已初始化,设备性能等级:", this.devicePerformance);
|
|
}
|
|
|
|
/**
|
|
* 开始液化操作
|
|
*/
|
|
startOperation() {
|
|
if (this.isOperating) return;
|
|
|
|
this.isOperating = true;
|
|
this.startTime = performance.now();
|
|
|
|
// 根据设备性能调整设置
|
|
this._adjustPerformanceSettings();
|
|
|
|
// 显示操作反馈
|
|
this._showOperationFeedback();
|
|
|
|
// console.log("🚀 开始液化操作");
|
|
}
|
|
|
|
/**
|
|
* 开始拖拽
|
|
*/
|
|
startDrag() {
|
|
if (this.isDragging) return;
|
|
|
|
this.isDragging = true;
|
|
|
|
// 优化拖拽性能
|
|
this.realtimeUpdater?.enableDragMode();
|
|
|
|
// 更新鼠标样式
|
|
this._updateCursor("liquifying");
|
|
|
|
// 禁用不必要的画布功能
|
|
this._disableCanvasFeatures();
|
|
|
|
// console.log("🖱️ 开始拖拽操作");
|
|
}
|
|
|
|
/**
|
|
* 结束拖拽
|
|
*/
|
|
async endDrag() {
|
|
if (!this.isDragging) return;
|
|
|
|
// 恢复鼠标样式
|
|
this._updateCursor("default");
|
|
|
|
// 恢复画布功能
|
|
this._enableCanvasFeatures();
|
|
|
|
// 处理待处理的更新
|
|
if (this.realtimeUpdater) {
|
|
try {
|
|
await this.realtimeUpdater.processPendingUpdates();
|
|
} catch (error) {
|
|
console.error("处理待处理更新失败:", error);
|
|
} finally {
|
|
this.isDragging = false;
|
|
// 恢复正常模式
|
|
this.realtimeUpdater?.disableDragMode();
|
|
|
|
// 结束液化操作 添加结果到命令中 更新当前激活图层对象
|
|
}
|
|
}
|
|
|
|
// console.log("✅ 结束拖拽操作");
|
|
}
|
|
|
|
/**
|
|
* 结束液化操作
|
|
*/
|
|
endOperation() {
|
|
if (!this.isOperating) return;
|
|
|
|
const operationTime = performance.now() - this.startTime;
|
|
this._updatePerformanceMetrics(operationTime);
|
|
|
|
this.isOperating = false;
|
|
this.operationCount++;
|
|
|
|
// 隐藏操作反馈
|
|
this._hideOperationFeedback();
|
|
|
|
// console.log(`⏱️ 液化操作完成,耗时: ${operationTime.toFixed(2)}ms`);
|
|
}
|
|
|
|
/**
|
|
* 记录单次变形操作
|
|
*/
|
|
recordDeformation(operationTime) {
|
|
this.performanceMetrics.totalOperations++;
|
|
this.performanceMetrics.totalTime += operationTime;
|
|
this.performanceMetrics.averageTime =
|
|
this.performanceMetrics.totalTime / this.performanceMetrics.totalOperations;
|
|
|
|
this.performanceMetrics.maxTime = Math.max(this.performanceMetrics.maxTime, operationTime);
|
|
this.performanceMetrics.minTime = Math.min(this.performanceMetrics.minTime, operationTime);
|
|
this.performanceMetrics.lastOperationTime = operationTime;
|
|
}
|
|
|
|
/**
|
|
* 记录操作性能指标
|
|
* @param {Object} metrics 性能指标对象
|
|
*/
|
|
recordOperationMetrics(metrics) {
|
|
const { operationTime, operationType, mode, coordinates, imageSize, renderMode, isRealTime } =
|
|
metrics;
|
|
|
|
// 记录基础性能数据
|
|
this.recordDeformation(operationTime);
|
|
|
|
// 记录详细操作信息
|
|
this.performanceMetrics.lastOperation = {
|
|
type: operationType,
|
|
mode,
|
|
coordinates,
|
|
imageSize,
|
|
renderMode,
|
|
isRealTime,
|
|
timestamp: Date.now(),
|
|
};
|
|
|
|
// 根据性能数据动态调整设置
|
|
this._adaptivePerformanceOptimization(operationTime);
|
|
|
|
// console.log(
|
|
// `📊 记录性能指标: ${operationType}/${mode}, 耗时: ${operationTime.toFixed(
|
|
// 2
|
|
// )}ms, 渲染模式: ${renderMode}`
|
|
// );
|
|
}
|
|
|
|
/**
|
|
* 自适应性能优化
|
|
* @param {Number} operationTime 操作耗时
|
|
* @private
|
|
*/
|
|
_adaptivePerformanceOptimization(operationTime) {
|
|
if (!this.realtimeUpdater) return;
|
|
|
|
// 如果操作耗时过长,动态降低质量或增加节流时间
|
|
if (operationTime > 50 && this.devicePerformance !== "high") {
|
|
// 降低图像质量
|
|
const currentQuality = this.realtimeUpdater.config.imageQuality || 1.0;
|
|
if (currentQuality > 0.7) {
|
|
this.realtimeUpdater.setImageQuality(Math.max(0.7, currentQuality - 0.1));
|
|
// console.log("⚡ 自动降低图像质量以提升性能");
|
|
}
|
|
|
|
// 增加节流时间
|
|
if (this.realtimeUpdater.config.throttleTime < 33) {
|
|
this.realtimeUpdater.config.throttleTime = Math.min(
|
|
33,
|
|
this.realtimeUpdater.config.throttleTime + 8
|
|
);
|
|
// console.log("⏱️ 自动增加节流时间以提升性能");
|
|
}
|
|
}
|
|
|
|
// 如果性能很好,可以适当提高质量
|
|
if (operationTime < 20 && this.devicePerformance === "high") {
|
|
const currentQuality = this.realtimeUpdater.config.imageQuality || 1.0;
|
|
if (currentQuality < 1.0) {
|
|
this.realtimeUpdater.setImageQuality(Math.min(1.0, currentQuality + 0.05));
|
|
}
|
|
}
|
|
}
|
|
|
|
/**
|
|
* 获取性能报告
|
|
*/
|
|
getPerformanceReport() {
|
|
return {
|
|
...this.performanceMetrics,
|
|
devicePerformance: this.devicePerformance,
|
|
fps: this._calculateFPS(),
|
|
recommendations: this._generateRecommendations(),
|
|
};
|
|
}
|
|
|
|
/**
|
|
* 设置用户反馈
|
|
*/
|
|
setFeedbackEnabled(enabled) {
|
|
this.feedbackEnabled = enabled;
|
|
}
|
|
|
|
/**
|
|
* 清理资源
|
|
*/
|
|
dispose() {
|
|
this._enableCanvasFeatures();
|
|
this._updateCursor("default");
|
|
this.cursorCache.clear();
|
|
|
|
// console.log("🧹 液化状态管理器已清理");
|
|
}
|
|
|
|
// === 私有方法 ===
|
|
|
|
/**
|
|
* 检测设备性能
|
|
*/
|
|
_detectDevicePerformance() {
|
|
// 检测硬件并发数
|
|
const cores = navigator.hardwareConcurrency || 4;
|
|
|
|
// 检测内存
|
|
const memory = navigator.deviceMemory || 4;
|
|
|
|
// 检测连接类型
|
|
const connection = navigator.connection;
|
|
const effectiveType = connection?.effectiveType || "4g";
|
|
|
|
// 简单的性能评分算法
|
|
let score = 0;
|
|
score += cores * 10;
|
|
score += memory * 5;
|
|
|
|
if (effectiveType === "4g") score += 10;
|
|
else if (effectiveType === "3g") score += 5;
|
|
|
|
// 性能等级
|
|
if (score >= 70) return "high";
|
|
if (score >= 40) return "medium";
|
|
return "low";
|
|
}
|
|
|
|
/**
|
|
* 根据设备性能调整设置
|
|
*/
|
|
_adjustPerformanceSettings() {
|
|
if (!this.realtimeUpdater) return;
|
|
|
|
switch (this.devicePerformance) {
|
|
case "high":
|
|
this.realtimeUpdater.setImageQuality(1.0);
|
|
this.realtimeUpdater.config.throttleTime = 8; // 120fps
|
|
break;
|
|
case "medium":
|
|
this.realtimeUpdater.setImageQuality(0.9);
|
|
this.realtimeUpdater.config.throttleTime = 16; // 60fps
|
|
break;
|
|
case "low":
|
|
this.realtimeUpdater.setImageQuality(0.8);
|
|
this.realtimeUpdater.config.throttleTime = 33; // 30fps
|
|
break;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* 显示操作反馈
|
|
*/
|
|
_showOperationFeedback() {
|
|
if (!this.feedbackEnabled) return;
|
|
|
|
// 添加视觉反馈(可以是加载动画、进度条等)
|
|
document.body.style.cursor = "wait";
|
|
}
|
|
|
|
/**
|
|
* 隐藏操作反馈
|
|
*/
|
|
_hideOperationFeedback() {
|
|
if (!this.feedbackEnabled) return;
|
|
|
|
document.body.style.cursor = "default";
|
|
}
|
|
|
|
/**
|
|
* 更新鼠标样式
|
|
*/
|
|
_updateCursor(type) {
|
|
if (!this.feedbackEnabled) return;
|
|
|
|
const cursors = {
|
|
default: "default",
|
|
liquifying: "crosshair",
|
|
wait: "wait",
|
|
"not-allowed": "not-allowed",
|
|
};
|
|
|
|
const cursor = cursors[type] || "default";
|
|
|
|
if (this.canvas && this.canvas.upperCanvasEl) {
|
|
this.canvas.upperCanvasEl.style.cursor = cursor;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* 禁用画布功能以提高性能
|
|
*/
|
|
_disableCanvasFeatures() {
|
|
if (!this.canvas) return;
|
|
|
|
// 保存原始设置
|
|
this._originalSettings = {
|
|
renderOnAddRemove: this.canvas.renderOnAddRemove,
|
|
skipOffscreen: this.canvas.skipOffscreen,
|
|
enableRetinaScaling: this.canvas.enableRetinaScaling,
|
|
};
|
|
|
|
// 应用性能优化设置
|
|
this.canvas.renderOnAddRemove = false;
|
|
this.canvas.skipOffscreen = true;
|
|
|
|
// 低性能设备关闭高分辨率支持
|
|
if (this.devicePerformance === "low") {
|
|
this.canvas.enableRetinaScaling = false;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* 恢复画布功能
|
|
*/
|
|
_enableCanvasFeatures() {
|
|
if (!this.canvas || !this._originalSettings) return;
|
|
|
|
// 恢复原始设置
|
|
this.canvas.renderOnAddRemove = this._originalSettings.renderOnAddRemove;
|
|
this.canvas.skipOffscreen = this._originalSettings.skipOffscreen;
|
|
this.canvas.enableRetinaScaling = this._originalSettings.enableRetinaScaling;
|
|
|
|
this._originalSettings = null;
|
|
}
|
|
|
|
/**
|
|
* 更新性能指标
|
|
*/
|
|
_updatePerformanceMetrics(operationTime) {
|
|
this.performanceMetrics.totalTime += operationTime;
|
|
this.performanceMetrics.averageTime =
|
|
this.performanceMetrics.totalTime / (this.operationCount + 1);
|
|
|
|
this.performanceMetrics.maxTime = Math.max(this.performanceMetrics.maxTime, operationTime);
|
|
this.performanceMetrics.minTime = Math.min(this.performanceMetrics.minTime, operationTime);
|
|
}
|
|
|
|
/**
|
|
* 计算FPS
|
|
*/
|
|
_calculateFPS() {
|
|
if (this.performanceMetrics.averageTime === 0) return 0;
|
|
return Math.round(1000 / this.performanceMetrics.averageTime);
|
|
}
|
|
|
|
/**
|
|
* 生成性能建议
|
|
*/
|
|
_generateRecommendations() {
|
|
const recommendations = [];
|
|
|
|
if (this.performanceMetrics.averageTime > 50) {
|
|
recommendations.push("操作响应较慢,建议降低图像尺寸或关闭高质量模式");
|
|
}
|
|
|
|
if (this.devicePerformance === "low") {
|
|
recommendations.push("检测到低性能设备,已自动启用性能优化模式");
|
|
}
|
|
|
|
const fps = this._calculateFPS();
|
|
if (fps < 30) {
|
|
recommendations.push("帧率较低,建议减少同时进行的操作或降低液化强度");
|
|
}
|
|
|
|
return recommendations;
|
|
}
|
|
}
|