574 lines
14 KiB
JavaScript
574 lines
14 KiB
JavaScript
import { register as registerFlow } from '@topology/flow-diagram'
|
|
import { register as registerActivity } from '@topology/activity-diagram'
|
|
import { register as registerSequence } from '@topology/sequence-diagram'
|
|
import { register as registerChart } from '@topology/chart-diagram'
|
|
import { Node, Rect, Point, Direction } from '@topology/core'
|
|
// import { register as registerClass } from './class-diagram/index'
|
|
export let canvas
|
|
|
|
export function canvasRegister () {
|
|
registerFlow()
|
|
registerActivity()
|
|
registerSequence()
|
|
registerChart()
|
|
// registerClass()
|
|
}
|
|
|
|
export const Tools = [
|
|
{
|
|
group: 'General',
|
|
children: [
|
|
// {
|
|
// name: 'rectangle',
|
|
// icon: 'icon-rect',
|
|
// data: {
|
|
// text: 'rect',
|
|
// rect: {
|
|
// width: 100,
|
|
// height: 100
|
|
// },
|
|
// paddingLeft: 10,
|
|
// paddingRight: 10,
|
|
// paddingTop: 10,
|
|
// paddingBottom: 10,
|
|
// name: 'rectangleImg',
|
|
// icon: '\ue680',
|
|
// iconFamily: 'nz-icon',
|
|
// iconColor: ''
|
|
// }
|
|
// },
|
|
{
|
|
name: 'rectangle',
|
|
icon: 'icon-cube',
|
|
data: {
|
|
rect: {
|
|
width: 100,
|
|
height: 100
|
|
},
|
|
is3D: true,
|
|
z: 20,
|
|
zRotate: 15,
|
|
name: 'myCube',
|
|
iconFamily: 'topology',
|
|
iconColor: '#777',
|
|
iconSize: 30
|
|
}
|
|
},
|
|
{
|
|
name: 'rectangle',
|
|
icon: 'icon-rect',
|
|
data: {
|
|
text: 'rect',
|
|
rect: {
|
|
width: 100,
|
|
height: 100
|
|
},
|
|
paddingLeft: 10,
|
|
paddingRight: 10,
|
|
paddingTop: 10,
|
|
paddingBottom: 10,
|
|
name: 'rectangle'
|
|
}
|
|
},
|
|
{
|
|
name: 'rectangle',
|
|
icon: 'icon-rectangle',
|
|
data: {
|
|
text: 'rectangle',
|
|
rect: {
|
|
width: 200,
|
|
height: 50
|
|
},
|
|
paddingLeft: 10,
|
|
paddingRight: 10,
|
|
paddingTop: 10,
|
|
paddingBottom: 10,
|
|
borderRadius: 0.1,
|
|
name: 'rectangle'
|
|
// icon: '\ue680',
|
|
// iconFamily: 'nz-icon',
|
|
// iconColor: ''
|
|
}
|
|
},
|
|
{
|
|
name: 'circle',
|
|
icon: 'icon-circle',
|
|
data: {
|
|
text: 'circle',
|
|
rect: {
|
|
width: 100,
|
|
height: 100
|
|
},
|
|
name: 'circle',
|
|
textMaxLine: 1
|
|
}
|
|
},
|
|
{
|
|
name: 'triangle',
|
|
icon: 'icon-triangle',
|
|
data: {
|
|
text: 'triangle',
|
|
rect: {
|
|
width: 100,
|
|
height: 100
|
|
},
|
|
name: 'triangle'
|
|
}
|
|
},
|
|
{
|
|
name: 'diamond',
|
|
icon: 'icon-diamond',
|
|
data: {
|
|
text: 'diamond',
|
|
rect: {
|
|
width: 100,
|
|
height: 100
|
|
},
|
|
name: 'diamond'
|
|
}
|
|
},
|
|
{
|
|
name: 'pentagon',
|
|
icon: 'icon-pentagon',
|
|
data: {
|
|
text: 'pentagon',
|
|
rect: {
|
|
width: 100,
|
|
height: 100
|
|
},
|
|
name: 'pentagon'
|
|
}
|
|
},
|
|
{
|
|
name: 'hexagon',
|
|
icon: 'icon-hexagon',
|
|
data: {
|
|
text: 'hexagon',
|
|
rect: {
|
|
width: 100,
|
|
height: 100
|
|
},
|
|
paddingTop: 10,
|
|
paddingBottom: 10,
|
|
name: 'hexagon'
|
|
}
|
|
},
|
|
{
|
|
name: 'pentagram',
|
|
icon: 'icon-pentagram',
|
|
data: {
|
|
text: 'pentagram',
|
|
rect: {
|
|
width: 100,
|
|
height: 100
|
|
},
|
|
name: 'pentagram'
|
|
}
|
|
}
|
|
]
|
|
}
|
|
]
|
|
|
|
export const imageTemp = {
|
|
name: 'rectangleImg',
|
|
icon: 'icon-image',
|
|
data: {
|
|
type: 0,
|
|
rect: {
|
|
x: 922,
|
|
y: 406,
|
|
width: 100,
|
|
height: 100
|
|
},
|
|
imageRatio: true,
|
|
lineWidth: 0,
|
|
rotate: 0,
|
|
offsetRotate: 0,
|
|
globalAlpha: 1,
|
|
dash: 0,
|
|
strokeStyle: '#000000',
|
|
animatePos: 0,
|
|
name: 'rectangleImg',
|
|
lineDashOffset: 0,
|
|
text: '',
|
|
textOffsetX: 0,
|
|
textOffsetY: 0,
|
|
visible: true,
|
|
zRotate: 0,
|
|
animateDuration: 0,
|
|
animateFrames: [],
|
|
animateFrame: 0,
|
|
borderRadius: 0,
|
|
icon: '',
|
|
image: '',
|
|
imageAlign: 'center',
|
|
bkType: 0,
|
|
gradientAngle: 0,
|
|
gradientRadius: 0.01,
|
|
paddingTop: 5,
|
|
paddingBottom: 5,
|
|
paddingLeft: 5,
|
|
paddingRight: 5,
|
|
paddingLeftNum: 5,
|
|
paddingRightNum: 5,
|
|
paddingTopNum: 5,
|
|
paddingBottomNum: 5,
|
|
fullIconRect: { width: 80, height: 90, center: { x: 972, y: 456 }, ex: 1012, ey: 496 }
|
|
}
|
|
}
|
|
/* 自定义图片组件 */
|
|
export function myShape (ctx, node) { // 自定义图片组件
|
|
ctx.beginPath()
|
|
|
|
ctx.rect(node.rect.x, node.rect.y, node.rect.width, node.rect.height)
|
|
if (node.data && node.data.lineWidth <= 0) {
|
|
ctx.strokeStyle = 'rgba(0,0,0,0)'
|
|
}
|
|
// 必须判空再填充
|
|
(node.fillStyle || node.bkType) && ctx.fill()
|
|
ctx.stroke()
|
|
}
|
|
export function myAnchors (node) {
|
|
node.anchors.push(new Point(node.rect.x, node.rect.y + node.rect.height / 2, Direction.Left))
|
|
node.anchors.push(new Point(node.rect.x + node.rect.width / 2, node.rect.y, Direction.Up))
|
|
node.anchors.push(new Point(node.rect.x + node.rect.width, node.rect.y + node.rect.height / 2, Direction.Right))
|
|
node.anchors.push(new Point(node.rect.x + node.rect.width / 2, node.rect.y + node.rect.height, Direction.Bottom))
|
|
}
|
|
export function myIconRect (node) {
|
|
node.iconRect = new Rect(node.rect.x + node.paddingLeft, node.rect.y + node.paddingTop, node.rect.width - (node.paddingLeft + node.paddingRight), node.rect.height - 20 - (node.paddingTop + node.paddingBottom))
|
|
node.fullIconRect = node.rect
|
|
}
|
|
export function myTextRect (node) {
|
|
node.textRect = new Rect(
|
|
node.rect.x + node.paddingLeft,
|
|
node.rect.y + node.rect.height - 20 - node.paddingBottom,
|
|
node.rect.width - (node.paddingLeft + node.paddingRight),
|
|
20
|
|
)
|
|
node.fullTextRect = node.rect
|
|
}
|
|
/* 自定义图片组件 */
|
|
|
|
/* 自定义立方体 */
|
|
export function myCubec (ctx, node) {
|
|
// 立方体
|
|
// ctx.rect(node.rect.x,node.rect.y,node.rect.width,node.rect.height);
|
|
const x = node.rect.x + 10; const y = node.rect.y + 10; const w = node.rect.width - 20; const h = node.rect.height - 20
|
|
|
|
// LINE MODE
|
|
ctx.lineJoin = 'round'
|
|
|
|
// center face
|
|
ctx.beginPath()
|
|
ctx.moveTo(x, y + h / 3)
|
|
ctx.lineTo(x + w * 2 / 3, y + h / 3)
|
|
ctx.lineTo(x + w * 2 / 3, y + h)
|
|
ctx.lineTo(x, y + h)
|
|
ctx.closePath()
|
|
ctx.fillStyle = node.fillStyle
|
|
ctx.strokeStyle = node.strokeStyle
|
|
ctx.stroke();
|
|
(node.fillStyle || node.bkType) && ctx.fill()
|
|
|
|
// top face
|
|
ctx.beginPath()
|
|
ctx.moveTo(x, y + h / 3)
|
|
ctx.lineTo(x + w / 3, y)
|
|
ctx.lineTo(x + w, y)
|
|
ctx.lineTo(x + w * 2 / 3, y + h / 3)
|
|
ctx.closePath()
|
|
ctx.fillStyle = node.fillStyle
|
|
ctx.strokeStyle = node.strokeStyle
|
|
ctx.stroke();
|
|
(node.fillStyle || node.bkType) && ctx.fill()
|
|
|
|
// right face
|
|
ctx.beginPath()
|
|
ctx.moveTo(x + w * 2 / 3, y + h / 3)
|
|
ctx.lineTo(x + w, y)
|
|
ctx.lineTo(x + w, y + h * 2 / 3)
|
|
ctx.lineTo(x + w * 2 / 3, y + h)
|
|
ctx.closePath()
|
|
ctx.fillStyle = node.fillStyle
|
|
ctx.strokeStyle = node.strokeStyle
|
|
ctx.stroke();
|
|
(node.fillStyle || node.bkType) && ctx.fill()
|
|
|
|
// 必须判空再填充
|
|
}
|
|
export function myCubeAnchors (node) { // 立方体锚点
|
|
node.anchors.push(new Point(node.rect.x, node.rect.y + node.rect.height / 2, Direction.Left))
|
|
node.anchors.push(new Point(node.rect.x + node.rect.width / 2, node.rect.y, Direction.Up))
|
|
node.anchors.push(new Point(node.rect.x + node.rect.width, node.rect.y + node.rect.height / 2, Direction.Right))
|
|
node.anchors.push(new Point(node.rect.x + node.rect.width / 2, node.rect.y + node.rect.height, Direction.Bottom))
|
|
}
|
|
/* 自定义立方体 */
|
|
|
|
export function onChangeAnimate (node, animateType, fillStyle, strokeStyle) {
|
|
node.animateType = animateType
|
|
if (node.animateType === 'custom') {
|
|
return
|
|
}
|
|
|
|
node.animateFrames = []
|
|
const state = Node.cloneState(node)
|
|
switch (animateType) {
|
|
case 'upDown':
|
|
state.rect.y -= 10
|
|
state.rect.ey -= 10
|
|
node.animateFrames.push({
|
|
duration: 100,
|
|
linear: true,
|
|
state
|
|
})
|
|
node.animateFrames.push({
|
|
duration: 100,
|
|
linear: true,
|
|
state: Node.cloneState(node)
|
|
})
|
|
node.animateFrames.push({
|
|
duration: 200,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
break
|
|
case 'leftRight':
|
|
state.rect.x -= 10
|
|
state.rect.ex -= 10
|
|
node.animateFrames.push({
|
|
duration: 100,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
state.rect.x += 20
|
|
state.rect.ex += 20
|
|
node.animateFrames.push({
|
|
duration: 80,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
state.rect.x -= 20
|
|
state.rect.ex -= 20
|
|
node.animateFrames.push({
|
|
duration: 50,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
state.rect.x += 20
|
|
state.rect.ex += 20
|
|
node.animateFrames.push({
|
|
duration: 30,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
node.animateFrames.push({
|
|
duration: 300,
|
|
linear: true,
|
|
state: Node.cloneState(node)
|
|
})
|
|
break
|
|
case 'heart':
|
|
state.rect.x -= 5
|
|
state.rect.ex += 5
|
|
state.rect.y -= 5
|
|
state.rect.ey += 5
|
|
state.rect.width += 5
|
|
state.rect.height += 10
|
|
node.animateFrames.push({
|
|
duration: 100,
|
|
linear: true,
|
|
state
|
|
})
|
|
node.animateFrames.push({
|
|
duration: 400,
|
|
linear: true,
|
|
state: Node.cloneState(node)
|
|
})
|
|
break
|
|
case 'success':
|
|
state.strokeStyle = strokeStyle || '#237804'
|
|
node.animateFrames.push({
|
|
duration: 100,
|
|
linear: true,
|
|
state
|
|
})
|
|
node.animateFrames.push({
|
|
duration: 100,
|
|
linear: true,
|
|
state: Node.cloneState(node)
|
|
})
|
|
state.strokeStyle = '#237804'
|
|
node.animateFrames.push({
|
|
duration: 100,
|
|
linear: true,
|
|
state
|
|
})
|
|
node.animateFrames.push({
|
|
duration: 100,
|
|
linear: true,
|
|
state: Node.cloneState(node)
|
|
})
|
|
state.strokeStyle = strokeStyle || '#237804'
|
|
state.fillStyle = fillStyle || '#389e0d22'
|
|
node.animateFrames.push({
|
|
duration: 3000,
|
|
linear: true,
|
|
state
|
|
})
|
|
break
|
|
case 'warning':
|
|
state.strokeStyle = strokeStyle || '#fa8c16'
|
|
state.fillStyle = fillStyle || '#fa8c16'
|
|
state.lineWidth = 5
|
|
state.dash = 2
|
|
node.animateFrames.push({
|
|
duration: 500,
|
|
linear: true,
|
|
state
|
|
})
|
|
state.strokeStyle = strokeStyle || '#fa8c16'
|
|
state.dash = 0
|
|
state.lineWidth = 1
|
|
state.fillStyle = '#ffffff'
|
|
node.animateFrames.push({
|
|
duration: 500,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
state.strokeStyle = strokeStyle || '#fa8c16'
|
|
state.dash = 2
|
|
state.lineWidth = 5
|
|
state.fillStyle = fillStyle || '#fa8c16'
|
|
node.animateFrames.push({
|
|
duration: 300,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
break
|
|
case 'error':
|
|
state.strokeStyle = strokeStyle || '#cf1322'
|
|
state.fillStyle = fillStyle || '#cf132222'
|
|
state.lineWidth = 5
|
|
state.dash = 2
|
|
node.animateFrames.push({
|
|
duration: 100,
|
|
linear: true,
|
|
state
|
|
})
|
|
state.strokeStyle = strokeStyle || '#cf1322'
|
|
state.fillStyle = '#ffffff'
|
|
state.dash = 0
|
|
state.lineWidth = 1
|
|
node.animateFrames.push({
|
|
duration: 500,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
state.strokeStyle = strokeStyle || '#cf1322'
|
|
state.fillStyle = fillStyle || '#cf132222'
|
|
state.dash = 2
|
|
state.lineWidth = 5
|
|
node.animateFrames.push({
|
|
duration: 300,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
break
|
|
case 'show':
|
|
state.strokeStyle = strokeStyle || '#fa541c'
|
|
state.rotate = -5
|
|
node.animateFrames.push({
|
|
duration: 100,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
state.rotate = 5
|
|
node.animateFrames.push({
|
|
duration: 100,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
state.rotate = 0
|
|
node.animateFrames.push({
|
|
duration: 100,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
break
|
|
case 'fade':
|
|
state.strokeStyle = strokeStyle || '#fa541c'
|
|
state.globalAlpha = 0.3
|
|
node.animateFrames.push({
|
|
duration: 300,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
state.globalAlpha = 0.5
|
|
node.animateFrames.push({
|
|
duration: 300,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
state.globalAlpha = 0.8
|
|
node.animateFrames.push({
|
|
duration: 300,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
state.globalAlpha = 1
|
|
node.animateFrames.push({
|
|
duration: 300,
|
|
linear: true,
|
|
state: Node.cloneState(state)
|
|
})
|
|
break
|
|
}
|
|
node.animatePlay = true
|
|
}
|
|
export function onChangeAnimateLine (line, type) {
|
|
line.animateType = type
|
|
line.animatePlay = true
|
|
}
|
|
export function changeImage (dataImg, callback) {
|
|
// const base64Img = document.createElement('base64Img')
|
|
const canvas = document.createElement('canvas')
|
|
const context = canvas.getContext('2d')
|
|
// 创建新图片
|
|
const img = new Image()
|
|
img.src = dataImg
|
|
img.addEventListener(
|
|
'load',
|
|
function () {
|
|
// 绘制图片到canvas上
|
|
canvas.width = img.width
|
|
canvas.height = img.height
|
|
context.drawImage(img, 0, 0)
|
|
|
|
// 将canvas的透明背景设置成白色
|
|
const imageData = context.getImageData(
|
|
0,
|
|
0,
|
|
canvas.width,
|
|
canvas.height
|
|
)
|
|
for (let i = 0; i < imageData.data.length; i += 4) {
|
|
// rgb大于250的透明度y均设置成0
|
|
if (
|
|
imageData.data[i] > 0 &&
|
|
imageData.data[i + 1] > 0 &&
|
|
imageData.data[i + 2] > 0
|
|
) {
|
|
imageData.data[i + 3] = 200
|
|
}
|
|
}
|
|
context.putImageData(imageData, 0, 0)
|
|
const baseImg = canvas.toDataURL('image/png')// 返回base64
|
|
if (typeof callback !== 'undefined') {
|
|
if (callback) callback(baseImg)
|
|
}
|
|
img.remove()
|
|
},
|
|
false
|
|
)
|
|
}
|