/**
 * CPU版本的液化管理器
 * 修复版本 - 解决三角形网格失真问题，优化持续按压效果
 */
export class LiquifyCPUManager {
	constructor(options = {}) {
		this.config = {
			gridSize: 8, // 稍微增大网格提高性能
			maxStrength: 200, // 适度降低最大强度
			smoothingIterations: 1, // 增加平滑处理
			relaxFactor: 0.05, // 适度松弛
			sharpenAmount: 0.3, // 添加锐化强度参数
			...options,
		};
		console.log("CPU版本的液化管理器config", this.config);

		this.params = {
			size: 60, // 增大默认尺寸
			pressure: 0.6, // 增大默认压力
			distortion: 0,
			power: 0.7, // 增大默认动力
		};

		this.modes = {
			PUSH: "push",
			CLOCKWISE: "clockwise",
			COUNTERCLOCKWISE: "counterclockwise",
			PINCH: "pinch",
			EXPAND: "expand",
			CRYSTAL: "crystal",
			EDGE: "edge",
			RECONSTRUCT: "reconstruct",
		};

		this.currentMode = this.modes.PUSH;
		this.originalImageData = null;
		this.currentImageData = null;
		this.mesh = null;
		this.initialized = false;
		this.canvas = document.createElement("canvas");
		this.ctx = this.canvas.getContext("2d");
		this.deformHistory = [];

		// 性能优化相关
		this.lastUpdateTime = 0;
		this.updateThrottle = 16; // 限制更新频率约60fps
		this.isProcessing = false;

		// 鼠标位置跟踪（用于推拉模式）
		this.initialMouseX = 0; // 初始点击位置X
		this.initialMouseY = 0; // 初始点击位置Y
		this.currentMouseX = 0; // 当前鼠标位置X
		this.currentMouseY = 0; // 当前鼠标位置Y
		this.lastMouseX = 0;
		this.lastMouseY = 0;
		this.mouseMovementX = 0;
		this.mouseMovementY = 0;
		this.isFirstApply = true; // 标记是否是首次应用
		this.isDragging = false; // 标记是否正在拖拽
		this.dragDistance = 0; // 拖拽距离
		this.dragAngle = 0; // 拖拽角度

		// 新增：持续按压相关状态
		this.pressStartTime = 0; // 按压开始时间
		this.pressDuration = 0; // 按压持续时间
		this.accumulatedRotation = 0; // 累积旋转角度（用于顺时针/逆时针）--废除使用固定角度
		this.fixedRotationAngle = 0.32; // 固定旋转角度
		this.accumulatedScale = 0; // 累积缩放量（用于捏合/展开）
		this.lastApplyTime = 0; // 上次应用时间
		this.continuousApplyInterval = 50; // 持续应用间隔（毫秒）
		this.isHolding = false; // 是否正在持续按压
	}

	initialize(imageSource) {
		try {
			if (imageSource instanceof ImageData) {
				this.originalImageData = new ImageData(
					new Uint8ClampedArray(imageSource.data),
					imageSource.width,
					imageSource.height
				);
			} else if (imageSource instanceof HTMLImageElement) {
				this.canvas.width = imageSource.width;
				this.canvas.height = imageSource.height;
				this.ctx.drawImage(imageSource, 0, 0);
				this.originalImageData = this.ctx.getImageData(0, 0, imageSource.width, imageSource.height);
			} else {
				throw new Error("不支持的图像类型");
			}

			this.currentImageData = new ImageData(
				new Uint8ClampedArray(this.originalImageData.data),
				this.originalImageData.width,
				this.originalImageData.height
			);

			this._initMesh(this.originalImageData.width, this.originalImageData.height);
			this.initialized = true;
			return true;
		} catch (error) {
			console.error("液化管理器初始化失败:", error);
			return false;
		}
	}

	_initMesh(width, height) {
		const gridSize = this.config.gridSize;
		const cols = Math.ceil(width / gridSize);
		const rows = Math.ceil(height / gridSize);

		this.mesh = {
			cols,
			rows,
			gridSize,
			width,
			height,
			originalPoints: [],
			deformedPoints: [],
		};

		for (let y = 0; y <= rows; y++) {
			for (let x = 0; x <= cols; x++) {
				const point = { x: x * gridSize, y: y * gridSize };
				this.mesh.originalPoints.push({ ...point });
				this.mesh.deformedPoints.push({ ...point });
			}
		}
	}

	setMode(mode) {
		if (Object.values(this.modes).includes(mode)) {
			this.currentMode = mode;
			return true;
		}
		return false;
	}

	setParam(param, value) {
		if (param === 'sharpness') {
			this.config.sharpenAmount = Math.max(0, Math.min(1, value));
			return true;
		}
		if (param in this.params) {
			this.params[param] = value;
			return true;
		}
		return false;
	}

	getParams() {
		return { ...this.params, sharpness: this.config.sharpenAmount, };
	}
	// 添加清晰度控制方法
	setSharpness(amount) {
		this.config.sharpenAmount = Math.max(0, Math.min(1, amount));
		return this;
	}
	resetParams() {
		this.params = {
			size: 60, // 增大默认尺寸
			pressure: 0.6, // 增大默认压力
			distortion: 0,
			power: 0.7, // 增大默认动力
		};
	}

	/**
	 * 开始液化操作（记录初始点）
	 * @param {Number} x 初始X坐标
	 * @param {Number} y 初始Y坐标
	 */
	startDeformation(x, y) {
		this.initialMouseX = x;
		this.initialMouseY = y;
		this.currentMouseX = x;
		this.currentMouseY = y;
		this.lastMouseX = x;
		this.lastMouseY = y;
		this.isDragging = true;
		this.isFirstApply = true;
		this.dragDistance = 0;
		this.dragAngle = 0;

		// 新增：初始化持续按压状态
		this.pressStartTime = Date.now();
		this.pressDuration = 0;
		this.accumulatedRotation = 0;
		this.accumulatedScale = 0;
		this.lastApplyTime = this.pressStartTime;
		this.isHolding = true;

		// 启动持续效果定时器（对于所有模式都支持持续按压）
		// this.startContinuousEffect();

		console.log(`开始液化操作，初始点: (${x}, ${y})`);
	}

