import { useVueFlow } from '@vue-flow/core'; import { ref, watch } from 'vue'; import { v4 as uuidv4 } from 'uuid'; const getId = (type) => { return `${type}_${uuidv4().replaceAll('-', '_')}`; }; const getOption = (e) => { if (e === 'line' || e === 'multiLines') { return { title: '', yNames: [], gridTop: 30, gridLeft: 5, gridBottom: 10, gridRight: 10, boundaryGap: true, xName: '', xNameLocation: 'end', xAxisLineShow: true, xAxisLineColor: '#DCE2E8', xAxisTickShow: true, xAxisTickInside: false, xAxisTickColor: '#DCE2E8', xAxisLabelShow: true, xAxisLabelInterval: false, xAxisLabelInside: false, xAxisLabelRotate: 0, xAxisLabelFormatter: '', xAxisLabelColor: '#fff', xAxisLabelFontSize: 12, xAxisLabelMargin: 3, xAxisSplitLineShow: false, xAxisSplitLineColor: '#DCE2E8', xAxisSplitLineType: 'solid', yName: '', yNameLocation: 'end', yAxisLineShow: true, yAxisLineColor: '#DCE2E8', yAxisTickShow: true, yAxisTickInside: false, yAxisTickColor: '#DCE2E8', yAxisLabelShow: true, yAxisLabelInterval: false, yAxisLabelInside: false, yAxisLabelRotate: 0, yAxisLabelFormatter: '', yAxisLabelColor: '#fff', yAxisLabelFontSize: 12, yAxisLabelMargin: 3, yAxisSplitLineShow: false, yAxisSplitLineColor: '#DCE2E8', yAxisSplitLineType: 'solid', lineSymbolShow: false, lineSymbolSize: 5, lineSymbolType: 'circle', seriesColor: '#9E87FF', tooltip: true, legend: true }; } else if (e === 'bar' || e === 'multiBars') { return { title: '', yNames: [], gridTop: 30, gridLeft: 5, gridBottom: 10, gridRight: 10, boundaryGap: true, xName: '', xNameLocation: 'end', xAxisLineShow: true, xAxisLineColor: '#DCE2E8', xAxisTickShow: true, xAxisTickInside: false, xAxisTickColor: '#DCE2E8', xAxisLabelShow: true, xAxisLabelInterval: false, xAxisLabelInside: false, xAxisLabelRotate: 0, xAxisLabelFormatter: '', xAxisLabelColor: '#fff', xAxisLabelFontSize: 12, xAxisLabelMargin: 3, xAxisSplitLineShow: false, xAxisSplitLineColor: '#DCE2E8', xAxisSplitLineType: 'solid', yName: '', yNameLocation: 'end', yAxisLineShow: true, yAxisLineColor: '#DCE2E8', yAxisTickShow: true, yAxisTickInside: false, yAxisTickColor: '#DCE2E8', yAxisLabelShow: true, yAxisLabelInterval: false, yAxisLabelInside: false, yAxisLabelRotate: 0, yAxisLabelFormatter: '', yAxisLabelColor: '#fff', yAxisLabelFontSize: 12, yAxisLabelMargin: 3, yAxisSplitLineShow: false, yAxisSplitLineColor: '#DCE2E8', yAxisSplitLineType: 'solid', seriesColor: '#9E87FF', tooltip: true, legend: true }; } else if (e === 'backgroundBar') { return { title: '', yNames: [], gridTop: 30, gridLeft: 5, gridBottom: 10, gridRight: 10, boundaryGap: true, xName: '', xNameLocation: 'end', xAxisLineShow: true, xAxisLineColor: '#DCE2E8', xAxisTickShow: true, xAxisTickInside: false, xAxisTickColor: '#DCE2E8', xAxisLabelShow: true, xAxisLabelInterval: false, xAxisLabelInside: false, xAxisLabelRotate: 0, xAxisLabelFormatter: '', xAxisLabelColor: '#fff', xAxisLabelFontSize: 12, xAxisLabelMargin: 3, xAxisSplitLineShow: false, xAxisSplitLineColor: '#DCE2E8', xAxisSplitLineType: 'solid', yName: '', yNameLocation: 'end', yAxisLineShow: true, yAxisLineColor: '#DCE2E8', yAxisTickShow: true, yAxisTickInside: false, yAxisTickColor: '#DCE2E8', yAxisLabelShow: true, yAxisLabelInterval: false, yAxisLabelInside: false, yAxisLabelRotate: 0, yAxisLabelFormatter: '', yAxisLabelColor: '#fff', yAxisLabelFontSize: 12, yAxisLabelMargin: 3, yAxisSplitLineShow: false, yAxisSplitLineColor: '#DCE2E8', yAxisSplitLineType: 'solid', tooltip: true, legend: true, seriesColor: '#9E87FF', backgroundColor: 'rgba(180, 180, 180, 0.2)' }; } else if (e === 'curve' || e === 'multiCurves') { return { title: '', yNames: [], gridTop: 30, gridLeft: 5, gridBottom: 10, gridRight: 10, boundaryGap: true, xName: '', xNameLocation: 'end', xAxisLineShow: true, xAxisLineColor: '#DCE2E8', xAxisTickShow: true, xAxisTickInside: false, xAxisTickColor: '#DCE2E8', xAxisLabelShow: true, xAxisLabelInterval: false, xAxisLabelInside: false, xAxisLabelRotate: 0, xAxisLabelFormatter: '', xAxisLabelColor: '#fff', xAxisLabelFontSize: 12, xAxisLabelMargin: 3, xAxisSplitLineShow: false, xAxisSplitLineColor: '#DCE2E8', xAxisSplitLineType: 'solid', yName: '', yNameLocation: 'end', yAxisLineShow: true, yAxisLineColor: '#DCE2E8', yAxisTickShow: true, yAxisTickInside: false, yAxisTickColor: '#DCE2E8', yAxisLabelShow: true, yAxisLabelInterval: false, yAxisLabelInside: false, yAxisLabelRotate: 0, yAxisLabelFormatter: '', yAxisLabelColor: '#fff', yAxisLabelFontSize: 12, yAxisLabelMargin: 3, yAxisSplitLineShow: false, yAxisSplitLineColor: '#DCE2E8', yAxisSplitLineType: 'solid', lineSymbolShow: false, lineSymbolSize: 5, lineSymbolType: 'circle', seriesColor: '#9E87FF', tooltip: true, legend: true }; } else if (e === 'lineBar') { return { title: '', yNames: [], gridTop: 30, gridLeft: 5, gridBottom: 10, gridRight: 10, xName: '', xNameLocation: 'end', xAxisLineShow: true, xAxisLineColor: '#DCE2E8', xAxisTickShow: true, xAxisTickInside: false, xAxisTickColor: '#DCE2E8', xAxisLabelShow: true, xAxisLabelInterval: false, xAxisLabelInside: false, xAxisLabelRotate: 0, xAxisLabelFormatter: '', xAxisLabelColor: '#fff', xAxisLabelFontSize: 12, xAxisLabelMargin: 3, xAxisSplitLineShow: false, xAxisSplitLineColor: '#DCE2E8', xAxisSplitLineType: 'solid', yName: '', yNameLocation: 'end', yAxisLineShow: true, yAxisLineColor: '#DCE2E8', yAxisTickShow: true, yAxisTickInside: false, yAxisTickColor: '#DCE2E8', yAxisLabelShow: true, yAxisLabelInterval: false, yAxisLabelInside: false, yAxisLabelRotate: 0, yAxisLabelFormatter: '', yAxisLabelColor: '#fff', yAxisLabelFontSize: 12, yAxisLabelMargin: 3, yAxisSplitLineShow: false, yAxisSplitLineColor: '#DCE2E8', yAxisSplitLineType: 'solid', lineSymbolShow: false, lineSymbolSize: 5, lineSymbolType: 'circle', tooltip: true, legend: true, seriesColor: '#9E87FF' }; } else if (e === 'radar') { return { title: '', seriesColor: '#9E87FF', yNames: [], gridTop: 30, gridLeft: 5, gridBottom: 10, gridRight: 10, tooltip: true, legend: true }; } else if (e === 'pie' || e === 'nightingaleRoseDiagram') { return { title: '', yNames: [], tooltip: true, legend: true, label: true, pieCenter: 50, pieLabelFormatter: '', legendColor: '#fff' }; } else if (e === 'annular') { return { title: '', yNames: [], tooltip: true, legend: true, label: true, pieCenter: 50, pieRadius: [30, 70] }; } else if (e === 'dashboard') { return { title: '', yNames: [], tooltip: true, legend: true, label: true }; } else if (e === 'customBoard') { return { title: '', yNames: [] }; } else if (e === 'data') { return { timeout: 5000 }; } else if (e === 'staticData') { return { defaultInputArea: '', field: 'input', defaultDataType: '' }; } else if (e === 'customData') { return { timeout: 5000 }; } else if (e === 'map') { return { dataMap: [] }; } else if (e === 'inputNode') { return { field: 'input', defaultInput: '' }; } else if (e === 'time') { return { startTimeId: 'startTime', endTimeId: 'endTime', defaultTime: [], format: '' }; } else if (e === 'text') { return { text: '文字', align: '', color: '#fff' }; } else if (e === 'img') { return { imgSrc: '' }; } else if (e === 'icon') { return { icon: '', iconSrc: '' }; } else if (e === 'video') { return { videoSrc: '' }; } else if (e === 'timeline') { return { color: '#fff', timestampColor: '#fff', field: 'content', timestampField: 'timestamp', isTimestamp: true }; } else if (e === 'scrollTable' || e === 'table') { return { tableOptions: [], tableCellOptions: [], tableClassOption: {}, isThShow: true, thHeight: '32px', tdHeight: '28px', thColor: '#D6F4FF', tdColor: ['#D6F4FF', '#D6F4FF', '#D6F4FF', '#D6F4FF'], thBgColor: '#1E90FF', tdBgColor: ['#0D2B3D', '#103B4C', '#14576B', '#187E99'] }; } else if (e === 'customTable') { return { tableOptions: [], tableCellOptions: [], cellNum: 2, dataNum: 2, tdHeight: '28px', tdColor: ['#D6F4FF', '#D6F4FF', '#D6F4FF', '#D6F4FF'], tdBgColor: ['#0D2B3D', '#103B4C', '#14576B', '#187E99'] }; } else if (e === 'carousel') { return { swiperOptions: {}, imageFit: 'contain', carouselImages: [] }; } else if (e === 'background') { return { backgroundColor: '#fff', isBorder: true, borderColor: '#fff', backgroundImage: '' }; } else if (e === 'pagination') { return { pageSizeField: 'pageSize', currentPageField: 'pageNum' }; } else if (e === 'digitalFlop') { return { field: '', number: 1111, backgroundColor: 'rgba(180, 180, 180, 0.2)', isBorder: true, borderColor: '#fff' }; } else { return {}; } }; const getNodeSize = (e) => { if (e === 'line' || e === 'multiLines' || e === 'bar' || e === 'multiBars' || e === 'curve' || e === 'multiCurves' || e === 'customBoard' || e === 'pie' || e === 'annular' || e === 'dashboard' || e === 'radar') { return { width: 300, height: 150 }; } else if (e === 'data' || e === 'customData') { return { width: 150, height: 50 }; } else if (e === 'inputNode') { return { width: 100, height: 30 }; } else if (e === 'staticData') { return { width: 100, height: 60 }; } else if (e === 'text') { return { width: 100, height: 30 }; } else if (e === 'time') { return { width: 200, height: 30 }; } else if (e === 'img') { return { width: 300, height: 300 }; } else if (e === 'map') { return { width: 100, height: 30 }; } else if (e === 'scrollTable' || e === 'table') { return { width: 500, height: 300 }; } else { return { width: 100, height: 100 }; } }; const nameEnum = { line: '折线', multiLines: '多折线', curve: '曲线', multiCurves: '多曲线', lineBar: '双轴图', bar: '柱状图', backgroundBar: '背景柱状图', multiBars: '多柱状图', pie: '饼图', annular: '中空饼图', dashboard: '仪表盘', radar: '雷达图', nightingaleRoseDiagram: '南丁格尔玫瑰图', carousel: '轮播图', map: '映射', staticData: '静态数据', customData: '自定义数据', text: '文字', inputNode: '输入框', time: '时间', img: '图片', icon: '图标', video: '视频', timeline: '时间线', digitalFlop: '数字翻牌器', scrollTable: '滚动表格', background: '背景' }; const tool = () => { const nodeType = ref(''); const customData = ref({ script: '' }); const { addNodes, screenToFlowCoordinate, onNodesInitialized, updateNode } = useVueFlow(); const onDragStart = (event, type, data) => { if (event.dataTransfer) { event.dataTransfer.setData('application/vueflow', type); event.dataTransfer.effectAllowed = 'move'; } nodeType.value = type; customData.value = { ...customData.value, ...(data || {}) }; document.addEventListener('drop', onDragEnd); }; const onDragEnd = () => { nodeType.value = null; document.removeEventListener('drop', onDragEnd); }; const onDrop = (event) => { const dimensions = getNodeSize(nodeType.value); const position = screenToFlowCoordinate({ x: event.clientX, y: event.clientY }); const nodeId = getId(nodeType.value); const newNode = { id: nodeId, name: nameEnum[nodeType.value], draggable: true, type: nodeType.value, dimensions, position, data: { options: getOption(nodeType.value), outputData: {}, customData: customData.value } }; const { off } = onNodesInitialized(() => { updateNode(nodeId, (node) => ({ position: { x: node.position.x - node.dimensions.width / 2, y: node.position.y - node.dimensions.height / 2 } })); off(); }); addNodes(newNode); }; const onDragOver = (event) => { event.preventDefault(); if (nodeType.value) { if (event.dataTransfer) { event.dataTransfer.dropEffect = 'move'; } } }; return { onDragStart, onDragEnd, onDrop, onDragOver }; }; export default tool; export const options = { isD: true, isJSON: (str) => { if (typeof str === 'string') { try { JSON.parse(str); return true; } catch (e) { return false; } } return false; }, getId };