|
@@ -1,78 +1,107 @@
|
|
|
<template>
|
|
|
<div class="flow-container">
|
|
|
+ <svg
|
|
|
+ xmlns="http://www.w3.org/2000/svg"
|
|
|
+ xmlns:xlink="http://www.w3.org/1999/xlink"
|
|
|
+ ref="svg"
|
|
|
+ class="view"
|
|
|
+ @dragover.prevent
|
|
|
+ @drop="managerDrop"
|
|
|
+ :width="width"
|
|
|
+ :height="height">
|
|
|
+ <defs>
|
|
|
+ <filter
|
|
|
+ id="highlight-border"
|
|
|
+ x="-100%"
|
|
|
+ y="-100%"
|
|
|
+ width="300%"
|
|
|
+ height="300%">
|
|
|
+ <feMorphology in="SourceGraphic" result="MORPH" operator="dilate" radius="1" />
|
|
|
+ <feColorMatrix in="MORPH" result="BORDER" type="matrix" values=".5 0 0 0 0, 0 .5 0 0 0, 0 0 .5 0 0, 0 0 0 1 0"/>
|
|
|
+ <feColorMatrix
|
|
|
+ result = "matrixOut"
|
|
|
+ in = "SourceGraphic"
|
|
|
+ type = "matrix"
|
|
|
+ values = ".2 0 0 0 0, 0 .2 0 0 0, 0 0 .2 0 0, 0 0 0 1 0"/>
|
|
|
+ <feGaussianBlur
|
|
|
+ result="blurOut"
|
|
|
+ in="matrixOut"
|
|
|
+ stdDeviation="2" />
|
|
|
+ <feMerge>
|
|
|
+ <feMergeNode in="blurOut"/>
|
|
|
+ <feMergeNode in="BORDER"/>
|
|
|
+ <feMergeNode in="SourceGraphic"/>
|
|
|
+ </feMerge>
|
|
|
|
|
|
- <hx-split
|
|
|
- dir="horizontal"
|
|
|
- :resizeable="funcsResizeable"
|
|
|
- :split="funcsActive?funcsSize:'0px'"
|
|
|
- @onSplitResize="funcsSizeUpdate"
|
|
|
- >
|
|
|
- <flow-panel
|
|
|
- :registry="registry"
|
|
|
- @toggleResizeable="funcsResizeable=!funcsResizeable"
|
|
|
- />
|
|
|
- <div class="flow-svgcontainer">
|
|
|
- <svg
|
|
|
- xmlns="http://www.w3.org/2000/svg"
|
|
|
- xmlns:xlink="http://www.w3.org/1999/xlink"
|
|
|
- ref="svg"
|
|
|
- class="view"
|
|
|
- @dragover.prevent
|
|
|
- @drop="managerDrop"
|
|
|
- :width="width"
|
|
|
- :height="height">
|
|
|
- <flow-pan-zoom
|
|
|
- ref="panzoom"
|
|
|
- v-model="panzoom">
|
|
|
- <flow-link
|
|
|
- v-for="(link,i) in nodeData.links"
|
|
|
- :key="i"
|
|
|
- v-bind="linkProps(link)"
|
|
|
- @click="linkRemove(link)"
|
|
|
- />
|
|
|
- <!-- mouse link-->
|
|
|
- <flow-link
|
|
|
- v-if="pointerLink.active"
|
|
|
- v-bind="pointerLink.props"
|
|
|
- />
|
|
|
- <flow-node
|
|
|
- ref="nodes"
|
|
|
- v-for="(n,i) of nodeData.nodes"
|
|
|
- v-bind="nodeProps(n)"
|
|
|
- :key="'node' + n.id"
|
|
|
- :id="n.id"
|
|
|
- @nodePointerDown.prevent="nodeDragStart($event,i)"
|
|
|
- @socketPointerDown="socketPointerDown(n.id,...arguments)"
|
|
|
- />
|
|
|
- </flow-pan-zoom>
|
|
|
- </svg>
|
|
|
- <div class="flow-svgcontainer__control">
|
|
|
- <button
|
|
|
- class="flow-funcs__toggle"
|
|
|
- @click="funcsActive=!funcsActive">Panel</button>
|
|
|
- <button
|
|
|
- @click="panzoomReset">Reset view</button>
|
|
|
+ </filter>
|
|
|
+ <filter id="highlight" x="-100%" y="-100%" width="300%" height="300%">
|
|
|
+ <feColorMatrix
|
|
|
+ result = "matrixOut"
|
|
|
+ in = "SourceGraphic"
|
|
|
+ type = "matrix"
|
|
|
+ values = "2 0 0 0 0 0 2 0 0 0 0 0 2 0 0 0 0 0 1 0"/>
|
|
|
+ <feGaussianBlur
|
|
|
+ result="blurOut"
|
|
|
+ in="matrixOut"
|
|
|
+ stdDeviation="4" />
|
|
|
+ <feMerge>
|
|
|
+ <feMergeNode in="blurOut"/>
|
|
|
+ <feMergeNode in="WHITENED"/>
|
|
|
+ <feMergeNode in="SourceGraphic"/>
|
|
|
+ </feMerge>
|
|
|
|
|
|
- </div>
|
|
|
- <div class="flow-svgcontainer__info">
|
|
|
- x:{{ panzoom.x.toFixed(2) }} y:{{ panzoom.y.toFixed(2) }} scale:{{ panzoom.zoom.toFixed(2) }}
|
|
|
- nodes: {{ nodeData.nodes.length }}
|
|
|
- links: {{ nodeData.links.length }}
|
|
|
- </div>
|
|
|
- </div> <!-- /svg-container-->
|
|
|
- </hx-split>
|
|
|
+ </filter>
|
|
|
+
|
|
|
+ <filter id="drag-shadow" x="-100%" y="-100%" width="300%" height="300%">
|
|
|
+ <feDropShadow dx="0" dy="2" stdDeviation="3"/>
|
|
|
+ </filter>
|
|
|
+
|
|
|
+ </defs>
|
|
|
+ <flow-pan-zoom
|
|
|
+ ref="panzoom"
|
|
|
+ v-model="panzoom">
|
|
|
+ <flow-link
|
|
|
+ v-for="(link,i) in nodeData.links"
|
|
|
+ :key="i"
|
|
|
+ v-bind="linkProps(link)"
|
|
|
+ @click="linkRemove(link)"
|
|
|
+ />
|
|
|
+ <!-- mouse link-->
|
|
|
+ <flow-link
|
|
|
+ v-if="pointerLink.active"
|
|
|
+ v-bind="pointerLink.props"
|
|
|
+ />
|
|
|
+ <flow-node
|
|
|
+ ref="nodes"
|
|
|
+ v-for="(n,i) of nodeData.nodes"
|
|
|
+ v-bind="nodeProps(n)"
|
|
|
+ :key="'node' + n.id"
|
|
|
+ :id="n.id"
|
|
|
+ @nodePointerDown.prevent="nodeDragStart($event,i)"
|
|
|
+ @socketPointerDown="socketPointerDown(n.id,...arguments)"
|
|
|
+ />
|
|
|
+ </flow-pan-zoom>
|
|
|
+ </svg>
|
|
|
+ <div class="flow-container__control">
|
|
|
+ <button @click="$emit('funcsPanelToggle')">Panel</button>
|
|
|
+ <button @click="panzoomReset">Reset view</button>
|
|
|
+
|
|
|
+ </div>
|
|
|
+ <div class="flow-container__info">
|
|
|
+ x:{{ panzoom.x.toFixed(2) }} y:{{ panzoom.y.toFixed(2) }} scale:{{ panzoom.zoom.toFixed(2) }}
|
|
|
+ nodes: {{ nodeData.nodes.length }}
|
|
|
+ links: {{ nodeData.links.length }}
|
|
|
+ </div>
|
|
|
</div>
|
|
|
</template>
|
|
|
<script>
|
|
|
-import FlowPanel from './panel'
|
|
|
import FlowNode from './node'
|
|
|
import FlowLink from './link'
|
|
|
import FlowPanZoom from './panzoom'
|
|
|
-import HxSplit from '@/components/shared/hx-split'
|
|
|
|
|
|
export default {
|
|
|
name: 'FlowManager',
|
|
|
- components: {FlowNode, FlowLink, FlowPanZoom, FlowPanel, HxSplit},
|
|
|
+ components: {FlowNode, FlowLink, FlowPanZoom},
|
|
|
props: {
|
|
|
'value': {type: Object, default: () => {}},
|
|
|
'registry': {type: Object, default: () => {}},
|
|
@@ -82,9 +111,6 @@ export default {
|
|
|
data () {
|
|
|
// const cloned = JSON.parse(JSON.stringify(this.value)) // initial?
|
|
|
return {
|
|
|
- funcsSize: '200px',
|
|
|
- funcsActive: true,
|
|
|
- funcsResizeable: false,
|
|
|
panzoom: { x: 0, y: 0, zoom: 1 },
|
|
|
nodeData: { nodes: [], links: [] },
|
|
|
dragging: null,
|
|
@@ -111,6 +137,7 @@ export default {
|
|
|
inputs: nodeClass.inputs,
|
|
|
output: nodeClass.output,
|
|
|
match: match,
|
|
|
+ dragging: this.dragging === node,
|
|
|
color: nodeClass.style && nodeClass.style.color,
|
|
|
textColor: nodeClass.style && nodeClass.style.textColor
|
|
|
}
|
|
@@ -169,9 +196,6 @@ export default {
|
|
|
})
|
|
|
},
|
|
|
methods: {
|
|
|
- funcsSizeUpdate (ev, size) {
|
|
|
- this.funcsSize = size
|
|
|
- },
|
|
|
panzoomReset () {
|
|
|
this.panzoom.x = 0
|
|
|
this.panzoom.y = 0
|
|
@@ -390,26 +414,24 @@ function guid () {
|
|
|
.flow-container {
|
|
|
display:flex;
|
|
|
flex-flow:row;
|
|
|
-}
|
|
|
-
|
|
|
-.flow-svgcontainer {
|
|
|
- width:100%;
|
|
|
- height:100%;
|
|
|
position:relative;
|
|
|
}
|
|
|
-.flow-svgcontainer__control {
|
|
|
+
|
|
|
+.flow-container__control {
|
|
|
position:absolute;
|
|
|
- top: 10px;
|
|
|
- left: 10px;
|
|
|
+ top: 0px;
|
|
|
+ left: 0px;
|
|
|
display:flex;
|
|
|
justify-content: center;
|
|
|
align-items: center;
|
|
|
}
|
|
|
-.flow-svgcontainer__control button {
|
|
|
+.flow-container__control button {
|
|
|
display:flex;
|
|
|
justify-content: center;
|
|
|
+ margin:0;
|
|
|
+ padding:14px;
|
|
|
}
|
|
|
-.flow-svgcontainer__info {
|
|
|
+.flow-container__info {
|
|
|
position:absolute;
|
|
|
bottom:10px;
|
|
|
left:10px;
|
|
@@ -417,36 +439,10 @@ function guid () {
|
|
|
font-size:8px;
|
|
|
color: #777;
|
|
|
}
|
|
|
-svg.view {
|
|
|
+.flow-container .svg.view {
|
|
|
border:none;
|
|
|
position:relative;
|
|
|
fill:transparent;
|
|
|
}
|
|
|
|
|
|
-.split .splitter{
|
|
|
- flex-basis:0px;
|
|
|
- position:relative;
|
|
|
- background: rgba(208,208,208,0.9);
|
|
|
-}
|
|
|
-.split:not(.resizeable) .content:first-child {
|
|
|
- transition: all .3s;
|
|
|
-}
|
|
|
-
|
|
|
-.split.resizeable.horizontal .splitter::after {
|
|
|
- display:flex;
|
|
|
- justify-content: center;
|
|
|
- align-items: center;
|
|
|
- z-index:100;
|
|
|
- content:" ";
|
|
|
- position:absolute;
|
|
|
-
|
|
|
- top:20%;
|
|
|
- bottom:20%;
|
|
|
- left:0px;
|
|
|
- width:20px;
|
|
|
-
|
|
|
- background: rgba(0,0,0,0.4);
|
|
|
- transition: all .3s;
|
|
|
-}
|
|
|
-
|
|
|
</style>
|