	/**
	 * 结束液化操作
	 */
	endDeformation() {
		this.isDragging = false;
		this.isFirstApply = true;
		this.dragDistance = 0;
		this.dragAngle = 0;

		// 新增：重置持续按压状态
		this.isHolding = false;
		this.pressStartTime = 0;
		this.pressDuration = 0;
		this.accumulatedRotation = 0;
		this.accumulatedScale = 0;
		this.lastApplyTime = 0;

		// 停止持续效果定时器
		this.stopContinuousEffect();

		console.log("结束液化操作");
	}

	// 新增：启动持续效果
	startContinuousEffect() {
		this.stopContinuousEffect(); // 先停止已有的定时器
		this.continuousTimer = setInterval(() => {
			if (this.isHolding && this.initialized) {
				// 更新持续时间
				this.pressDuration = Date.now() - this.pressStartTime;

				// 所有模式都支持持续效果
				this.applyContinuousDeformation();
			}
		}, this.continuousApplyInterval);
	}

	// 新增：停止持续效果
	stopContinuousEffect() {
		if (this.continuousTimer) {
			clearInterval(this.continuousTimer);
			this.continuousTimer = null;
		}
	}

	/**
	 * 稳定的旋转衰减函数 - 确保内圈快外圈慢，保持纹理连续性
	 * @param {number} t 归一化距离 (0-1)
	 * @returns {number} 衰减因子 (0-1)
	 */
	_stableRotationFalloff(t) {
		if (t >= 1.0) return 0;
		if (t <= 0) return 1;

		// 使用反向二次函数：内圈(t=0)时值为1，外圈(t=1)时值为0
		// 这确保了内圈旋转最快，外圈旋转最慢
		const inverseFalloff = 1 - t;

		// 使用平滑的二次衰减，确保内圈效果强，外圈效果弱
		const quadraticFalloff = inverseFalloff * inverseFalloff;

		// 添加轻微的线性分量，确保过渡平滑
		const linearFalloff = inverseFalloff;

		// 混合二次和线性衰减，70%二次衰减 + 30%线性衰减
		return quadraticFalloff * 0.7 + linearFalloff * 0.3;
	}

	/**
	 * 基于test-liquify-enhanced.html的旋转算法 - 像素级实现
	 * @param {number} centerX 旋转中心X坐标
	 * @param {number} centerY 旋转中心Y坐标
	 * @param {number} radius 影响半径
	 * @param {number} strength 强度
	 * @param {boolean} isClockwise 是否顺时针旋转
	 */
	_applyEnhancedRotationDeformation(centerX, centerY, radius, strength, isClockwise) {
		if (!this.currentImageData) return;
		const data = this.currentImageData.data;
		const width = this.currentImageData.width;
		const height = this.currentImageData.height;
		const tempData = new Uint8ClampedArray(data);

		// 计算旋转角度 - 基于test-liquify-enhanced.html的算法
		const { pressure, power } = this.params;
		const timeFactor = Math.min(this.pressDuration / 1000, 5.0);
		const baseRotationSpeed = 0.02; // 使用与测试文件相同的速度
		const rotationAngle =
			(isClockwise ? 1 : -1) * baseRotationSpeed * pressure * power * (1.0 + timeFactor * 0.5);

		console.log("持续应用旋转效果");
		// 累积旋转角度 - 关键：这确保了持续旋转效果
		this.accumulatedRotation += rotationAngle;

		const processRadius = Math.min(radius, Math.min(width, height) / 2);
		const minX = Math.max(0, Math.floor(centerX - processRadius));
		const maxX = Math.min(width, Math.ceil(centerX + processRadius));
		const minY = Math.max(0, Math.floor(centerY - processRadius));
		const maxY = Math.min(height, Math.ceil(centerY + processRadius));

		// 遍历影响区域内的每个像素
		for (let y = minY; y < maxY; y++) {
			for (let x = minX; x < maxX; x++) {
				const dx = x - centerX;
				const dy = y - centerY;
				const distance = Math.sqrt(dx * dx + dy * dy);

				if (distance < processRadius && distance > 0.1) {
					// 距离衰减：内圈快，外圈慢 - 与测试文件算法一致
					const normalizedDistance = distance / processRadius;
					const falloff = Math.pow(1 - normalizedDistance, 2); // 二次衰减

					// 计算旋转后的源位置 - 关键算法
					const angle = Math.atan2(dy, dx);
					// const newAngle = angle + this.accumulatedRotation * falloff;
					const newAngle = angle + (isClockwise ? this.fixedRotationAngle : -this.fixedRotationAngle) * falloff;

					const sourceX = centerX + Math.cos(newAngle) * distance;
					const sourceY = centerY + Math.sin(newAngle) * distance;

					// 双线性插值采样 - 确保像素连续性
					const color = this._bicubicInterpolate(tempData, width, height, sourceX, sourceY);

					if (color) {
						const targetIdx = (y * width + x) * 4;
						data[targetIdx] = color[0];
						data[targetIdx + 1] = color[1];
						data[targetIdx + 2] = color[2];
						data[targetIdx + 3] = color[3];
					}
				}
			}
		}

		return true;
	}

