Added handleEdgeSelect hook & click on edge-label now selects edge

This commit is contained in:
peterkogo
2024-01-18 14:26:35 +01:00
parent 6bb9c5360d
commit 88aa0fccf3
7 changed files with 86 additions and 50 deletions
@@ -1,7 +1,7 @@
<script lang="ts"> <script lang="ts">
import cc from 'classcat'; import cc from 'classcat';
import { EdgeLabelRenderer } from '$lib/components/EdgeLabelRenderer';
import type { BaseEdgeProps } from './types'; import type { BaseEdgeProps } from './types';
import EdgeLabel from '../EdgeLabel/EdgeLabel.svelte';
type $$Props = BaseEdgeProps; type $$Props = BaseEdgeProps;
@@ -43,13 +43,7 @@
{/if} {/if}
{#if label} {#if label}
<EdgeLabelRenderer> <EdgeLabel {labelX} {labelY} {labelStyle}>
<div {label}
class="svelte-flow__edge-label" </EdgeLabel>
style:transform="translate(-50%, -50%) translate({labelX}px,{labelY}px)"
style={labelStyle}
>
{label}
</div>
</EdgeLabelRenderer>
{/if} {/if}
@@ -0,0 +1,27 @@
<script lang="ts">
import { EdgeLabelRenderer } from '$lib/components/EdgeLabelRenderer';
import { useHandleEdgeSelect } from '$lib/hooks/useHandleEdgeSelect';
import { getContext } from 'svelte';
import type { BaseEdgeProps } from '../BaseEdge/types';
export let labelStyle: BaseEdgeProps['labelStyle'] = undefined;
export let labelX: BaseEdgeProps['labelX'] = undefined;
export let labelY: BaseEdgeProps['labelY'] = undefined;
const handleEdgeSelect = useHandleEdgeSelect();
const id = getContext<string>('svelteflow__edge_id');
</script>
<EdgeLabelRenderer>
<div
class="svelte-flow__edge-label"
style:transform="translate(-50%, -50%) translate({labelX}px,{labelY}px)"
style={'pointer-events: all;' + labelStyle}
on:click={() => {
if (id) handleEdgeSelect(id);
}}
>
<slot />
</div>
</EdgeLabelRenderer>
@@ -0,0 +1 @@
export { default as EdgeLabel } from './EdgeLabel.svelte';
@@ -2,13 +2,13 @@
<script lang="ts"> <script lang="ts">
import cc from 'classcat'; import cc from 'classcat';
import { createEventDispatcher } from 'svelte'; import { createEventDispatcher, setContext } from 'svelte';
import { errorMessages, getMarkerId } from '@xyflow/system'; import { getMarkerId } from '@xyflow/system';
import { useStore } from '$lib/store'; import { useStore } from '$lib/store';
import { BezierEdgeInternal } from '$lib/components/edges'; import { BezierEdgeInternal } from '$lib/components/edges';
import type { EdgeLayouted, Edge } from '$lib/types'; import type { EdgeLayouted, Edge } from '$lib/types';
import { get } from 'svelte/store'; import { useHandleEdgeSelect } from '$lib/hooks/useHandleEdgeSelect';
type $$Props = EdgeLayouted; type $$Props = EdgeLayouted;
@@ -22,7 +22,6 @@
export let animated: $$Props['animated'] = false; export let animated: $$Props['animated'] = false;
export let selected: $$Props['selected'] = false; export let selected: $$Props['selected'] = false;
export let selectable: $$Props['selectable'] = true;
export let hidden: $$Props['hidden'] = false; export let hidden: $$Props['hidden'] = false;
export let label: $$Props['label'] = undefined; export let label: $$Props['label'] = undefined;
export let labelStyle: $$Props['labelStyle'] = undefined; export let labelStyle: $$Props['labelStyle'] = undefined;
@@ -43,16 +42,9 @@
let className: string = ''; let className: string = '';
export { className as class }; export { className as class };
const { setContext('svelteflow__edge_id', id);
edges,
edgeTypes, const { edgeLookup, edgeTypes, flowId } = useStore();
flowId,
selectionRect,
selectionRectMode,
multiselectionKeyPressed,
addSelectedEdges,
unselectNodesAndEdges
} = useStore();
const dispatch = createEventDispatcher<{ const dispatch = createEventDispatcher<{
edgeclick: { edge: Edge; event: MouseEvent | TouchEvent }; edgeclick: { edge: Edge; event: MouseEvent | TouchEvent };
edgecontextmenu: { edge: Edge; event: MouseEvent }; edgecontextmenu: { edge: Edge; event: MouseEvent };
@@ -62,30 +54,19 @@
$: markerStartUrl = markerStart ? `url(#${getMarkerId(markerStart, $flowId)})` : undefined; $: markerStartUrl = markerStart ? `url(#${getMarkerId(markerStart, $flowId)})` : undefined;
$: markerEndUrl = markerEnd ? `url(#${getMarkerId(markerEnd, $flowId)})` : undefined; $: markerEndUrl = markerEnd ? `url(#${getMarkerId(markerEnd, $flowId)})` : undefined;
const handleEdgeSelect = useHandleEdgeSelect();
function onClick(event: MouseEvent | TouchEvent) { function onClick(event: MouseEvent | TouchEvent) {
const edge = $edges.find((e) => e.id === id); const edge = $edgeLookup.get(id);
if (!edge) { if (edge) {
console.warn('012', errorMessages['error012'](id)); handleEdgeSelect(id);
return; dispatch('edgeclick', { event, edge });
} }
if (selectable) {
selectionRect.set(null);
selectionRectMode.set(null);
if (!edge.selected) {
addSelectedEdges([id]);
} else if (edge.selected && get(multiselectionKeyPressed)) {
unselectNodesAndEdges({ nodes: [], edges: [edge] });
}
}
dispatch('edgeclick', { event, edge });
} }
function onContextMenu(event: MouseEvent) { function onContextMenu(event: MouseEvent) {
const edge = $edges.find((e) => e.id === id); const edge = $edgeLookup.get(id);
if (edge) { if (edge) {
dispatch('edgecontextmenu', { event, edge }); dispatch('edgecontextmenu', { event, edge });
@@ -24,12 +24,6 @@
</svg> </svg>
{#each $visibleEdges as edge (edge.id)} {#each $visibleEdges as edge (edge.id)}
{@const edgeType = edge.type || 'default'}
{@const selectable = !!(
edge.selectable ||
($elementsSelectable && typeof edge.selectable === 'undefined')
)}
<EdgeWrapper <EdgeWrapper
id={edge.id} id={edge.id}
source={edge.source} source={edge.source}
@@ -54,9 +48,8 @@
ariaLabel={edge.ariaLabel} ariaLabel={edge.ariaLabel}
interactionWidth={edge.interactionWidth} interactionWidth={edge.interactionWidth}
class={edge.class} class={edge.class}
type={edgeType} type={edge.type || 'default'}
zIndex={edge.zIndex} zIndex={edge.zIndex}
{selectable}
on:edgeclick on:edgeclick
on:edgecontextmenu on:edgecontextmenu
/> />
@@ -0,0 +1,39 @@
import { get } from 'svelte/store';
import { useStore } from '$lib/store';
import { errorMessages } from '@xyflow/system';
export function useHandleEdgeSelect() {
const {
edgeLookup,
selectionRect,
selectionRectMode,
multiselectionKeyPressed,
addSelectedEdges,
unselectNodesAndEdges,
elementsSelectable
} = useStore();
return (id: string) => {
const edge = get(edgeLookup).get(id);
if (!edge) {
console.warn('012', errorMessages['error012'](id));
return;
}
const selectable =
edge.selectable || (get(elementsSelectable) && typeof edge.selectable === 'undefined');
if (selectable) {
selectionRect.set(null);
selectionRectMode.set(null);
if (!edge.selected) {
addSelectedEdges([id]);
} else if (edge.selected && get(multiselectionKeyPressed)) {
unselectNodesAndEdges({ nodes: [], edges: [edge] });
}
}
};
}
+1
View File
@@ -8,6 +8,7 @@
position: absolute; position: absolute;
padding: 2px; padding: 2px;
font-size: 10px; font-size: 10px;
cursor: pointer;
color: var(--xy-edge-label-color, var(--xy-edge-label-color-default)); color: var(--xy-edge-label-color, var(--xy-edge-label-color-default));
background: var(--xy-edge-label-background-color, var(--xy-edge-label-background-color-default)); background: var(--xy-edge-label-background-color, var(--xy-edge-label-background-color-default));
} }