有时候我们先在画布上画一个表格类似一下设计软件那种。一方面作为参考线,一方面给人一直专业的赶脚。。。
先贴上一段网上(不是我写的)可以运行的代码 https://codepen.io/rodan8888/pen/eBWNdp
通过这个代码提供了我们一个思路,即横着画完,竖着画,每个五行变个色。但是实际应用中我们不可能这么简单的就能完成,考虑到画布的大小是不规则的,画布的zoom是变化的,如何根据后续其他画布刷新grid,清空grid还需要一些操作。
// 首先根据画布的大小计算分十大个格子,
let dis = state.pannelW / 50
let oneDis = dis * 5
// 要让grid不可以选中selectable,不可以有事件触发evented,不可以输出excludeFromExport
let options = {
distance: dis,
width: state.canvas.width / state.zoom + oneDis,
height: state.canvas.height / state.zoom + oneDis,
param: {
stroke: '#ebebeb',
strokeWidth: 1,
hoverCursor: 'default',
selectable: false,
evented: false,
excludeFromExport: true,
hasControls: false,
perPixelTargetFind: false,
}
}
let gridLen = options.width / options.distance;
let lines = [];
for (let i = 0; i < gridLen; i++) {
let distance = i * options.distance,
horizontal = new fabric.Line([distance, 0, distance, options.width], options.param),
vertical = new fabric.Line([0, distance, options.width, distance], options.param);
if (i % 5 === 0) {
horizontal.set({
stroke: '#cccccc'
});
vertical.set({
stroke: '#cccccc'
});
}
lines.push(horizontal)
lines.push(vertical)
}
let _left = state.arrX[0] > oneDis ?
state.arrX[0] % oneDis - oneDis : state.arrX[0] - oneDis
let _top = state.arrY[0] > oneDis ?
state.arrY[0] % oneDis - oneDis : state.arrY[0] - oneDis
//定义好之后放到一个group里面
state.groupLines = new fabric.Group(lines, {
selectable: false,
lockMovementX: true,
lockMovementY: true,
lockRotation: true,
lockScalingX: true,
lockScalingY: true,
lockUniScaling: true,
hoverCursor: 'auto',
name: 'grid',
left: _left,
top: _top,
evented: false,
});
state.canvas.add(state.groupLines);
state.canvas.sendToBack(state.groupLines);
这个地方我定义了一个group放在操作的树(或者全局变量)中,这样其他地方可以对grid进行操作。比如zoom的时候直接remove掉重新绘制。
最后补充一个小功能吧,自动对齐,在一些简单严格的设计需求中,可能需要自动对齐表格参考线。紧接着上面的代码,添加一个move和modified的事件监听。
let onLeft = dis - state.arrX[0] % dis
let onTop = dis - state.arrY[0] % dis
state.canvas.off('object:moved')
state.canvas.off('object:modified')
state.canvas.on('object:moved', function(options) {
options.target.set({
left: Math.round(options.target.left / dis) * dis - onLeft + dis,
top: Math.round(options.target.top / dis) * dis - onTop + dis
});
options.target.setCoords();
});
state.canvas.on('object:modified', function(options) {
let newWidth = (Math.round(options.target.getScaledWidth() / dis)) * dis;
let newHeight = (Math.round(options.target.getScaledHeight() / dis)) * dis;
options.target.set({
left: Math.round(options.target.left / dis) * dis - onLeft + dis,
top: Math.round(options.target.top / dis) * dis - onTop + dis,
width: newWidth,
height: newHeight,
scaleX: 1,
scaleY: 1
});
options.target.setCoords();
});
到此表格就完成了。