	/**
	 * 基于test-liquify-enhanced.html的捏合/展开算法
	 * @param {number} centerX 中心X坐标
	 * @param {number} centerY 中心Y坐标
	 * @param {number} radius 影响半径
	 * @param {number} strength 强度
	 * @param {boolean} isPinch 是否为捏合模式
	 */
	_applyEnhancedPinchDeformation(centerX, centerY, radius, strength, isPinch) {
		if (!this.currentImageData) return;

		const data = this.currentImageData.data;
		const width = this.currentImageData.width;
		const height = this.currentImageData.height;
		const tempData = new Uint8ClampedArray(data);

		// 计算时间相关的缩放因子 - 基于test-liquify-enhanced.html
		const timeFactor = Math.min(this.pressDuration / 1000, 3.0);
		const baseScaleFactor = isPinch ? -0.01 : 0.01;
		const scaleFactor = baseScaleFactor * (1.0 + timeFactor * 0.5);

		this.accumulatedScale += scaleFactor;

		const processRadius = Math.min(radius, Math.min(width, height) / 2);
		const minX = Math.max(0, Math.floor(centerX - processRadius));
		const maxX = Math.min(width, Math.ceil(centerX + processRadius));
		const minY = Math.max(0, Math.floor(centerY - processRadius));
		const maxY = Math.min(height, Math.ceil(centerY + processRadius));

		for (let y = minY; y < maxY; y++) {
			for (let x = minX; x < maxX; x++) {
				const dx = x - centerX;
				const dy = y - centerY;
				const distance = Math.sqrt(dx * dx + dy * dy);

				if (distance < processRadius && distance > 0.1) {
					const normalizedDistance = distance / processRadius;
					const falloff = 1 - normalizedDistance * normalizedDistance;

					// 计算缩放后的位置
					const scale = 1 + this.accumulatedScale * falloff;
					const sourceX = centerX + dx * scale;
					const sourceY = centerY + dy * scale;

					// 双线性插值采样
					const color = this._bicubicInterpolate(tempData, width, height, sourceX, sourceY);

					if (color) {
						const targetIdx = (y * width + x) * 4;
						data[targetIdx] = color[0];
						data[targetIdx + 1] = color[1];
						data[targetIdx + 2] = color[2];
						data[targetIdx + 3] = color[3];
					}
				}
			}
		}

		return true;
	}

	/**
	 * 基于test-liquify-enhanced.html的推拉算法
	 * @param {number} centerX 中心X坐标
	 * @param {number} centerY 中心Y坐标
	 * @param {number} radius 影响半径
	 * @param {number} strength 强度
	 */
	_applyEnhancedPushDeformation(centerX, centerY, radius, strength) {
		if (!this.currentImageData) return;
		const data = this.currentImageData.data;
		const width = this.currentImageData.width;
		const height = this.currentImageData.height;
		const tempData = new Uint8ClampedArray(data);

		// 计算推拉方向
		const deltaX = this.currentMouseX - this.lastMouseX;
		const deltaY = this.currentMouseY - this.lastMouseY;
		const dragLength = Math.sqrt(deltaX * deltaX + deltaY * deltaY);
		this.lastMouseX = this.currentMouseX;
		this.lastMouseY = this.currentMouseY;

		const processRadius = Math.min(radius, Math.min(width, height) / 2);
		const minX = Math.max(0, Math.floor(centerX - processRadius));
		const maxX = Math.min(width, Math.ceil(centerX + processRadius));
		const minY = Math.max(0, Math.floor(centerY - processRadius));
		const maxY = Math.min(height, Math.ceil(centerY + processRadius));

		if (dragLength === 0) {
			// 如果没有拖拽，在持续按压时执行基础的外推效果
			if (this.isHolding) {
				const timeFactor = Math.min(this.pressDuration / 1000, 2.0);
				const pushStrength = strength * timeFactor * 0.3;

				for (let y = minY; y < maxY; y++) {
					for (let x = minX; x < maxX; x++) {
						// 此处循环4万次
						const dx = x - centerX;
						const dy = y - centerY;
						const distance = Math.sqrt(dx * dx + dy * dy);

						if (distance < processRadius && distance > 0.1) {
							const normalizedDistance = distance / processRadius;
							const falloff = 1 - normalizedDistance * normalizedDistance;
							const factor = falloff * pushStrength;

							// 径向外推效果
							const pushX = (dx / distance) * factor;
							const pushY = (dy / distance) * factor;

							const sourceX = x - pushX;
							const sourceY = y - pushY;

							const color = this._bicubicInterpolate(tempData, width, height, sourceX, sourceY);

							if (color) {
								const targetIdx = (y * width + x) * 4;
								data[targetIdx] = color[0];
								data[targetIdx + 1] = color[1];
								data[targetIdx + 2] = color[2];
								data[targetIdx + 3] = color[3];
							}
						}
					}
				}
			}
			return true;
		}

		// 有拖拽时的推拉效果
		const dirX = deltaX / dragLength;
		const dirY = deltaY / dragLength;
		for (let y = minY; y < maxY; y++) {
			for (let x = minX; x < maxX; x++) {
				// 此处循环4万次
				const dx = x - centerX;
				const dy = y - centerY;
				const distance = Math.sqrt(dx * dx + dy * dy);

				if (distance < processRadius && distance > 0.1) {
					const normalizedDistance = distance / processRadius;
					const falloff = 1 - normalizedDistance * normalizedDistance;
					const factor = falloff * strength;

					const offsetX = dirX * factor * Math.min(dragLength * 2, 30);
					const offsetY = dirY * factor * Math.min(dragLength * 2, 30);

					const sourceX = x - offsetX;
					const sourceY = y - offsetY;

					const color = this._bicubicInterpolate(tempData, width, height, sourceX, sourceY);

					if (color) {
						const targetIdx = (y * width + x) * 4;
						data[targetIdx] = color[0];
						data[targetIdx + 1] = color[1];
						data[targetIdx + 2] = color[2];
						data[targetIdx + 3] = color[3];
					}
				}
			}
		}

		return true;
	}

	/**
	 * 优化的持续变形效果处理 - 使用增强算法
	 */
	applyContinuousDeformation() {
		if (!this.isHolding || !this.initialized || !this.currentImageData) return;

		const { size, pressure, power } = this.params;
		const mode = this.currentMode;
		const radius = size;
		const x = this.initialMouseX;
		const y = this.initialMouseY;
		const strength = pressure * power;

		// 根据模式使用相应的增强算法
		switch (mode) {
			case this.modes.CLOCKWISE:
				this._applyEnhancedRotationDeformation(x, y, radius, strength, true);
				break;

			case this.modes.COUNTERCLOCKWISE:
				this._applyEnhancedRotationDeformation(x, y, radius, strength, false);
				break;

			case this.modes.PINCH:
				this._applyEnhancedPinchDeformation(x, y, radius, strength, true);
				break;

			case this.modes.EXPAND:
				this._applyEnhancedPinchDeformation(x, y, radius, strength, false);
				break;

			case this.modes.PUSH:
				// this._applyEnhancedPushDeformation(x, y, radius, strength);
				break;

			default: {
				// 对于其他模式，使用原有的网格算法
				if (!this.mesh) return;

				const baseStrength = (pressure * power * this.config.maxStrength) / 100;
				const timeFactor = Math.min(this.pressDuration / 1000, 4.0);
				const finalStrength = baseStrength * (1.0 + timeFactor * 0.5);

				this._applyDeformation(x, y, radius, finalStrength, mode, this.params.distortion);

				if (this.config.smoothingIterations > 0) {
					this._lightSmoothing();
				}

				return this._applyMeshToImage();
			}
		}

		// 对于像素算法，直接返回当前图像数据
		return this.currentImageData;
	}

