Svelte Flow: possible to add multiple keys
This commit is contained in:
@@ -1,5 +1,9 @@
|
||||
<script lang="ts">
|
||||
import { shortcut, type ShortcutModifierDefinition } from '@svelte-put/shortcut';
|
||||
import {
|
||||
shortcut,
|
||||
type ShortcutEventDetail,
|
||||
type ShortcutModifierDefinition
|
||||
} from '@svelte-put/shortcut';
|
||||
import { isInputDOMNode, isMacOs } from '@xyflow/system';
|
||||
|
||||
import { useStore } from '$lib/store';
|
||||
@@ -40,140 +44,101 @@
|
||||
return isKeyObject(key) ? key.key : key;
|
||||
}
|
||||
|
||||
$: selectionKeyDefinition = {
|
||||
key: getKeyString(selectionKey),
|
||||
modifier: getModifier(selectionKey)
|
||||
};
|
||||
function getShortcutDefinition(keyString: KeyDefinition | KeyDefinition[] | null | undefined) {
|
||||
return Array.isArray(keyString)
|
||||
? keyString.map((key) => ({
|
||||
key: getKeyString(key),
|
||||
modifier: getModifier(key)
|
||||
}))
|
||||
: [
|
||||
{
|
||||
key: getKeyString(keyString),
|
||||
modifier: getModifier(keyString)
|
||||
}
|
||||
];
|
||||
}
|
||||
|
||||
$: multiSelectionKeyDefinition = {
|
||||
key: getKeyString(multiSelectionKey),
|
||||
modifier: getModifier(multiSelectionKey)
|
||||
};
|
||||
function getShortcutTrigger(
|
||||
keyDefinition: KeyDefinitionObject[],
|
||||
callback: (detail: ShortcutEventDetail) => void
|
||||
) {
|
||||
return keyDefinition.map((definition) => ({
|
||||
...definition,
|
||||
enabled: definition.key !== null,
|
||||
callback
|
||||
}));
|
||||
}
|
||||
|
||||
$: deleteKeyDefinition = {
|
||||
key: getKeyString(deleteKey),
|
||||
modifier: getModifier(deleteKey)
|
||||
};
|
||||
$: selectionKeyDefinition = getShortcutDefinition(selectionKey);
|
||||
|
||||
$: panActivationKeyDefinition = {
|
||||
key: getKeyString(panActivationKey),
|
||||
modifier: getModifier(panActivationKey)
|
||||
};
|
||||
$: multiSelectionKeyDefinition = getShortcutDefinition(multiSelectionKey);
|
||||
|
||||
$: zoomActivationKeyDefinition = {
|
||||
key: getKeyString(zoomActivationKey),
|
||||
modifier: getModifier(zoomActivationKey)
|
||||
};
|
||||
$: deleteKeyDefinition = getShortcutDefinition(deleteKey);
|
||||
|
||||
$: panActivationKeyDefinition = getShortcutDefinition(panActivationKey);
|
||||
|
||||
$: zoomActivationKeyDefinition = getShortcutDefinition(zoomActivationKey);
|
||||
</script>
|
||||
|
||||
<svelte:window
|
||||
use:shortcut={{
|
||||
trigger: [
|
||||
{
|
||||
...selectionKeyDefinition,
|
||||
enabled: selectionKeyDefinition.key !== null,
|
||||
callback: () => selectionKeyPressed.set(true)
|
||||
}
|
||||
],
|
||||
|
||||
trigger: getShortcutTrigger(selectionKeyDefinition, () => selectionKeyPressed.set(true)),
|
||||
type: 'keydown'
|
||||
}}
|
||||
use:shortcut={{
|
||||
trigger: [
|
||||
{
|
||||
...selectionKeyDefinition,
|
||||
enabled: selectionKeyDefinition.key !== null,
|
||||
callback: () => selectionKeyPressed.set(false)
|
||||
}
|
||||
],
|
||||
trigger: getShortcutTrigger(selectionKeyDefinition, () => selectionKeyPressed.set(false)),
|
||||
type: 'keyup'
|
||||
}}
|
||||
use:shortcut={{
|
||||
trigger: [
|
||||
{
|
||||
...multiSelectionKeyDefinition,
|
||||
enabled: multiSelectionKeyDefinition.key !== null,
|
||||
callback: () => multiselectionKeyPressed.set(true)
|
||||
}
|
||||
],
|
||||
trigger: getShortcutTrigger(multiSelectionKeyDefinition, () =>
|
||||
multiselectionKeyPressed.set(true)
|
||||
),
|
||||
type: 'keydown'
|
||||
}}
|
||||
use:shortcut={{
|
||||
trigger: [
|
||||
{
|
||||
...multiSelectionKeyDefinition,
|
||||
enabled: multiSelectionKeyDefinition.key !== null,
|
||||
callback: () => multiselectionKeyPressed.set(false)
|
||||
}
|
||||
],
|
||||
trigger: getShortcutTrigger(multiSelectionKeyDefinition, () =>
|
||||
multiselectionKeyPressed.set(false)
|
||||
),
|
||||
type: 'keyup'
|
||||
}}
|
||||
use:shortcut={{
|
||||
trigger: [
|
||||
{
|
||||
...deleteKeyDefinition,
|
||||
enabled: deleteKeyDefinition.key !== null,
|
||||
callback: (detail) => {
|
||||
const isModifierKey =
|
||||
detail.originalEvent.ctrlKey ||
|
||||
detail.originalEvent.metaKey ||
|
||||
detail.originalEvent.shiftKey;
|
||||
if (!isModifierKey && !isInputDOMNode(detail.originalEvent)) {
|
||||
deleteKeyPressed.set(true);
|
||||
}
|
||||
}
|
||||
trigger: getShortcutTrigger(deleteKeyDefinition, (detail) => {
|
||||
const isModifierKey =
|
||||
detail.originalEvent.ctrlKey ||
|
||||
detail.originalEvent.metaKey ||
|
||||
detail.originalEvent.shiftKey;
|
||||
if (!isModifierKey && !isInputDOMNode(detail.originalEvent)) {
|
||||
deleteKeyPressed.set(true);
|
||||
}
|
||||
],
|
||||
}),
|
||||
type: 'keydown'
|
||||
}}
|
||||
use:shortcut={{
|
||||
trigger: [
|
||||
{
|
||||
...deleteKeyDefinition,
|
||||
enabled: deleteKeyDefinition.key !== null,
|
||||
callback: () => deleteKeyPressed.set(false)
|
||||
}
|
||||
],
|
||||
trigger: getShortcutTrigger(deleteKeyDefinition, () => deleteKeyPressed.set(false)),
|
||||
type: 'keyup'
|
||||
}}
|
||||
use:shortcut={{
|
||||
trigger: [
|
||||
{
|
||||
...panActivationKeyDefinition,
|
||||
enabled: panActivationKeyDefinition.key !== null,
|
||||
callback: () => panActivationKeyPressed.set(true)
|
||||
}
|
||||
],
|
||||
trigger: getShortcutTrigger(panActivationKeyDefinition, () =>
|
||||
panActivationKeyPressed.set(true)
|
||||
),
|
||||
type: 'keydown'
|
||||
}}
|
||||
use:shortcut={{
|
||||
trigger: [
|
||||
{
|
||||
...panActivationKeyDefinition,
|
||||
enabled: panActivationKeyDefinition.key !== null,
|
||||
callback: () => panActivationKeyPressed.set(false)
|
||||
}
|
||||
],
|
||||
trigger: getShortcutTrigger(panActivationKeyDefinition, () =>
|
||||
panActivationKeyPressed.set(false)
|
||||
),
|
||||
type: 'keyup'
|
||||
}}
|
||||
use:shortcut={{
|
||||
trigger: [
|
||||
{
|
||||
...zoomActivationKeyDefinition,
|
||||
enabled: zoomActivationKeyDefinition.key !== null,
|
||||
callback: () => zoomActivationKeyPressed.set(true)
|
||||
}
|
||||
],
|
||||
trigger: getShortcutTrigger(zoomActivationKeyDefinition, () =>
|
||||
zoomActivationKeyPressed.set(true)
|
||||
),
|
||||
type: 'keydown'
|
||||
}}
|
||||
use:shortcut={{
|
||||
trigger: [
|
||||
{
|
||||
...zoomActivationKeyDefinition,
|
||||
enabled: zoomActivationKeyDefinition.key !== null,
|
||||
callback: () => zoomActivationKeyPressed.set(false)
|
||||
}
|
||||
],
|
||||
trigger: getShortcutTrigger(zoomActivationKeyDefinition, () =>
|
||||
zoomActivationKeyPressed.set(false)
|
||||
),
|
||||
type: 'keyup'
|
||||
}}
|
||||
/>
|
||||
|
||||
@@ -1,9 +1,9 @@
|
||||
import type { KeyDefinition } from '$lib/types';
|
||||
|
||||
export type KeyHandlerProps = {
|
||||
selectionKey?: KeyDefinition | null;
|
||||
multiSelectionKey?: KeyDefinition | null;
|
||||
deleteKey?: KeyDefinition | null;
|
||||
panActivationKey?: KeyDefinition | null;
|
||||
zoomActivationKey?: KeyDefinition | null;
|
||||
selectionKey?: KeyDefinition | KeyDefinition[] | null;
|
||||
multiSelectionKey?: KeyDefinition | KeyDefinition[] | null;
|
||||
deleteKey?: KeyDefinition | KeyDefinition[] | null;
|
||||
panActivationKey?: KeyDefinition | KeyDefinition[] | null;
|
||||
zoomActivationKey?: KeyDefinition | KeyDefinition[] | null;
|
||||
};
|
||||
|
||||
@@ -86,27 +86,27 @@ export type SvelteFlowProps = DOMAttributes<HTMLDivElement> & {
|
||||
/** Pressing down this key you can select multiple elements with a selection box.
|
||||
* @default 'Shift'
|
||||
*/
|
||||
selectionKey?: KeyDefinition | null;
|
||||
selectionKey?: KeyDefinition | KeyDefinition[] | null;
|
||||
/** If a key is set, you can pan the viewport while that key is held down even if panOnScroll is set to false.
|
||||
*
|
||||
* By setting this prop to null you can disable this functionality.
|
||||
* @default 'Space'
|
||||
*/
|
||||
panActivationKey?: KeyDefinition | null;
|
||||
panActivationKey?: KeyDefinition | KeyDefinition[] | null;
|
||||
/** Pressing down this key deletes all selected nodes & edges.
|
||||
* @default 'Backspace'
|
||||
*/
|
||||
deleteKey?: KeyDefinition | null;
|
||||
deleteKey?: KeyDefinition | KeyDefinition[] | null;
|
||||
/** Pressing down this key you can select multiple elements by clicking.
|
||||
* @default 'Meta' for macOS, "Ctrl" for other systems
|
||||
*/
|
||||
multiSelectionKey?: KeyDefinition | null;
|
||||
multiSelectionKey?: KeyDefinition | KeyDefinition[] | null;
|
||||
/** If a key is set, you can zoom the viewport while that key is held down even if panOnScroll is set to false.
|
||||
*
|
||||
* By setting this prop to null you can disable this functionality.
|
||||
* @default 'Meta' for macOS, "Ctrl" for other systems
|
||||
* */
|
||||
zoomActivationKey?: KeyDefinition | null;
|
||||
zoomActivationKey?: KeyDefinition | KeyDefinition[] | null;
|
||||
/** If set, initial viewport will show all nodes & edges */
|
||||
fitView?: boolean;
|
||||
/** Options to be used in combination with fitView
|
||||
|
||||
Reference in New Issue
Block a user