diff --git a/frontend/src/views/Editor.vue b/frontend/src/views/Editor.vue
index 238fd07..67edd5e 100644
--- a/frontend/src/views/Editor.vue
+++ b/frontend/src/views/Editor.vue
@@ -35,6 +35,27 @@
:style="{ border: 'none', background: 'transparent', color: l.zIndex >= layers.length - 1 ? '#333' : '#888', cursor: l.zIndex >= layers.length - 1 ? 'default' : 'pointer', fontSize: '10px', padding: '0' }">▼
+
+
属性编辑
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ 选中画布上的对象查看属性
+
@@ -86,12 +107,44 @@ const currentCards = computed(() => {
})
const layers = ref([
- { id: 'bg', name: '背景层', visible: true, zIndex: 0 },
- { id: 'border', name: '边框层', visible: true, zIndex: 1 },
+ { id: 'bg', name: '背景层', visible: true, zIndex: 0, fillColor: '#ffffff' },
+ { id: 'border', name: '边框层', visible: true, zIndex: 1, strokeColor: '#333333', strokeWidth: 2 },
{ id: 'pattern', name: '图案层', visible: true, zIndex: 2 },
- { id: 'text', name: '文字层', visible: true, zIndex: 3 }
+ { id: 'text', name: '文字层', visible: true, zIndex: 3, textSize: 32 }
])
+const bgColor = ref('#ffffff')
+const borderColor = ref('#333333')
+const borderWidth = ref(2)
+const textSize = ref(32)
+
+function updateBgColor() {
+ const l = layers.value.find(x => x.id === 'bg')
+ if (l) l.fillColor = bgColor.value
+}
+
+function applyBgColor() {
+ updateBgColor()
+ drawCard()
+}
+
+function applyBorder() {
+ const l = layers.value.find(x => x.id === 'border')
+ if (l) { l.strokeColor = borderColor.value; l.strokeWidth = parseInt(borderWidth.value) }
+ drawCard()
+}
+
+function updateBorderColor() {
+ const l = layers.value.find(x => x.id === 'border')
+ if (l) l.strokeColor = borderColor.value
+}
+
+function applyTextStyle() {
+ const l = layers.value.find(x => x.id === 'text')
+ if (l) l.textSize = parseInt(textSize.value)
+ drawCard()
+}
+
function getSymbol(suit) {
return { spade: '♠', heart: '♥', club: '♣', diamond: '♦' }[suit] || ''
}
@@ -135,8 +188,24 @@ function initCanvas() {
fabricCanvas.value = new Canvas('main-canvas', {
width: 400,
height: 560,
- backgroundColor: '#f5f5f5'
+ backgroundColor: '#f5f5f5',
+ selection: true
})
+
+ fabricCanvas.value.on('selection:created', (e) => {
+ const obj = e.selected[0]
+ if (obj && obj.layerId) {
+ activeLayer.value = obj.layerId
+ }
+ })
+
+ fabricCanvas.value.on('selection:updated', (e) => {
+ const obj = e.selected[0]
+ if (obj && obj.layerId) {
+ activeLayer.value = obj.layerId
+ }
+ })
+
drawCard()
}
@@ -158,31 +227,37 @@ function drawCard() {
if (!layer.visible) continue
if (layer.id === 'bg') {
- const bg = new Rect({ left: 0, top: 0, width: cardW, height: cardH, fill: '#ffffff', selectable: false })
+ const bg = new Rect({ left: 0, top: 0, width: cardW, height: cardH, fill: layer.fillColor || '#ffffff', selectable: true, hasControls: false, lockMovementX: true, lockMovementY: true, stroke: 'transparent', strokeWidth: 0 })
+ bg.layerId = 'bg'
c.add(bg)
}
if (layer.id === 'border') {
- const frame = new Rect({ left: 10, top: 10, width: cardW - 20, height: cardH - 20, fill: 'transparent', stroke: '#333', strokeWidth: 2, selectable: false })
+ const frame = new Rect({ left: 10, top: 10, width: cardW - 20, height: cardH - 20, fill: 'transparent', stroke: layer.strokeColor || '#333', strokeWidth: layer.strokeWidth || 2, selectable: true, hasControls: false, lockMovementX: true, lockMovementY: true })
+ frame.layerId = 'border'
c.add(frame)
}
if (layer.id === 'pattern') {
const center = new FabricText(sym, {
- left: cardW / 2, top: cardH / 2, fontSize: 80, fill: color, selectable: true, originX: 'center', originY: 'center'
+ left: cardW / 2, top: cardH / 2, fontSize: 80, fill: color, selectable: true, hasControls: false, lockMovementX: true, lockMovementY: true, originX: 'center', originY: 'center'
})
+ center.layerId = 'pattern'
c.add(center)
}
if (layer.id === 'text') {
+ const ts = layer.textSize || 32
const topLabel = new FabricText(`${rank}${sym}`, {
- left: 18, top: 16, fontSize: 32, fill: color, selectable: true
+ left: 18, top: 16, fontSize: ts, fill: color, selectable: true, hasControls: false, lockMovementX: true, lockMovementY: true
})
+ topLabel.layerId = 'text'
c.add(topLabel)
const bottomLabel = new FabricText(`${sym}${rank}`, {
- left: cardW - 18, top: cardH - 16, fontSize: 32, fill: color, selectable: true, originX: 'right', originY: 'bottom'
+ left: cardW - 18, top: cardH - 16, fontSize: ts, fill: color, selectable: true, hasControls: false, lockMovementX: true, lockMovementY: true, originX: 'right', originY: 'bottom'
})
+ bottomLabel.layerId = 'text'
c.add(bottomLabel)
}
}