	/**
	 * 双线性插值函数
	 * @param {Uint8ClampedArray} data 图像数据
	 * @param {number} width 图像宽度
	 * @param {number} height 图像高度
	 * @param {number} x X坐标
	 * @param {number} y Y坐标
	 * @returns {Array|null} RGBA颜色值数组或null
	 */
	_bilinearInterpolate(data, width, height, x, y) {
		const x1 = Math.floor(x);
		const y1 = Math.floor(y);
		const x2 = Math.min(width - 1, x1 + 1);
		const y2 = Math.min(height - 1, y1 + 1);

		const dx = x - x1;
		const dy = y - y1;
		const dx1 = 1 - dx;
		const dy1 = 1 - dy;
		const index1 = (y1 * width + x1) * 4;
		const index2 = (y1 * width + x2) * 4;
		const index3 = (y2 * width + x1) * 4;
		const index4 = (y2 * width + x2) * 4;
		const r =
			data[index1] * dx1 * dy1 +
			data[index2] * dx * dy1 +
			data[index3] * dx1 * dy +
			data[index4] * dx * dy;
		const g =
			data[index1 + 1] * dx1 * dy1 +
			data[index2 + 1] * dx * dy1 +
			data[index3 + 1] * dx1 * dy +
			data[index4 + 1] * dx * dy;
		const b =
			data[index1 + 2] * dx1 * dy1 +
			data[index2 + 2] * dx * dy1 +
			data[index3 + 2] * dx1 * dy +
			data[index4 + 2] * dx * dy;
		const a =
			data[index1 + 3] * dx1 * dy1 +
			data[index2 + 3] * dx * dy1 +
			data[index3 + 3] * dx1 * dy +
			data[index4 + 3] * dx * dy;
		return [Math.round(r), Math.round(g), Math.round(b), Math.round(a)];
	}

	/**
	 * 三次插值实现 - 确保正确处理Alpha通道
	 * @param {Uint8ClampedArray} data 图像数据
	 * @param {number} width 图像宽度
	 * @param {number} height 图像高度
	 * @param {number} x X坐标
	 * @param {number} y Y坐标
	 * @returns {Array|null} RGBA颜色值数组或null
	 */
	_bicubicInterpolate(data, width, height, x, y) {
		// return this._bilinearInterpolate(data, width, height, x, y);

		// 获取周围16个像素点
		const x1 = Math.floor(x) - 1;
		const y1 = Math.floor(y) - 1;

		// 创建16个采样点的颜色数组
		const pixels = [];
		for (let ky = 0; ky < 4; ky++) {
			for (let kx = 0; kx < 4; kx++) {
				const px = Math.max(0, Math.min(width - 1, x1 + kx));
				const py = Math.max(0, Math.min(height - 1, y1 + ky));
				const idx = (py * width + px) * 4;
				pixels[ky * 4 + kx] = [data[idx], data[idx + 1], data[idx + 2], data[idx + 3]];
			}
		}

		// 计算小数部分
		const fx = x - (x1 + 1);
		const fy = y - (y1 + 1);

		// 计算行插值
		const row0 = this._cubicInterpolateRow(pixels[0], pixels[1], pixels[2], pixels[3], fx);
		const row1 = this._cubicInterpolateRow(pixels[4], pixels[5], pixels[6], pixels[7], fx);
		const row2 = this._cubicInterpolateRow(pixels[8], pixels[9], pixels[10], pixels[11], fx);
		const row3 = this._cubicInterpolateRow(pixels[12], pixels[13], pixels[14], pixels[15], fx);

		// 计算最终结果
		return this._cubicInterpolateRow(row0, row1, row2, row3, fy);
	}
	// 三次插值辅助方法 - 单行插值
	_cubicInterpolateRow(p0, p1, p2, p3, t) {
		// 使用三次多项式插值公式
		const a = [0, 0, 0, 0];
		const b = [0, 0, 0, 0];
		const c = [0, 0, 0, 0];

		// 为每个通道计算插值系数
		for (let i = 0; i < 4; i++) {
			a[i] = -0.5 * p0[i] + 1.5 * p1[i] - 1.5 * p2[i] + 0.5 * p3[i];
			b[i] = p0[i] - 2.5 * p1[i] + 2 * p2[i] - 0.5 * p3[i];
			c[i] = -0.5 * p0[i] + 0.5 * p2[i];
		}

		// 应用三次多项式
		const t2 = t * t;
		const t3 = t * t2;

		return [
			Math.round(a[0] * t3 + b[0] * t2 + c[0] * t + p1[0]),
			Math.round(a[1] * t3 + b[1] * t2 + c[1] * t + p1[1]),
			Math.round(a[2] * t3 + b[2] * t2 + c[2] * t + p1[2]),
			Math.round(a[3] * t3 + b[3] * t2 + c[3] * t + p1[3]) // 确保Alpha通道也被正确插值
		];
	}

