画布增加的新功能
This commit is contained in:
@@ -10,6 +10,7 @@ import { AddObjectToLayerCommand } from "./ObjectLayerCommands";
|
||||
import { ToolCommand } from "./ToolCommands";
|
||||
import {
|
||||
findObjectById,
|
||||
findObjectByLayerId,
|
||||
generateId,
|
||||
getObjectZIndex,
|
||||
insertObjectAtZIndex,
|
||||
@@ -19,7 +20,7 @@ import {
|
||||
} from "../utils/helper";
|
||||
import { fabric } from "fabric-with-all";
|
||||
import { restoreFabricObject } from "../utils/objectHelper";
|
||||
|
||||
import EventManager from "../utils/event.js";
|
||||
/**
|
||||
* 添加图层命令
|
||||
*/
|
||||
@@ -36,7 +37,7 @@ export class AddLayerCommand extends Command {
|
||||
|
||||
this.insertIndex = options.insertIndex;
|
||||
this.oldActiveLayerId = null;
|
||||
this.beforeLayers = [...this.layers.value]; // 备份原图层列表
|
||||
this.beforeLayers = JSON.stringify(this.layers.value); // 备份原图层列表
|
||||
|
||||
this.options = options.options || {};
|
||||
}
|
||||
@@ -70,7 +71,7 @@ export class AddLayerCommand extends Command {
|
||||
|
||||
undo() {
|
||||
// 从图层列表删除该图层
|
||||
this.layers.value = [...this.beforeLayers];
|
||||
this.layers.value = JSON.parse(this.beforeLayers);
|
||||
|
||||
// 恢复原活动图层
|
||||
this.activeLayerId.value = this.oldActiveLayerId;
|
||||
@@ -251,12 +252,12 @@ export class PasteLayerCommand extends Command {
|
||||
(await restoreFabricObject(groupLayer?.clippingMask, this.canvas)) ||
|
||||
null;
|
||||
|
||||
clippingMaskFabricObject.clipPath = null;
|
||||
// clippingMaskFabricObject.clipPath = null;
|
||||
clippingMaskFabricObject.set({
|
||||
absolutePositioned: true,
|
||||
});
|
||||
|
||||
clippingMaskFabricObject.dirty = true;
|
||||
// clippingMaskFabricObject.dirty = true;
|
||||
clippingMaskFabricObject.setCoords();
|
||||
// 添加所有对象到画布
|
||||
allObjects.forEach((obj) => {
|
||||
@@ -802,15 +803,23 @@ export class ToggleLayerVisibilityCommand extends Command {
|
||||
|
||||
// 切换可见性
|
||||
this.layer.visible = !this.layer.visible;
|
||||
const ids = [this.layerId];
|
||||
const childLayers = this.layer?.children || [];
|
||||
childLayers.forEach((childLayer) => {
|
||||
childLayer.visible = this.layer.visible;
|
||||
ids.push(childLayer.id);
|
||||
});
|
||||
|
||||
// 更新画布上图层对象的可见性
|
||||
if (this.canvas) {
|
||||
const layerObjects = this.canvas
|
||||
.getObjects()
|
||||
.filter((obj) => obj.layerId === this.layerId);
|
||||
layerObjects.forEach((obj) => {
|
||||
obj.visible = this.layer.visible;
|
||||
});
|
||||
this.canvas.getObjects().forEach((obj) => {
|
||||
if (ids.includes(obj.layerId)) {
|
||||
obj.getObjects?.()?.forEach((item) => {
|
||||
item.visible = this.layer.visible;
|
||||
});
|
||||
obj.visible = this.layer.visible;
|
||||
}
|
||||
});
|
||||
}
|
||||
// 更新画布上对象的可选择状态
|
||||
await this.layerManager?.updateLayersObjectsInteractivity();
|
||||
@@ -868,13 +877,14 @@ export class ToggleChildLayerVisibilityCommand extends Command {
|
||||
|
||||
// 更新画布上图层对象的可见性
|
||||
if (this.canvas) {
|
||||
const layerObjects = this.canvas
|
||||
.getObjects()
|
||||
.filter((obj) => obj.layerId === this.layerId);
|
||||
|
||||
layerObjects.forEach((obj) => {
|
||||
obj.visible = this.childLayer.visible;
|
||||
});
|
||||
this.canvas.getObjects().forEach((obj) => {
|
||||
if (obj.layerId === this.layerId) {
|
||||
obj.getObjects?.()?.forEach((item) => {
|
||||
item.visible = this.childLayer.visible;
|
||||
});
|
||||
obj.visible = this.childLayer.visible;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
// 更新画布上对象的可选择状态
|
||||
@@ -1007,9 +1017,8 @@ export class LayerLockCommand extends Command {
|
||||
|
||||
// 如果是组图层,递归更新所有子图层
|
||||
if (
|
||||
layer.type === "group" &&
|
||||
layer.children &&
|
||||
Array.isArray(layer.children)
|
||||
Array.isArray(layer.children) && layer.children.length > 0
|
||||
) {
|
||||
layer.children.forEach((child) => {
|
||||
this._updateLayerLockState(child, locked);
|
||||
@@ -1108,7 +1117,7 @@ export class SetLayerOpacityCommand extends Command {
|
||||
|
||||
this.canvas.renderAll();
|
||||
}
|
||||
|
||||
EventManager.emit("object:opacity:execute", this.layerId, this.opacity);
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -1130,6 +1139,7 @@ export class SetLayerOpacityCommand extends Command {
|
||||
this.canvas.renderAll();
|
||||
}
|
||||
}
|
||||
EventManager.emit("object:opacity:undo", this.layerId, this.opacity);
|
||||
}
|
||||
|
||||
getInfo() {
|
||||
@@ -1371,7 +1381,7 @@ export class GroupLayersCommand extends Command {
|
||||
// 备份原图层
|
||||
this.originalLayers = [...this.layers.value];
|
||||
// 新组ID
|
||||
this.groupId =
|
||||
this.groupId = options.id ||
|
||||
generateId("group_layer_") ||
|
||||
`group_layer_${Date.now()}_${Math.floor(Math.random() * 1000)}`;
|
||||
|
||||
@@ -4434,3 +4444,87 @@ export class ChildLayerLockCommand extends Command {
|
||||
};
|
||||
}
|
||||
}
|
||||
/**
|
||||
* 设置图层混合模式
|
||||
*/
|
||||
export class SetLayerCompositeCommand extends Command {
|
||||
constructor(options) {
|
||||
super({
|
||||
name: "设置图层混合模式",
|
||||
saveState: false,
|
||||
});
|
||||
this.canvas = options.canvas;
|
||||
this.layers = options.layers;
|
||||
this.layerManager = options.layerManager;
|
||||
this.layerId = options.layerId;
|
||||
this.newValue = options.newValue;
|
||||
this.oldValue = options.oldValue;
|
||||
}
|
||||
|
||||
execute(isUndo = false) {
|
||||
const { layer } = findLayerRecursively(this.layers.value, this.layerId);
|
||||
const { object } = findObjectByLayerId(this.canvas, this.layerId);
|
||||
if (!layer || !object) {
|
||||
console.error(`图层${this.layerId}不存在`);
|
||||
return false;
|
||||
}
|
||||
// console.log("==========", this.newValue, this.oldValue);
|
||||
const value = isUndo ? this.oldValue : this.newValue;
|
||||
layer.blendMode = value;
|
||||
object.set("globalCompositeOperation", value);
|
||||
this.canvas.renderAll();
|
||||
const event = isUndo ? "object:composite:undo" : "object:composite:execute";
|
||||
EventManager.emit(event, object);
|
||||
return true;
|
||||
}
|
||||
|
||||
undo() {
|
||||
return this.execute(true);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* 设置颜色图层颜色
|
||||
*/
|
||||
export class SetColorLayerFillCommand extends Command {
|
||||
constructor(options) {
|
||||
super({
|
||||
name: "设置颜色图层颜色",
|
||||
saveState: false,
|
||||
});
|
||||
this.canvas = options.canvas;
|
||||
this.layerManager = options.layerManager;
|
||||
this.object = options.object;
|
||||
this.layer = this.layerManager?.getLayerById(this.object.layerId);
|
||||
this.newFill = options.newFill;
|
||||
this.oldFill = JSON.parse(JSON.stringify(this.object.fill));
|
||||
}
|
||||
|
||||
async execute(isUndo = false) {
|
||||
if (!this.object) {
|
||||
console.error(`颜色图层不存在`);
|
||||
return false;
|
||||
}
|
||||
const isVisible = this.layer?.visible;
|
||||
if(!isVisible && this.layer) this.layer.visible = true;
|
||||
const gradient = new fabric.Gradient({
|
||||
type: "linear",
|
||||
gradientUnits: "percentage",
|
||||
...(isUndo ? this.oldFill : this.newFill),
|
||||
});
|
||||
this.object.setFill(gradient);
|
||||
this.canvas.renderAll();
|
||||
await this.canvas?.thumbnailManager?.generateLayerThumbnail?.(
|
||||
this.object.id
|
||||
);
|
||||
if(!isVisible && this.layer) this.layer.visible = false;
|
||||
this.layerManager?.updateLayersObjectsInteractivity();
|
||||
return true;
|
||||
}
|
||||
|
||||
undo() {
|
||||
this.execute(true);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user