refactor(nodes)!: Remove dragging from graph nodes
# What's changed? * Dragging property removed from position updates and graph nodes * Dragging is handled internally by nodes and passed to custom nodes
This commit is contained in:
@@ -154,7 +154,6 @@ export default {
|
|||||||
:name="`node-${node.type}`"
|
:name="`node-${node.type}`"
|
||||||
:parent-node="node.parentNode"
|
:parent-node="node.parentNode"
|
||||||
:selected="node.selected"
|
:selected="node.selected"
|
||||||
:dragging="node.dragging"
|
|
||||||
:position="node.computedPosition"
|
:position="node.computedPosition"
|
||||||
:dimensions="node.dimensions"
|
:dimensions="node.dimensions"
|
||||||
:style="node.style"
|
:style="node.style"
|
||||||
|
|||||||
@@ -37,6 +37,8 @@ const {
|
|||||||
|
|
||||||
const nodeElement = ref()
|
const nodeElement = ref()
|
||||||
|
|
||||||
|
let dragging = $ref(false)
|
||||||
|
|
||||||
useDrag({
|
useDrag({
|
||||||
id,
|
id,
|
||||||
el: nodeElement,
|
el: nodeElement,
|
||||||
@@ -66,26 +68,21 @@ useDrag({
|
|||||||
emits.nodeDragStart({ event: event.sourceEvent, node, connectedEdges: getConnectedEdges([node], edges) })
|
emits.nodeDragStart({ event: event.sourceEvent, node, connectedEdges: getConnectedEdges([node], edges) })
|
||||||
},
|
},
|
||||||
onDrag(event, { dx, dy }) {
|
onDrag(event, { dx, dy }) {
|
||||||
updateNodePosition({ id: node.id, diff: { x: dx, y: dy }, dragging: true })
|
dragging = true
|
||||||
|
updateNodePosition({ id: node.id, diff: { x: dx, y: dy } })
|
||||||
emits.nodeDrag({ event: event.sourceEvent, node, connectedEdges: getConnectedEdges([node], edges) })
|
emits.nodeDrag({ event: event.sourceEvent, node, connectedEdges: getConnectedEdges([node], edges) })
|
||||||
},
|
},
|
||||||
onStop(event) {
|
onStop(event) {
|
||||||
if (!node.dragging) {
|
dragging = false
|
||||||
if (selectable && !selectNodesOnDrag && !node.selected) {
|
|
||||||
addSelectedNodes([node])
|
|
||||||
}
|
|
||||||
emits.nodeClick({ event: event.sourceEvent, node, connectedEdges: getConnectedEdges([node], edges) })
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
updateNodePosition({ id: node.id, dragging: false })
|
updateNodePosition({ id: node.id })
|
||||||
|
|
||||||
emits.nodeDragStop({ event: event.sourceEvent, node, connectedEdges: getConnectedEdges([node], edges) })
|
emits.nodeDragStop({ event: event.sourceEvent, node, connectedEdges: getConnectedEdges([node], edges) })
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
onBeforeMount(() => {
|
onBeforeMount(() => {
|
||||||
updateNodePosition({ id: node.id, diff: { x: 0, y: 0 }, dragging: false })
|
updateNodePosition({ id: node.id, diff: { x: 0, y: 0 } })
|
||||||
})
|
})
|
||||||
|
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
@@ -110,7 +107,7 @@ onMounted(() => {
|
|||||||
([pos, parent]) => {
|
([pos, parent]) => {
|
||||||
const xyzPos = {
|
const xyzPos = {
|
||||||
...pos,
|
...pos,
|
||||||
z: node.dragging || node.selected ? 1000 : 0,
|
z: node.computedPosition.z ? node.computedPosition.z : node.selected ? 1000 : 0,
|
||||||
}
|
}
|
||||||
const graphNode = getNode(id)!
|
const graphNode = getNode(id)!
|
||||||
|
|
||||||
@@ -131,19 +128,19 @@ onUnmounted(() => {
|
|||||||
})
|
})
|
||||||
|
|
||||||
const onMouseEnter = (event: MouseEvent) => {
|
const onMouseEnter = (event: MouseEvent) => {
|
||||||
if (!node.dragging) {
|
if (!dragging) {
|
||||||
emits.nodeMouseEnter({ event, node, connectedEdges: getConnectedEdges([node], edges) })
|
emits.nodeMouseEnter({ event, node, connectedEdges: getConnectedEdges([node], edges) })
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const onMouseMove = (event: MouseEvent) => {
|
const onMouseMove = (event: MouseEvent) => {
|
||||||
if (!node.dragging) {
|
if (!dragging) {
|
||||||
emits.nodeMouseMove({ event, node, connectedEdges: getConnectedEdges([node], edges) })
|
emits.nodeMouseMove({ event, node, connectedEdges: getConnectedEdges([node], edges) })
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const onMouseLeave = (event: MouseEvent) => {
|
const onMouseLeave = (event: MouseEvent) => {
|
||||||
if (!node.dragging) {
|
if (!dragging) {
|
||||||
emits.nodeMouseLeave({ event, node, connectedEdges: getConnectedEdges([node], edges) })
|
emits.nodeMouseLeave({ event, node, connectedEdges: getConnectedEdges([node], edges) })
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -160,8 +157,8 @@ const onDoubleClick = (event: MouseEvent) =>
|
|||||||
emits.nodeDoubleClick({ event, node, connectedEdges: getConnectedEdges([node], edges) })
|
emits.nodeDoubleClick({ event, node, connectedEdges: getConnectedEdges([node], edges) })
|
||||||
|
|
||||||
const onSelectNode = (event: MouseEvent) => {
|
const onSelectNode = (event: MouseEvent) => {
|
||||||
if (!draggable) {
|
if (!dragging) {
|
||||||
if (selectable) {
|
if (selectable && !selectNodesOnDrag && !node.selected) {
|
||||||
setState({
|
setState({
|
||||||
nodesSelectionActive: false,
|
nodesSelectionActive: false,
|
||||||
})
|
})
|
||||||
@@ -179,7 +176,7 @@ const getClass = computed(() => {
|
|||||||
`vue-flow__node-${name}`,
|
`vue-flow__node-${name}`,
|
||||||
noPanClassName,
|
noPanClassName,
|
||||||
{
|
{
|
||||||
dragging: node.dragging,
|
dragging,
|
||||||
selected: node.selected,
|
selected: node.selected,
|
||||||
selectable,
|
selectable,
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -13,11 +13,10 @@ useDrag({
|
|||||||
},
|
},
|
||||||
onDrag(event, { dx, dy }) {
|
onDrag(event, { dx, dy }) {
|
||||||
emits.selectionDrag({ event: event.sourceEvent, nodes: getSelectedNodes })
|
emits.selectionDrag({ event: event.sourceEvent, nodes: getSelectedNodes })
|
||||||
updateNodePosition({ diff: { x: dx, y: dy }, dragging: true })
|
updateNodePosition({ diff: { x: dx, y: dy } })
|
||||||
},
|
},
|
||||||
onStop(event) {
|
onStop(event) {
|
||||||
emits.selectionDragStop({ event: event.sourceEvent, nodes: getSelectedNodes })
|
emits.selectionDragStop({ event: event.sourceEvent, nodes: getSelectedNodes })
|
||||||
getSelectedNodes.forEach((node) => (node.dragging = false))
|
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|||||||
@@ -117,18 +117,18 @@ const createGraphNodes = (nodes: Node[], getNode: Getters['getNode'], currGraphN
|
|||||||
}
|
}
|
||||||
|
|
||||||
export default (state: State, getters: ComputedGetters): Actions => {
|
export default (state: State, getters: ComputedGetters): Actions => {
|
||||||
const updateNodePosition: Actions['updateNodePosition'] = ({ id, diff = { x: 0, y: 0 }, dragging }) => {
|
const updateNodePosition: Actions['updateNodePosition'] = ({ id, diff = { x: 0, y: 0 } }) => {
|
||||||
const nodePosPromise = new Promise<NodePositionChange[]>((resolve) => {
|
const nodePosPromise = new Promise<NodePositionChange[]>((resolve) => {
|
||||||
const changes: NodePositionChange[] = []
|
const changes: NodePositionChange[] = []
|
||||||
const curr = id ? getters.getNode.value(id)! : undefined
|
const curr = id ? getters.getNode.value(id)! : undefined
|
||||||
if (curr) {
|
if (curr) {
|
||||||
changes.push(createPositionChange({ node: curr, diff, nodeExtent: state.nodeExtent, dragging }, getters.getNode.value))
|
changes.push(createPositionChange({ node: curr, diff, nodeExtent: state.nodeExtent }, getters.getNode.value))
|
||||||
} else {
|
} else {
|
||||||
getters.getSelectedNodes.value.forEach((node) => {
|
getters.getSelectedNodes.value.forEach((node) => {
|
||||||
if (!node.parentNode) {
|
if (!node.parentNode) {
|
||||||
changes.push(createPositionChange({ node, diff, nodeExtent: state.nodeExtent, dragging }, getters.getNode.value))
|
changes.push(createPositionChange({ node, diff, nodeExtent: state.nodeExtent }, getters.getNode.value))
|
||||||
} else if (!isParentSelected(node, getters.getNode.value)) {
|
} else if (!isParentSelected(node, getters.getNode.value)) {
|
||||||
changes.push(createPositionChange({ node, diff, nodeExtent: state.nodeExtent, dragging }, getters.getNode.value))
|
changes.push(createPositionChange({ node, diff, nodeExtent: state.nodeExtent }, getters.getNode.value))
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -13,7 +13,6 @@ export interface NodePositionChange {
|
|||||||
id: string
|
id: string
|
||||||
type: 'position'
|
type: 'position'
|
||||||
position?: XYPosition
|
position?: XYPosition
|
||||||
dragging?: boolean
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface NodeSelectionChange {
|
export interface NodeSelectionChange {
|
||||||
|
|||||||
@@ -68,7 +68,6 @@ export interface GraphNode<Data = ElementData> extends Node<Data> {
|
|||||||
dimensions: Dimensions
|
dimensions: Dimensions
|
||||||
isParent: boolean
|
isParent: boolean
|
||||||
selected: boolean
|
selected: boolean
|
||||||
dragging: boolean
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/** these props are passed to node components */
|
/** these props are passed to node components */
|
||||||
|
|||||||
@@ -25,11 +25,7 @@ export interface UpdateNodeDimensionsParams {
|
|||||||
forceUpdate?: boolean
|
forceUpdate?: boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface UpdateNodePositionsParams {
|
export type UpdateNodePositionsParams = { id?: string; diff?: XYPosition }
|
||||||
id?: string
|
|
||||||
diff?: XYPosition
|
|
||||||
dragging?: boolean
|
|
||||||
}
|
|
||||||
|
|
||||||
export interface State extends Omit<FlowOptions, 'id' | 'modelValue'> {
|
export interface State extends Omit<FlowOptions, 'id' | 'modelValue'> {
|
||||||
/** Event hooks, you can manipulate the triggers at your own peril */
|
/** Event hooks, you can manipulate the triggers at your own peril */
|
||||||
@@ -130,7 +126,7 @@ export type SetState = (
|
|||||||
| Partial<FlowOptions & Omit<State, 'nodes' | 'edges' | 'modelValue'>>
|
| Partial<FlowOptions & Omit<State, 'nodes' | 'edges' | 'modelValue'>>
|
||||||
| ((state: State) => Partial<FlowOptions & Omit<State, 'nodes' | 'edges' | 'modelValue'>>),
|
| ((state: State) => Partial<FlowOptions & Omit<State, 'nodes' | 'edges' | 'modelValue'>>),
|
||||||
) => void
|
) => void
|
||||||
export type UpdateNodePosition = ({ id, diff, dragging }: UpdateNodePositionsParams) => void
|
export type UpdateNodePosition = (params: UpdateNodePositionsParams) => void
|
||||||
export type UpdateNodeDimensions = (updates: UpdateNodeDimensionsParams[]) => void
|
export type UpdateNodeDimensions = (updates: UpdateNodeDimensionsParams[]) => void
|
||||||
|
|
||||||
export interface Actions {
|
export interface Actions {
|
||||||
|
|||||||
@@ -23,7 +23,6 @@ interface CreatePositionChangeParams {
|
|||||||
node: GraphNode
|
node: GraphNode
|
||||||
nodeExtent: CoordinateExtent
|
nodeExtent: CoordinateExtent
|
||||||
diff?: XYPosition
|
diff?: XYPosition
|
||||||
dragging?: boolean
|
|
||||||
}
|
}
|
||||||
|
|
||||||
function handleParentExpand(updateItem: GraphNode, parent: GraphNode) {
|
function handleParentExpand(updateItem: GraphNode, parent: GraphNode) {
|
||||||
@@ -115,7 +114,6 @@ export const applyChanges = <
|
|||||||
case 'position':
|
case 'position':
|
||||||
if (isGraphNode(el)) {
|
if (isGraphNode(el)) {
|
||||||
if (typeof change.position !== 'undefined') el.position = change.position
|
if (typeof change.position !== 'undefined') el.position = change.position
|
||||||
if (typeof change.dragging !== 'undefined') el.dragging = change.dragging
|
|
||||||
if (el.expandParent && el.parentNode) {
|
if (el.expandParent && el.parentNode) {
|
||||||
const parent = elements.find((parent) => parent.id === el.parentNode)
|
const parent = elements.find((parent) => parent.id === el.parentNode)
|
||||||
|
|
||||||
@@ -159,14 +157,13 @@ export const createSelectionChange = (id: string, selected: boolean): NodeSelect
|
|||||||
})
|
})
|
||||||
|
|
||||||
export const createPositionChange = (
|
export const createPositionChange = (
|
||||||
{ node, diff, dragging, nodeExtent }: CreatePositionChangeParams,
|
{ node, diff, nodeExtent }: CreatePositionChangeParams,
|
||||||
getNode: Getters['getNode'],
|
getNode: Getters['getNode'],
|
||||||
): NodePositionChange => {
|
): NodePositionChange => {
|
||||||
const parent = node.parentNode ? getNode(node.parentNode) : undefined
|
const parent = node.parentNode ? getNode(node.parentNode) : undefined
|
||||||
const change: NodePositionChange = {
|
const change: NodePositionChange = {
|
||||||
id: node.id,
|
id: node.id,
|
||||||
type: 'position',
|
type: 'position',
|
||||||
dragging: !!dragging,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (diff) {
|
if (diff) {
|
||||||
|
|||||||
@@ -75,7 +75,6 @@ export const parseNode = (node: Node, nodeExtent: CoordinateExtent, defaults?: P
|
|||||||
x: 0,
|
x: 0,
|
||||||
y: 0,
|
y: 0,
|
||||||
},
|
},
|
||||||
dragging: false,
|
|
||||||
draggable: undefined,
|
draggable: undefined,
|
||||||
selectable: undefined,
|
selectable: undefined,
|
||||||
connectable: undefined,
|
connectable: undefined,
|
||||||
@@ -270,7 +269,7 @@ export const getNodesInside = (
|
|||||||
|
|
||||||
return nodes.filter((node) => {
|
return nodes.filter((node) => {
|
||||||
if (!node || node.selectable === false) return false
|
if (!node || node.selectable === false) return false
|
||||||
const { computedPosition = { x: 0, y: 0 }, dimensions = { width: 0, height: 0 }, dragging = false } = node
|
const { computedPosition = { x: 0, y: 0 }, dimensions = { width: 0, height: 0 } } = node
|
||||||
const nBox = rectToBox({ ...computedPosition, ...dimensions })
|
const nBox = rectToBox({ ...computedPosition, ...dimensions })
|
||||||
const xOverlap = Math.max(0, Math.min(rBox.x2, nBox.x2) - Math.max(rBox.x, nBox.x))
|
const xOverlap = Math.max(0, Math.min(rBox.x2, nBox.x2) - Math.max(rBox.x, nBox.x))
|
||||||
const yOverlap = Math.max(0, Math.min(rBox.y2, nBox.y2) - Math.max(rBox.y, nBox.y))
|
const yOverlap = Math.max(0, Math.min(rBox.y2, nBox.y2) - Math.max(rBox.y, nBox.y))
|
||||||
@@ -279,8 +278,7 @@ export const getNodesInside = (
|
|||||||
typeof dimensions.width === 'undefined' ||
|
typeof dimensions.width === 'undefined' ||
|
||||||
typeof dimensions.height === 'undefined' ||
|
typeof dimensions.height === 'undefined' ||
|
||||||
dimensions.width === 0 ||
|
dimensions.width === 0 ||
|
||||||
dimensions.height === 0 ||
|
dimensions.height === 0
|
||||||
dragging
|
|
||||||
|
|
||||||
const partiallyVisible = partially && overlappingArea > 0
|
const partiallyVisible = partially && overlappingArea > 0
|
||||||
const area = dimensions.width * dimensions.height
|
const area = dimensions.width * dimensions.height
|
||||||
|
|||||||
Reference in New Issue
Block a user