	/**
	 * 应用变形到网格 - 原有的网格算法（用于其他模式）
	 */
	_applyDeformation(x, y, radius, strength, mode, distortion) {
		if (!this.mesh) return;

		const points = this.mesh.deformedPoints;
		const originalPoints = this.mesh.originalPoints;

		// 性能优化：只计算影响范围内的网格点
		const affectedPoints = this._getAffectedPoints(x, y, radius);

		for (const pointInfo of affectedPoints) {
			const { index: i, point, originalPoint, distance } = pointInfo;

			if (distance > 0) {
				// 使用优化的衰减函数
				const normalizedDistance = distance / radius;
				const factor = this._optimizedFalloff(normalizedDistance) * strength;

				switch (mode) {
					case this.modes.CRYSTAL: {
						// 水晶模式
						const dx = point.x - x;
						const dy = point.y - y;
						const crystalAngle = Math.atan2(dy, dx);
						const crystalRadius = normalizedDistance;

						const baseDistortion = Math.max(distortion, 0.3);
						const timeFactor = Math.min(this.pressDuration / 1000, 2.0);
						const timeEnhancedDistortion = baseDistortion * (1.0 + timeFactor * 0.3);

						const wave1 = Math.sin(crystalAngle * 8 + this.pressDuration * 0.005) * 0.6;
						const wave2 = Math.cos(crystalAngle * 12 + this.pressDuration * 0.003) * 0.4;
						const waveAngle = crystalAngle + (wave1 + wave2) * timeEnhancedDistortion;

						const radialMod =
							1 + Math.sin(crystalRadius * Math.PI * 2 + this.pressDuration * 0.002) * 0.3;
						const modDistance = distance * radialMod;

						const crystalX = x + Math.cos(waveAngle) * modDistance;
						const crystalY = y + Math.sin(waveAngle) * modDistance;

						const crystalFactor = factor * timeEnhancedDistortion * 0.7;
						point.x += (crystalX - point.x) * crystalFactor;
						point.y += (crystalY - point.y) * crystalFactor;
						break;
					}

					case this.modes.EDGE: {
						// 边缘模式
						const dx = point.x - x;
						const dy = point.y - y;
						const edgeAngle = Math.atan2(dy, dx);
						const edgeRadius = normalizedDistance;

						const baseEdgeDistortion = Math.max(distortion, 0.5);
						const timeFactor = Math.min(this.pressDuration / 1000, 2.5);
						const timeEnhancedDistortion = baseEdgeDistortion * (1.0 + timeFactor * 0.4);

						const edgeWave =
							Math.sin(edgeRadius * Math.PI * 4 + this.pressDuration * 0.004) *
							Math.cos(edgeAngle * 6 + this.pressDuration * 0.002);
						const perpAngle = edgeAngle + Math.PI / 2;

						const edgeFactor = edgeWave * factor * timeEnhancedDistortion * 0.5;
						const edgeOffsetX = Math.cos(perpAngle) * edgeFactor;
						const edgeOffsetY = Math.sin(perpAngle) * edgeFactor;

						point.x += edgeOffsetX;
						point.y += edgeOffsetY;
						break;
					}

					case this.modes.RECONSTRUCT: {
						// 重建模式
						const restoreFactor = factor * 0.2;
						point.x += (originalPoint.x - point.x) * restoreFactor;
						point.y += (originalPoint.y - point.y) * restoreFactor;
						break;
					}
				}
			}
		}
	}

	/**
	 * 获取受影响的网格点（范围优化）
	 */
	_getAffectedPoints(centerX, centerY, radius) {
		const { cols, rows, gridSize } = this.mesh;
		const points = this.mesh.deformedPoints;
		const originalPoints = this.mesh.originalPoints;
		const affectedPoints = [];

		// 计算影响范围的网格边界
		const minGridX = Math.max(0, Math.floor((centerX - radius) / gridSize));
		const maxGridX = Math.min(cols, Math.ceil((centerX + radius) / gridSize));
		const minGridY = Math.max(0, Math.floor((centerY - radius) / gridSize));
		const maxGridY = Math.min(rows, Math.ceil((centerY + radius) / gridSize));

		// 只遍历影响范围内的网格点
		for (let gridY = minGridY; gridY <= maxGridY; gridY++) {
			for (let gridX = minGridX; gridX <= maxGridX; gridX++) {
				const index = gridY * (cols + 1) + gridX;
				if (index < points.length) {
					const point = points[index];
					const originalPoint = originalPoints[index];
					const dx = point.x - centerX;
					const dy = point.y - centerY;
					const distance = Math.sqrt(dx * dx + dy * dy);

					// 只包含在影响半径内的点
					if (distance <= radius) {
						affectedPoints.push({
							index,
							point,
							originalPoint,
							distance,
							dx,
							dy,
						});
					}
				}
			}
		}

		return affectedPoints;
	}

	_smoothMesh() {
		const { rows, cols } = this.mesh;
		const points = this.mesh.deformedPoints;
		const tempPoints = points.map((p) => ({ x: p.x, y: p.y }));

		for (let iteration = 0; iteration < this.config.smoothingIterations; iteration++) {
			for (let y = 1; y < rows; y++) {
				for (let x = 1; x < cols; x++) {
					const idx = y * (cols + 1) + x;
					const left = points[y * (cols + 1) + (x - 1)];
					const right = points[y * (cols + 1) + (x + 1)];
					const top = points[(y - 1) * (cols + 1) + x];
					const bottom = points[(y + 1) * (cols + 1) + x];

					const centerX = (left.x + right.x + top.x + bottom.x) / 4;
					const centerY = (left.y + right.y + top.y + bottom.y) / 4;

					const relaxFactor = this.config.relaxFactor;
					tempPoints[idx].x += (centerX - points[idx].x) * relaxFactor;
					tempPoints[idx].y += (centerY - points[idx].y) * relaxFactor;
				}
			}

			for (let i = 0; i < points.length; i++) {
				points[i].x = tempPoints[i].x;
				points[i].y = tempPoints[i].y;
			}
		}
	}

	/**
	 * 专门为旋转模式优化的网格平滑
	 */
	_lightSmoothing() {
		const { rows, cols } = this.mesh;
		const points = this.mesh.deformedPoints;
		const tempPoints = points.map((p) => ({ x: p.x, y: p.y }));

		// 只进行一次轻微平滑
		for (let y = 1; y < rows; y++) {
			for (let x = 1; x < cols; x++) {
				const idx = y * (cols + 1) + x;
				const left = points[y * (cols + 1) + (x - 1)];
				const right = points[y * (cols + 1) + (x + 1)];
				const top = points[(y - 1) * (cols + 1) + x];
				const bottom = points[(y + 1) * (cols + 1) + x];

				const centerX = (left.x + right.x + top.x + bottom.x) / 4;
				const centerY = (left.y + right.y + top.y + bottom.y) / 4;

				// 使用更小的松弛因子
				const lightRelaxFactor = this.config.relaxFactor * 0.3;
				tempPoints[idx].x += (centerX - points[idx].x) * lightRelaxFactor;
				tempPoints[idx].y += (centerY - points[idx].y) * lightRelaxFactor;
			}
		}

		for (let i = 0; i < points.length; i++) {
			points[i].x = tempPoints[i].x;
			points[i].y = tempPoints[i].y;
		}
	}

	/**
	 * 使用更优化的衰减函数
	 * @param {number} t 归一化距离 (0-1)
	 * @returns {number} 衰减因子 (0-1)
	 */
	_optimizedFalloff(t) {
		if (t >= 1.0) return 0;

		// 对于旋转模式，使用专门的衰减函数
		if (
			this.currentMode === this.modes.CLOCKWISE ||
			this.currentMode === this.modes.COUNTERCLOCKWISE
		) {
			return this._stableRotationFalloff(t); // 修复函数名
		}

		// 其他模式使用原来的衰减函数
		const smoothT = 1 - t;

		// 多项式衰减 + 指数衰减的组合
		const polynomial = smoothT * smoothT * (3 - 2 * smoothT); // 平滑阶梯函数
		const exponential = Math.exp(-t * 2); // 指数衰减

		// 组合两种衰减方式，在不同区域有不同特性
		const weight = Math.cos(t * Math.PI * 0.5); // 权重函数

		return polynomial * weight + exponential * (1 - weight);
	}

	_applyMeshToImage() {
		if (!this.mesh || !this.originalImageData) {
			return this.currentImageData;
		}

		const width = this.originalImageData.width;
		const height = this.originalImageData.height;
		const result = new ImageData(width, height);
		const srcData = this.originalImageData.data;
		const dstData = result.data;

		// 移除步长采样，始终使用1:1采样
		for (let y = 0; y < height; y++) {
			for (let x = 0; x < width; x++) {
				const srcPos = this._mapPointBack(x, y);
				const dstIdx = (y * width + x) * 4;

				if (srcPos.x >= 0 && srcPos.x < width && srcPos.y >= 0 && srcPos.y < height) {
					// 使用双三次插值获取颜色
					const color = this._bicubicInterpolate(srcData, width, height, srcPos.x, srcPos.y);
					dstData[dstIdx] = color[0];
					dstData[dstIdx + 1] = color[1];
					dstData[dstIdx + 2] = color[2];
					dstData[dstIdx + 3] = color[3]; // 确保Alpha通道值被正确设置
				} else {
					// 对于边界外的点，使用最近的有效像素或保持原Alpha通道
					// 这里我们确保Alpha通道不为0，防止出现透明区域
					const nearestX = Math.max(0, Math.min(width - 1, Math.round(srcPos.x)));
					const nearestY = Math.max(0, Math.min(height - 1, Math.round(srcPos.y)));
					const nearestIdx = (nearestY * width + nearestX) * 4;

					// 复制最近像素的颜色，但保持Alpha通道为不透明
					dstData[dstIdx] = srcData[nearestIdx];
					dstData[dstIdx + 1] = srcData[nearestIdx + 1];
					dstData[dstIdx + 2] = srcData[nearestIdx + 2];
					dstData[dstIdx + 3] = 255; // 强制设置为完全不透明
				}
			}
		}

		this.currentImageData = result;
		// 添加锐化处理
		if (this.config.sharpenAmount > 0) {
			this.currentImageData = this._sharpenImage(this.currentImageData, this.config.sharpenAmount);
		}
		return result;
	}

	// 添加异步处理方法用于大图像
	async applyDeformationAsync(x, y) {
		return new Promise((resolve) => {
			setTimeout(() => {
				const result = this.applyDeformation(x, y);
				resolve(result);
			}, 0);
		});
	}

	// 批量处理方法
	applyDeformationBatch(positions) {
		if (!this.initialized || !this.mesh || positions.length === 0) {
			return this.currentImageData;
		}

		// 对于批量处理，模拟连续的拖拽操作
		if (positions.length > 0) {
			// 使用第一个位置作为初始点
			this.startDeformation(positions[0].x, positions[0].y);

			// 逐个应用每个位置的变形
			positions.forEach((pos, index) => {
				if (index === 0) return; // 跳过第一个，因为已经作为初始点

				// 更新当前位置并应用变形
				this.currentMouseX = pos.x;
				this.currentMouseY = pos.y;

				// 重新计算拖拽参数
				const deltaX = this.currentMouseX - this.initialMouseX;
				const deltaY = this.currentMouseY - this.initialMouseY;
				this.dragDistance = Math.sqrt(deltaX * deltaX + deltaY * deltaY);
				this.dragAngle = Math.atan2(deltaY, deltaX);

				const { size, pressure, distortion, power } = this.params;
				const mode = this.currentMode;
				const radius = size * 0.8;

				// 根据推拉模式和拖拽距离动态调整强度
				let strength;
				if (mode === this.modes.PUSH) {
					const baseStrength = (pressure * power * this.config.maxStrength) / 100;
					const distanceFactor = Math.min(this.dragDistance / radius, 2.0);
					strength = baseStrength * distanceFactor * 0.3; // 批量处理时降低强度
				} else {
					strength = (pressure * power * this.config.maxStrength) / 100;
				}

				this._applyDeformation(pos.x, pos.y, radius, strength, mode, distortion);
			});

			// 结束拖拽操作
			this.endDeformation();
		}

		if (this.config.smoothingIterations > 0) {
			this._smoothMesh();
		}

		return this._applyMeshToImage();
	}

	/**
	 * 改进的网格映射算法 - 防止空白区域
	 */
	_mapPointBack(x, y) {
		const { cols, rows, gridSize } = this.mesh;
		const gridX = x / gridSize;
		const gridY = y / gridSize;

		const x1 = Math.floor(gridX);
		const y1 = Math.floor(gridY);
		const x2 = Math.min(x1 + 1, cols);
		const y2 = Math.min(y1 + 1, rows);

		const fx = gridX - x1;
		const fy = gridY - y1;

		// 获取四个网格点的变形和原始坐标
		const deformed = [
			this.mesh.deformedPoints[y1 * (cols + 1) + x1],
			this.mesh.deformedPoints[y1 * (cols + 1) + x2],
			this.mesh.deformedPoints[y2 * (cols + 1) + x1],
			this.mesh.deformedPoints[y2 * (cols + 1) + x2],
		];

		const original = [
			this.mesh.originalPoints[y1 * (cols + 1) + x1],
			this.mesh.originalPoints[y1 * (cols + 1) + x2],
			this.mesh.originalPoints[y2 * (cols + 1) + x1],
			this.mesh.originalPoints[y2 * (cols + 1) + x2],
		];

		// 双线性插值计算变形后的位置
		const deformedX =
			(1 - fx) * (1 - fy) * deformed[0].x +
			fx * (1 - fy) * deformed[1].x +
			(1 - fx) * fy * deformed[2].x +
			fx * fy * deformed[3].x;
		const deformedY =
			(1 - fx) * (1 - fy) * deformed[0].y +
			fx * (1 - fy) * deformed[1].y +
			(1 - fx) * fy * deformed[2].y +
			fx * fy * deformed[3].y;

		// 计算原始网格位置
		const originalX = x1 * gridSize + fx * gridSize;
		const originalY = y1 * gridSize + fy * gridSize;

		// 检查是否接近边缘，如果是则减少偏移量
		const isNearEdge = this._isNearEdge(originalX, originalY);
		const edgeProtectionFactor = isNearEdge ? 0.2 : 1.0; // 边缘区域减少变形量

		// 计算偏移量并应用反向映射
		const offsetX = (deformedX - originalX) * edgeProtectionFactor;
		const offsetY = (deformedY - originalY) * edgeProtectionFactor;

		return {
			x: Math.max(0, Math.min(this.mesh.width - 1, x - offsetX)),
			y: Math.max(0, Math.min(this.mesh.height - 1, y - offsetY)),
		};
	}
	// 边缘检测辅助方法
	_isNearEdge(x, y, threshold = 10) {
		if (!this.originalImageData) return false;

		const data = this.originalImageData.data;
		const width = this.originalImageData.width;
		const height = this.originalImageData.height;

		// 检查像素是否在边缘
		if (x <= 0 || x >= width - 1 || y <= 0 || y >= height - 1) return true;

		// 简单的Sobel边缘检测
		const getPixelBrightness = (px, py) => {
			const idx = (py * width + px) * 4;
			return (data[idx] + data[idx + 1] + data[idx + 2]) / 3;
		};

		const kernelX = [
			[-1, 0, 1],
			[-2, 0, 2],
			[-1, 0, 1]
		];

		const kernelY = [
			[-1, -2, -1],
			[0, 0, 0],
			[1, 2, 1]
		];

		let gradientX = 0;
		let gradientY = 0;

		for (let ky = -1; ky <= 1; ky++) {
			for (let kx = -1; kx <= 1; kx++) {
				const px = Math.min(Math.max(0, x + kx), width - 1);
				const py = Math.min(Math.max(0, y + ky), height - 1);
				const brightness = getPixelBrightness(px, py);
				gradientX += brightness * kernelX[ky + 1][kx + 1];
				gradientY += brightness * kernelY[ky + 1][kx + 1];
			}
		}

		const gradientMagnitude = Math.sqrt(gradientX * gradientX + gradientY * gradientY);
		return gradientMagnitude > threshold;
	}
	// 图像锐化方法
	_sharpenImage(imageData, amount = 0.5) {
		if (!imageData) return imageData;

		const data = new Uint8ClampedArray(imageData.data);
		const width = imageData.width;
		const height = imageData.height;
		const result = new ImageData(width, height);
		const dstData = result.data;

		// 锐化核 - 中心为5，周围为-1
		const kernel = [
			[0, -1, 0],
			[-1, 5, -1],
			[0, -1, 0]
		];

		for (let y = 0; y < height; y++) {
			for (let x = 0; x < width; x++) {
				// 边缘像素不处理
				if (x === 0 || x === width - 1 || y === 0 || y === height - 1) {
					const idx = (y * width + x) * 4;
					for (let c = 0; c < 4; c++) {
						dstData[idx + c] = data[idx + c];
					}
					continue;
				}

				const sharpened = [0, 0, 0, 0];

				// 应用锐化核
				for (let ky = -1; ky <= 1; ky++) {
					for (let kx = -1; kx <= 1; kx++) {
						const px = x + kx;
						const py = y + ky;
						const idx = (py * width + px) * 4;
						const weight = kernel[ky + 1][kx + 1];

						for (let c = 0; c < 3; c++) { // 只锐化RGB通道
							sharpened[c] += data[idx + c] * weight;
						}
						sharpened[3] = data[idx + 3]; // 保持Alpha通道不变
					}
				}

				// 应用锐化强度并裁剪值范围
				const idx = (y * width + x) * 4;
				for (let c = 0; c < 3; c++) {
					const original = data[idx + c];
					const diff = sharpened[c] - original;
					dstData[idx + c] = Math.max(0, Math.min(255, original + diff * amount));
				}
				dstData[idx + 3] = sharpened[3];
			}
		}

		return result;
	}
	_bilinearInterpolate(data, width, height, x, y) {
		const x1 = Math.floor(x);
		const y1 = Math.floor(y);
		const x2 = Math.min(x1 + 1, width - 1);
		const y2 = Math.min(y1 + 1, height - 1);

		const fx = x - x1;
		const fy = y - y1;

		const getPixel = (px, py) => {
			const idx = (py * width + px) * 4;
			return [data[idx], data[idx + 1], data[idx + 2], data[idx + 3]];
		};

		const p1 = getPixel(x1, y1);
		const p2 = getPixel(x2, y1);
		const p3 = getPixel(x1, y2);
		const p4 = getPixel(x2, y2);

		return [
			Math.round(
				(1 - fx) * (1 - fy) * p1[0] +
				fx * (1 - fy) * p2[0] +
				(1 - fx) * fy * p3[0] +
				fx * fy * p4[0]
			),
			Math.round(
				(1 - fx) * (1 - fy) * p1[1] +
				fx * (1 - fy) * p2[1] +
				(1 - fx) * fy * p3[1] +
				fx * fy * p4[1]
			),
			Math.round(
				(1 - fx) * (1 - fy) * p1[2] +
				fx * (1 - fy) * p2[2] +
				(1 - fx) * fy * p3[2] +
				fx * fy * p4[2]
			),
			Math.round(
				(1 - fx) * (1 - fy) * p1[3] +
				fx * (1 - fy) * p2[3] +
				(1 - fx) * fy * p3[3] +
				fx * fy * p4[3]
			),
		];
	}

	reset() {
		if (!this.mesh || !this.originalImageData) return false;

		for (let i = 0; i < this.mesh.deformedPoints.length; i++) {
			this.mesh.deformedPoints[i].x = this.mesh.originalPoints[i].x;
			this.mesh.deformedPoints[i].y = this.mesh.originalPoints[i].y;
		}

		this.currentImageData = new ImageData(
			new Uint8ClampedArray(this.originalImageData.data),
			this.originalImageData.width,
			this.originalImageData.height
		);

		// 重置拖拽状态
		this.initialMouseX = 0;
		this.initialMouseY = 0;
		this.currentMouseX = 0;
		this.currentMouseY = 0;
		this.lastMouseX = 0;
		this.lastMouseY = 0;
		this.mouseMovementX = 0;
		this.mouseMovementY = 0;
		this.isFirstApply = true;
		this.isDragging = false;
		this.dragDistance = 0;
		this.dragAngle = 0;

		// 新增：重置持续按压状态
		this.isHolding = false;
		this.pressStartTime = 0;
		this.pressDuration = 0;
		this.accumulatedRotation = 0;
		this.accumulatedScale = 0;
		this.lastApplyTime = 0;

		this.deformHistory = [];
		return true;
	}

	// 新增：获取持续按压状态信息
	getHoldingInfo() {
		return {
			isHolding: this.isHolding,
			pressDuration: this.pressDuration,
			accumulatedRotation: this.accumulatedRotation,
			accumulatedScale: this.accumulatedScale,
			pressStartTime: this.pressStartTime,
		};
	}

	/**
	 * 应用液化变形 - 主要的公共接口方法
	 * @param {Number} x X坐标
	 * @param {Number} y Y坐标
	 * @returns {ImageData} 变形后的图像数据
	 */
	applyDeformation(x, y) {
		if (!this.initialized || !this.mesh || !this.originalImageData) {
			console.warn("液化管理器未初始化或缺少必要数据");
			return this.currentImageData;
		}

		// 更新鼠标位置
		this.currentMouseX = x;
		this.currentMouseY = y;

		// 计算拖拽参数
		const deltaX = this.currentMouseX - this.initialMouseX;
		const deltaY = this.currentMouseY - this.initialMouseY;
		this.dragDistance = Math.sqrt(deltaX * deltaX + deltaY * deltaY);
		this.dragAngle = Math.atan2(deltaY, deltaX);

		// 获取当前参数
		const { size, pressure, power } = this.params;
		const mode = this.currentMode;
		const radius = size;
		const strength = pressure * power;

		// 根据模式选择算法
		const pixelModes = [
			this.modes.CLOCKWISE,
			this.modes.COUNTERCLOCKWISE,
			this.modes.PINCH,
			this.modes.EXPAND,
			this.modes.PUSH,
		];

		if (pixelModes.includes(mode)) {
			// 使用增强的像素算法
			switch (mode) {
				case this.modes.CLOCKWISE:
					this._applyEnhancedRotationDeformation(x, y, radius, strength, false);
					break;
				case this.modes.COUNTERCLOCKWISE:
					this._applyEnhancedRotationDeformation(x, y, radius, strength, true);
					break;
				case this.modes.PINCH:
					this._applyEnhancedPinchDeformation(x, y, radius, strength, true);
					break;
				case this.modes.EXPAND:
					this._applyEnhancedPinchDeformation(x, y, radius, strength, false);
					break;
				case this.modes.PUSH:
					this._applyEnhancedPushDeformation(x, y, radius, strength);
					break;
			}

			// 更新最后应用时间
			this.lastApplyTime = Date.now();
			this.isFirstApply = false;

			return this.currentImageData;
		} else {
			// 使用原有的网格算法处理其他模式
			if (!this.mesh) {
				console.warn("网格未初始化");
				return this.currentImageData;
			}

			const finalStrength = (strength * this.config.maxStrength) / 100;

			// 应用变形
			this._applyDeformation(x, y, radius, finalStrength, mode, this.params.distortion);

			// 有条件地应用平滑处理，仅在特定模式下应用
			const smoothingModes = [this.modes.CRYSTAL, this.modes.EDGE];
			if (smoothingModes.includes(mode) && this.config.smoothingIterations > 0) {
				this._smoothMesh();
			}

			// 更新图像数据
			const result = this._applyMeshToImage();

			// 更新最后应用时间
			this.lastApplyTime = Date.now();
			this.isFirstApply = false;

			return result;
		}
	}

	getCurrentImageData() {
		return this.currentImageData;
	}

	destroy() {
		// 停止持续效果定时器
		this.stopContinuousEffect();

		this.originalImageData = null;
		this.currentImageData = null;
		this.mesh = null;
		this.deformHistory = [];
		this.initialized = false;

		// 清理拖拽状态
		this.initialMouseX = 0;
		this.initialMouseY = 0;
		this.currentMouseX = 0;
		this.currentMouseY = 0;
		this.lastMouseX = 0;
		this.lastMouseY = 0;
		this.mouseMovementX = 0;
		this.mouseMovementY = 0;
		this.isFirstApply = true;
		this.isDragging = false;
		this.dragDistance = 0;
		this.dragAngle = 0;

		// 新增：清理持续按压状态
		this.isHolding = false;
		this.pressStartTime = 0;
		this.pressDuration = 0;
		this.accumulatedRotation = 0;
		this.accumulatedScale = 0;
		this.lastApplyTime = 0;
	}

	/**
	 * 释放资源 - 别名方法，与其他管理器保持一致
	 */
	dispose() {
		this.destroy();
	}
}
