svedit 0.12.0 → 0.14.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (88) hide show
  1. package/README.md +35 -22
  2. package/dist/Command.svelte.d.ts +38 -30
  3. package/dist/Command.svelte.d.ts.map +1 -1
  4. package/dist/Command.svelte.js +271 -326
  5. package/dist/CustomProperty.svelte +3 -5
  6. package/dist/CustomProperty.svelte.d.ts +3 -6
  7. package/dist/CustomProperty.svelte.d.ts.map +1 -1
  8. package/dist/KeyMapper.svelte.d.ts +19 -6
  9. package/dist/KeyMapper.svelte.d.ts.map +1 -1
  10. package/dist/KeyMapper.svelte.js +95 -112
  11. package/dist/Node.svelte +16 -13
  12. package/dist/Node.svelte.d.ts +3 -5
  13. package/dist/Node.svelte.d.ts.map +1 -1
  14. package/dist/NodeArrayProperty.svelte +39 -22
  15. package/dist/NodeArrayProperty.svelte.d.ts +3 -5
  16. package/dist/NodeArrayProperty.svelte.d.ts.map +1 -1
  17. package/dist/NodeCaret.svelte +2 -2
  18. package/dist/NodeCaret.svelte.d.ts +6 -14
  19. package/dist/NodeCaret.svelte.d.ts.map +1 -1
  20. package/dist/NodeGap.svelte +12 -6
  21. package/dist/NodeGap.svelte.d.ts +7 -14
  22. package/dist/NodeGap.svelte.d.ts.map +1 -1
  23. package/dist/NodeGapMarkers.svelte +36 -14
  24. package/dist/NodeGapMarkers.svelte.d.ts +6 -11
  25. package/dist/NodeGapMarkers.svelte.d.ts.map +1 -1
  26. package/dist/NodeSelectionMarkers.svelte +21 -7
  27. package/dist/NodeSelectionMarkers.svelte.d.ts +2 -5
  28. package/dist/NodeSelectionMarkers.svelte.d.ts.map +1 -1
  29. package/dist/Session.svelte.d.ts +81 -129
  30. package/dist/Session.svelte.d.ts.map +1 -1
  31. package/dist/Session.svelte.js +542 -648
  32. package/dist/Svedit.svelte +146 -140
  33. package/dist/Svedit.svelte.d.ts +30 -10
  34. package/dist/Svedit.svelte.d.ts.map +1 -1
  35. package/dist/TextProperty.svelte +37 -23
  36. package/dist/TextProperty.svelte.d.ts +3 -5
  37. package/dist/TextProperty.svelte.d.ts.map +1 -1
  38. package/dist/Transaction.svelte.d.ts +64 -127
  39. package/dist/Transaction.svelte.d.ts.map +1 -1
  40. package/dist/Transaction.svelte.js +839 -1001
  41. package/dist/UnknownNode.svelte +4 -3
  42. package/dist/UnknownNode.svelte.d.ts +5 -9
  43. package/dist/UnknownNode.svelte.d.ts.map +1 -1
  44. package/dist/doc_utils.d.ts +67 -155
  45. package/dist/doc_utils.d.ts.map +1 -1
  46. package/dist/doc_utils.js +619 -863
  47. package/dist/index.d.ts +20 -17
  48. package/dist/index.d.ts.map +1 -1
  49. package/dist/index.js +1 -17
  50. package/dist/node_visibility.svelte.d.ts +110 -9
  51. package/dist/node_visibility.svelte.d.ts.map +1 -1
  52. package/dist/node_visibility.svelte.js +473 -544
  53. package/dist/paste_utils.d.ts +11 -44
  54. package/dist/paste_utils.d.ts.map +1 -1
  55. package/dist/paste_utils.js +111 -152
  56. package/dist/styles/svedit-colors.css +8 -5
  57. package/dist/transforms.svelte.d.ts +9 -7
  58. package/dist/transforms.svelte.d.ts.map +1 -1
  59. package/dist/transforms.svelte.js +125 -150
  60. package/dist/types.d.ts +294 -309
  61. package/dist/types.d.ts.map +1 -0
  62. package/dist/types.js +1 -0
  63. package/dist/utils.d.ts +40 -119
  64. package/dist/utils.d.ts.map +1 -1
  65. package/dist/utils.js +346 -473
  66. package/package.json +70 -70
  67. package/src/lib/{Command.svelte.js → Command.svelte.ts} +29 -17
  68. package/src/lib/CustomProperty.svelte +3 -5
  69. package/src/lib/{KeyMapper.svelte.js → KeyMapper.svelte.ts} +28 -11
  70. package/src/lib/Node.svelte +16 -13
  71. package/src/lib/NodeArrayProperty.svelte +39 -22
  72. package/src/lib/NodeCaret.svelte +2 -2
  73. package/src/lib/NodeGap.svelte +12 -6
  74. package/src/lib/NodeGapMarkers.svelte +36 -14
  75. package/src/lib/NodeSelectionMarkers.svelte +21 -7
  76. package/src/lib/{Session.svelte.js → Session.svelte.ts} +130 -127
  77. package/src/lib/Svedit.svelte +146 -140
  78. package/src/lib/TextProperty.svelte +37 -23
  79. package/src/lib/{Transaction.svelte.js → Transaction.svelte.ts} +139 -143
  80. package/src/lib/UnknownNode.svelte +4 -3
  81. package/src/lib/{doc_utils.js → doc_utils.ts} +247 -206
  82. package/src/lib/{index.js → index.ts} +48 -0
  83. package/src/lib/{node_visibility.svelte.js → node_visibility.svelte.ts} +68 -92
  84. package/src/lib/{paste_utils.js → paste_utils.ts} +47 -58
  85. package/src/lib/styles/svedit-colors.css +8 -5
  86. package/src/lib/{transforms.svelte.js → transforms.svelte.ts} +39 -21
  87. package/src/lib/{types.d.ts → types.ts} +161 -66
  88. package/src/lib/{utils.js → utils.ts} +110 -129
@@ -1,10 +1,8 @@
1
- <script>
1
+ <script lang="ts">
2
2
  import { serialize_path } from './utils.js';
3
+ import type { CustomPropertyProps } from './types.js';
3
4
 
4
- /** @import { CustomPropertyProps } from './types.d.ts'; */
5
-
6
- /** @type {CustomPropertyProps} */
7
- let { path, tag = 'div', class: css_class, children, style, ...rest } = $props();
5
+ let { path, tag = 'div', class: css_class, children, style, ...rest }: CustomPropertyProps = $props();
8
6
  let path_str = $derived(serialize_path(path));
9
7
 
10
8
  </script>
@@ -1,8 +1,5 @@
1
- export default CustomProperty;
2
- type CustomProperty = {
3
- $on?(type: string, callback: (e: any) => void): () => void;
4
- $set?(props: Partial<CustomPropertyProps>): void;
5
- };
1
+ import type { CustomPropertyProps } from './types.js';
6
2
  declare const CustomProperty: import("svelte").Component<CustomPropertyProps, {}, "">;
7
- import type { CustomPropertyProps } from './types.d.ts';
3
+ type CustomProperty = ReturnType<typeof CustomProperty>;
4
+ export default CustomProperty;
8
5
  //# sourceMappingURL=CustomProperty.svelte.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"CustomProperty.svelte.d.ts","sourceRoot":"","sources":["../src/lib/CustomProperty.svelte.js"],"names":[],"mappings":";;;;;AA4BA,sFAA6D;yCApBnB,cAAc"}
1
+ {"version":3,"file":"CustomProperty.svelte.d.ts","sourceRoot":"","sources":["../src/lib/CustomProperty.svelte.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,YAAY,CAAC;AAuBtD,QAAA,MAAM,cAAc,yDAAwC,CAAC;AAC7D,KAAK,cAAc,GAAG,UAAU,CAAC,OAAO,cAAc,CAAC,CAAC;AACxD,eAAe,cAAc,CAAC"}
@@ -1,10 +1,21 @@
1
+ /**
2
+ * A command as required by the key mapper: anything with is_enabled/execute.
3
+ */
4
+ type KeymapCommand = {
5
+ is_enabled: () => boolean;
6
+ execute: () => unknown;
7
+ };
8
+ /**
9
+ * A keymap maps key combo strings to arrays of commands.
10
+ */
11
+ export type Keymap = Record<string, KeymapCommand[]>;
1
12
  /**
2
13
  * Validates and defines a keymap.
3
14
  * Throws an error if any key combo is invalid.
4
15
  * Valid formats: 'meta+e,ctrl+e' or 'meta+shift+a'
5
16
  * Invalid: 'meta+e+a' (only one non-modifier key allowed)
6
17
  */
7
- export function define_keymap(keymap: any): any;
18
+ export declare function define_keymap<K extends Keymap>(keymap: K): K;
8
19
  /**
9
20
  * KeyMapper manages keyboard shortcuts using a stack-based scope system.
10
21
  *
@@ -17,20 +28,22 @@ export function define_keymap(keymap: any): any;
17
28
  * mapper.push_scope(editor_keymap); // When editor gains focus
18
29
  * mapper.pop_scope(); // When editor loses focus
19
30
  */
20
- export class KeyMapper {
21
- scope_stack: any[];
31
+ export declare class KeyMapper {
32
+ scope_stack: Keymap[];
22
33
  skip_onkeydown: boolean;
34
+ constructor();
23
35
  /**
24
36
  * Push a new scope onto the stack (becomes highest priority)
25
37
  */
26
- push_scope(keymap: any): void;
38
+ push_scope(keymap: Keymap): void;
27
39
  /**
28
40
  * Pop the most recent scope from the stack
29
41
  */
30
- pop_scope(): any;
42
+ pop_scope(): Keymap | undefined;
31
43
  /**
32
44
  * Handle keyboard event by trying scopes from top to bottom
33
45
  */
34
- handle_keydown(event: any): void;
46
+ handle_keydown(event: KeyboardEvent): void;
35
47
  }
48
+ export {};
36
49
  //# sourceMappingURL=KeyMapper.svelte.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"KeyMapper.svelte.d.ts","sourceRoot":"","sources":["../src/lib/KeyMapper.svelte.js"],"names":[],"mappings":"AAUA;;;;;GAKG;AACH,gDAgBC;AAuED;;;;;;;;;;;GAWG;AACH;IAEE,mBAAqB;IACrB,wBAA2B;IAG5B;;OAEG;IACH,8BAGC;IAED;;OAEG;IACH,iBAIC;IAED;;OAEG;IACH,iCAUC;CACD"}
1
+ {"version":3,"file":"KeyMapper.svelte.d.ts","sourceRoot":"","sources":["../src/lib/KeyMapper.svelte.ts"],"names":[],"mappings":"AAUA;;GAEG;AACH,KAAK,aAAa,GAAG;IAAE,UAAU,EAAE,MAAM,OAAO,CAAC;IAAC,OAAO,EAAE,MAAM,OAAO,CAAA;CAAE,CAAC;AAE3E;;GAEG;AACH,MAAM,MAAM,MAAM,GAAG,MAAM,CAAC,MAAM,EAAE,aAAa,EAAE,CAAC,CAAC;AAErD;;;;;GAKG;AACH,wBAAgB,aAAa,CAAC,CAAC,SAAS,MAAM,EAAE,MAAM,EAAE,CAAC,GAAG,CAAC,CAgB5D;AA2ED;;;;;;;;;;;GAWG;AACH,qBAAa,SAAS;IACrB,WAAW,EAAE,MAAM,EAAE,CAAC;IACtB,cAAc,EAAE,OAAO,CAAC;;IAOxB;;OAEG;IACH,UAAU,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI;IAKhC;;OAEG;IACH,SAAS,IAAI,MAAM,GAAG,SAAS;IAM/B;;OAEG;IACH,cAAc,CAAC,KAAK,EAAE,aAAa,GAAG,IAAI;CAW1C"}
@@ -1,13 +1,11 @@
1
1
  import { is_virtual_keyboard_active } from './utils.js';
2
-
3
2
  const MODIFIER_KEYS = ['meta', 'ctrl', 'alt', 'shift'];
4
3
  const MODIFIER_EVENT_KEYS = {
5
- meta: 'metaKey',
6
- ctrl: 'ctrlKey',
7
- alt: 'altKey',
8
- shift: 'shiftKey'
4
+ meta: 'metaKey',
5
+ ctrl: 'ctrlKey',
6
+ alt: 'altKey',
7
+ shift: 'shiftKey'
9
8
  };
10
-
11
9
  /**
12
10
  * Validates and defines a keymap.
13
11
  * Throws an error if any key combo is invalid.
@@ -15,58 +13,48 @@ const MODIFIER_EVENT_KEYS = {
15
13
  * Invalid: 'meta+e+a' (only one non-modifier key allowed)
16
14
  */
17
15
  export function define_keymap(keymap) {
18
- for (const [key_combo] of Object.entries(keymap)) {
19
- const alternatives = key_combo.split(',');
20
-
21
- for (const alternative of alternatives) {
22
- const parts = alternative.trim().toLowerCase().split('+');
23
- const non_modifiers = parts.filter((part) => !MODIFIER_KEYS.includes(part));
24
-
25
- if (non_modifiers.length !== 1) {
26
- throw new Error(
27
- `Invalid key combo: "${alternative}". Must have exactly one non-modifier key. Found: ${non_modifiers.length}`
28
- );
29
- }
30
- }
31
- }
32
- return keymap;
16
+ for (const [key_combo] of Object.entries(keymap)) {
17
+ const alternatives = key_combo.split(',');
18
+ for (const alternative of alternatives) {
19
+ const parts = alternative.trim().toLowerCase().split('+');
20
+ const non_modifiers = parts.filter((part) => !MODIFIER_KEYS.includes(part));
21
+ if (non_modifiers.length !== 1) {
22
+ throw new Error(`Invalid key combo: "${alternative}". Must have exactly one non-modifier key. Found: ${non_modifiers.length}`);
23
+ }
24
+ }
25
+ }
26
+ return keymap;
33
27
  }
34
-
35
28
  /**
36
29
  * Matches a keyboard event against a key combo string.
37
30
  * Example: 'meta+e,ctrl+e' matches either (metaKey && key==='e') OR (ctrlKey && key==='e')
38
31
  */
39
32
  function matches_key_combo(key_combo, event, virtual_keyboard_active = false) {
40
- const alternatives = key_combo.split(',');
41
-
42
- return alternatives.some((alternative) => {
43
- const parts = alternative.trim().toLowerCase().split('+');
44
- const modifiers = parts.filter((part) => MODIFIER_KEYS.includes(part));
45
- const non_modifier = parts.find((part) => !MODIFIER_KEYS.includes(part));
46
-
47
- if (virtual_keyboard_active && modifiers.length > 0) {
48
- return false;
49
- }
50
-
51
- // Check if all specified modifiers are pressed
52
- const modifiers_match = modifiers.every((mod) => event[MODIFIER_EVENT_KEYS[mod]]);
53
-
54
- // Check if no unspecified modifiers are pressed
55
- // NOTE: On virtual keyboards (iOS / Anroid) modifier keys are just ignored, because
56
- // they must be assumed accidental (e.g. Shift activated as a result of auto-capitalization)
57
- const no_extra_modifiers = virtual_keyboard_active
58
- ? true
59
- : MODIFIER_KEYS.every((mod) => {
60
- if (modifiers.includes(mod)) return true; // This modifier is expected
61
- return !event[MODIFIER_EVENT_KEYS[mod]]; // This modifier should NOT be pressed
62
- });
63
-
64
- // Check if the key matches
65
- const key_matches = event.key.toLowerCase() === non_modifier;
66
- return modifiers_match && no_extra_modifiers && key_matches;
67
- });
33
+ const alternatives = key_combo.split(',');
34
+ return alternatives.some((alternative) => {
35
+ const parts = alternative.trim().toLowerCase().split('+');
36
+ const modifiers = parts.filter((part) => MODIFIER_KEYS.includes(part));
37
+ const non_modifier = parts.find((part) => !MODIFIER_KEYS.includes(part));
38
+ if (virtual_keyboard_active && modifiers.length > 0) {
39
+ return false;
40
+ }
41
+ // Check if all specified modifiers are pressed
42
+ const modifiers_match = modifiers.every((mod) => event[MODIFIER_EVENT_KEYS[mod]]);
43
+ // Check if no unspecified modifiers are pressed
44
+ // NOTE: On virtual keyboards (iOS / Anroid) modifier keys are just ignored, because
45
+ // they must be assumed accidental (e.g. Shift activated as a result of auto-capitalization)
46
+ const no_extra_modifiers = virtual_keyboard_active
47
+ ? true
48
+ : MODIFIER_KEYS.every((mod) => {
49
+ if (modifiers.includes(mod))
50
+ return true; // This modifier is expected
51
+ return !event[MODIFIER_EVENT_KEYS[mod]]; // This modifier should NOT be pressed
52
+ });
53
+ // Check if the key matches
54
+ const key_matches = event.key.toLowerCase() === non_modifier;
55
+ return modifiers_match && no_extra_modifiers && key_matches;
56
+ });
68
57
  }
69
-
70
58
  /**
71
59
  * Handles a key map by matching keyboard event against registered key combos
72
60
  * and executing the first enabled command.
@@ -75,32 +63,27 @@ function matches_key_combo(key_combo, event, virtual_keyboard_active = false) {
75
63
  * but don't crash the application.
76
64
  */
77
65
  function handle_key_map(key_map, event) {
78
- const virtual_keyboard_active = is_virtual_keyboard_active();
79
-
80
- for (const [key_combo, commands] of Object.entries(key_map)) {
81
- if (matches_key_combo(key_combo, event, virtual_keyboard_active)) {
82
- // Find the first enabled command and execute it
83
- const enabled_command = commands.find((cmd) => cmd.is_enabled());
84
- if (enabled_command) {
85
- event.preventDefault();
86
-
87
- // Execute command (may be sync or async)
88
- const result = enabled_command.execute();
89
-
90
- // If it's a promise, handle errors (fire-and-forget)
91
- if (result instanceof Promise) {
92
- result.catch((err) => {
93
- console.error('Command execution failed:', err);
94
- });
95
- }
96
-
97
- return true;
98
- }
99
- }
100
- }
101
- return false;
66
+ const virtual_keyboard_active = is_virtual_keyboard_active();
67
+ for (const [key_combo, commands] of Object.entries(key_map)) {
68
+ if (matches_key_combo(key_combo, event, virtual_keyboard_active)) {
69
+ // Find the first enabled command and execute it
70
+ const enabled_command = commands.find((cmd) => cmd.is_enabled());
71
+ if (enabled_command) {
72
+ event.preventDefault();
73
+ // Execute command (may be sync or async)
74
+ const result = enabled_command.execute();
75
+ // If it's a promise, handle errors (fire-and-forget)
76
+ if (result instanceof Promise) {
77
+ result.catch((err) => {
78
+ console.error('Command execution failed:', err);
79
+ });
80
+ }
81
+ return true;
82
+ }
83
+ }
84
+ }
85
+ return false;
102
86
  }
103
-
104
87
  /**
105
88
  * KeyMapper manages keyboard shortcuts using a stack-based scope system.
106
89
  *
@@ -114,40 +97,40 @@ function handle_key_map(key_map, event) {
114
97
  * mapper.pop_scope(); // When editor loses focus
115
98
  */
116
99
  export class KeyMapper {
117
- constructor() {
118
- this.scope_stack = [];
119
- this.skip_onkeydown = false;
120
- }
121
-
122
- /**
123
- * Push a new scope onto the stack (becomes highest priority)
124
- */
125
- push_scope(keymap) {
126
- // console.log('pushed keymap', keymap);
127
- this.scope_stack.push(keymap);
128
- }
129
-
130
- /**
131
- * Pop the most recent scope from the stack
132
- */
133
- pop_scope() {
134
- const keymap = this.scope_stack.pop();
135
- // console.log('popped keymap', keymap);
136
- return keymap;
137
- }
138
-
139
- /**
140
- * Handle keyboard event by trying scopes from top to bottom
141
- */
142
- handle_keydown(event) {
143
- // Key handling temporarily disabled (e.g. while character composition takes place)
144
- if (this.skip_onkeydown) return;
145
- // console.log('KeyMapper.handle_keydown', event);
146
- // Try from most specific (top of stack) to most general (bottom)
147
- for (let i = this.scope_stack.length - 1; i >= 0; i--) {
148
- if (handle_key_map(this.scope_stack[i], event)) {
149
- return;
150
- }
151
- }
152
- }
100
+ scope_stack;
101
+ skip_onkeydown;
102
+ constructor() {
103
+ this.scope_stack = [];
104
+ this.skip_onkeydown = false;
105
+ }
106
+ /**
107
+ * Push a new scope onto the stack (becomes highest priority)
108
+ */
109
+ push_scope(keymap) {
110
+ // console.log('pushed keymap', keymap);
111
+ this.scope_stack.push(keymap);
112
+ }
113
+ /**
114
+ * Pop the most recent scope from the stack
115
+ */
116
+ pop_scope() {
117
+ const keymap = this.scope_stack.pop();
118
+ // console.log('popped keymap', keymap);
119
+ return keymap;
120
+ }
121
+ /**
122
+ * Handle keyboard event by trying scopes from top to bottom
123
+ */
124
+ handle_keydown(event) {
125
+ // Key handling temporarily disabled (e.g. while character composition takes place)
126
+ if (this.skip_onkeydown)
127
+ return;
128
+ // console.log('KeyMapper.handle_keydown', event);
129
+ // Try from most specific (top of stack) to most general (bottom)
130
+ for (let i = this.scope_stack.length - 1; i >= 0; i--) {
131
+ if (handle_key_map(this.scope_stack[i], event)) {
132
+ return;
133
+ }
134
+ }
135
+ }
153
136
  }
package/dist/Node.svelte CHANGED
@@ -1,19 +1,22 @@
1
- <script>
1
+ <script lang="ts">
2
2
  import { getContext } from 'svelte';
3
3
  import { serialize_path } from './utils.js';
4
+ import type {
5
+ NodeArrayAttachmentContext,
6
+ NodeArrayRenderContext,
7
+ NodeProps,
8
+ SveditRenderContext
9
+ } from './types.js';
4
10
 
5
- /** @import { NodeProps } from './types.d.ts'; */
11
+ const svedit = getContext<SveditRenderContext>('svedit');
6
12
 
7
- const svedit = getContext('svedit');
8
-
9
- /** @type {NodeProps} */
10
- let { path, children, tag = 'div', class: css_class, style = '', ...rest } = $props();
13
+ let { path, children, tag = 'div', class: css_class, style = '', ...rest }: NodeProps = $props();
11
14
 
12
15
  let node = $derived(svedit.session.get(path));
13
16
  let path_str = $derived(serialize_path(path));
14
17
 
15
- const node_array_meta = getContext('node_array_meta');
16
- let child_index = $derived(node_array_meta ? parseInt(String(path.at(-1)), 10) : -1);
18
+ const node_array_meta = getContext<NodeArrayRenderContext | undefined>('node_array_meta');
19
+ let child_index = $derived(node_array_meta ? (path.at(-1) as number) : -1);
17
20
  let is_first = $derived(node_array_meta && child_index === 0);
18
21
  let is_last = $derived(node_array_meta && child_index === node_array_meta.length - 1);
19
22
 
@@ -25,9 +28,9 @@
25
28
  // `annotations` props.
26
29
  let range_classes = $derived.by(() => {
27
30
  if (child_index < 0 || !node_array_meta?.annotations_for) return '';
28
- const classes = [];
31
+ const classes: string[] = [];
29
32
 
30
- const add_classes = (range, prefix) => {
33
+ const add_classes = (range: NodeArrayAttachmentContext | null | undefined, prefix: string) => {
31
34
  const range_type = range?.node?.type;
32
35
  if (!range_type) return;
33
36
  classes.push(`${prefix}-${range_type}`);
@@ -46,9 +49,9 @@
46
49
  <svelte:element
47
50
  this={tag}
48
51
  id={node.id}
49
- class="node-{node.type} {css_class}{range_classes
50
- ? ` ${range_classes}`
51
- : ''}{is_first ? ' first' : ''}{is_last ? ' last' : ''}"
52
+ class="node-{node.type} {css_class}{range_classes ? ` ${range_classes}` : ''}{is_first
53
+ ? ' first'
54
+ : ''}{is_last ? ' last' : ''}"
52
55
  data-node-id={node.id}
53
56
  data-path={path_str}
54
57
  data-type="node"
@@ -1,7 +1,5 @@
1
+ import type { NodeProps } from './types.js';
2
+ declare const Node: import("svelte").Component<NodeProps, {}, "">;
3
+ type Node = ReturnType<typeof Node>;
1
4
  export default Node;
2
- type Node = {
3
- $on?(type: string, callback: (e: any) => void): () => void;
4
- $set?(props: Partial<NodeProps>): void;
5
- };
6
- declare const Node: import("svelte").Component<import("./types.d.ts").NodeProps, {}, "">;
7
5
  //# sourceMappingURL=Node.svelte.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"Node.svelte.d.ts","sourceRoot":"","sources":["../src/lib/Node.svelte.js"],"names":[],"mappings":";;;;;AA6DA,yFAAmD"}
1
+ {"version":3,"file":"Node.svelte.d.ts","sourceRoot":"","sources":["../src/lib/Node.svelte.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAGV,SAAS,EAET,MAAM,YAAY,CAAC;AAuDrB,QAAA,MAAM,IAAI,+CAAwC,CAAC;AACnD,KAAK,IAAI,GAAG,UAAU,CAAC,OAAO,IAAI,CAAC,CAAC;AACpC,eAAe,IAAI,CAAC"}
@@ -1,20 +1,33 @@
1
- <script>
1
+ <script lang="ts">
2
2
  import { getContext, setContext } from 'svelte';
3
3
  import UnknownNode from './UnknownNode.svelte';
4
4
  import { serialize_path, calculate_fragment_ranges } from './utils.js';
5
5
  import DefaultNodeGap from './NodeGap.svelte';
6
6
  import DefaultNodeGapMarkers from './NodeGapMarkers.svelte';
7
-
8
- /** @import { NodeArrayPropertyProps, NodeArrayAttachmentContext } from './types.d.ts'; */
9
-
10
- const svedit = getContext('svedit');
7
+ import type {
8
+ NodeArrayPropertyProps,
9
+ NodeArrayAttachmentContext,
10
+ NodeArrayFragment,
11
+ NodeId,
12
+ Attachment,
13
+ Mark,
14
+ NodeArrayRenderContext,
15
+ SveditRenderContext
16
+ } from './types.js';
17
+
18
+ const svedit = getContext<SveditRenderContext>('svedit');
11
19
  let NodeGap = $derived(svedit.session.config.system_components?.node_gap ?? DefaultNodeGap);
12
20
  let NodeGapMarkers = $derived(
13
21
  svedit.session.config.system_components?.node_gap_markers ?? DefaultNodeGapMarkers
14
22
  );
15
23
 
16
- /** @type {NodeArrayPropertyProps} */
17
- let { path, tag = 'div', class: css_class, style = '', ...rest } = $props();
24
+ let {
25
+ path,
26
+ tag = 'div',
27
+ class: css_class,
28
+ style = '',
29
+ ...rest
30
+ }: NodeArrayPropertyProps = $props();
18
31
 
19
32
  // Pre-joined once per path change; reused by data-path and by every
20
33
  // NodeGap's should_position_gap call to avoid N+1 joins per render.
@@ -27,9 +40,9 @@
27
40
 
28
41
  let fragments = $derived(get_fragments(node_ids, marks));
29
42
 
30
- function get_fragments(node_ids, marks) {
43
+ function get_fragments(node_ids: NodeId[], marks: Mark[]): NodeArrayFragment[] {
31
44
  const ranges = calculate_fragment_ranges(node_ids.length, marks);
32
- let fragments = [];
45
+ const fragments: NodeArrayFragment[] = [];
33
46
 
34
47
  for (const range of ranges) {
35
48
  const nodes_slice = node_ids.slice(range.start_offset, range.end_offset);
@@ -41,7 +54,7 @@
41
54
  node,
42
55
  nodes: nodes_slice,
43
56
  start_index: range.start_offset,
44
- mark_index: range.mark_index
57
+ mark_index: range.mark_index!
45
58
  });
46
59
  } else if (range.type === 'content') {
47
60
  fragments.push({
@@ -54,7 +67,7 @@
54
67
  return fragments;
55
68
  }
56
69
 
57
- function get_node_key(node_id, index) {
70
+ function get_node_key(node_id: NodeId, index: number): string {
58
71
  let occurrence = 0;
59
72
  for (let current_index = 0; current_index < index; current_index++) {
60
73
  if (node_ids[current_index] === node_id) occurrence += 1;
@@ -62,10 +75,11 @@
62
75
  return `${node_id}:${occurrence}`;
63
76
  }
64
77
 
65
- /**
66
- * @returns {NodeArrayAttachmentContext}
67
- */
68
- function get_range_context(range, index, node_index) {
78
+ function get_range_context(
79
+ range: Attachment,
80
+ index: number,
81
+ node_index: number
82
+ ): NodeArrayAttachmentContext {
69
83
  const node = svedit.session.get(range.node_id);
70
84
  const is_start = node_index === range.start_offset;
71
85
  const is_end = node_index === range.end_offset - 1;
@@ -80,18 +94,21 @@
80
94
  };
81
95
  }
82
96
 
83
- function get_covering_ranges(ranges, node_index) {
97
+ function get_covering_ranges(
98
+ ranges: Attachment[],
99
+ node_index: number
100
+ ): NodeArrayAttachmentContext[] {
84
101
  return ranges
85
102
  .map((range, index) => ({ range, index }))
86
103
  .filter(({ range }) => range.start_offset <= node_index && node_index < range.end_offset)
87
104
  .map(({ range, index }) => get_range_context(range, index, node_index));
88
105
  }
89
106
 
90
- function get_annotation_contexts(node_index) {
107
+ function get_annotation_contexts(node_index: number): NodeArrayAttachmentContext[] {
91
108
  return get_covering_ranges(annotations, node_index);
92
109
  }
93
110
 
94
- function get_mark(node_index) {
111
+ function get_mark(node_index: number): NodeArrayAttachmentContext | null {
95
112
  // The single mark wrapping this node, or null. Mark exclusivity
96
113
  // guarantees at most one. Annotations never wrap and are exposed via
97
114
  // `annotations` instead.
@@ -107,17 +124,17 @@
107
124
  serialize_path(svedit.session.selection.path) === path_str
108
125
  );
109
126
 
110
- setContext('node_array_meta', {
127
+ setContext<NodeArrayRenderContext>('node_array_meta', {
111
128
  get length() {
112
129
  return node_ids.length;
113
130
  },
114
131
  // Lets Node self-serve the marks and annotations covering a child, so
115
132
  // node wrappers can carry range classes without every node component
116
133
  // having to thread the `mark`/`annotations` props through.
117
- mark_for(node_index) {
134
+ mark_for(node_index: number) {
118
135
  return get_mark(node_index);
119
136
  },
120
- annotations_for(node_index) {
137
+ annotations_for(node_index: number) {
121
138
  return get_annotation_contexts(node_index);
122
139
  }
123
140
  });
@@ -145,7 +162,7 @@
145
162
  <NodeGap array_path={path} offset={0} count={0} empty />
146
163
  </div>
147
164
  {/if}
148
- {#snippet render_nodes(nodes_slice, start_index)}
165
+ {#snippet render_nodes(nodes_slice: NodeId[], start_index: number)}
149
166
  {#each nodes_slice as id, slice_index (get_node_key(id, start_index + slice_index))}
150
167
  {@const index = start_index + slice_index}
151
168
  {@const node = svedit.session.get(id)}
@@ -1,7 +1,5 @@
1
+ import type { NodeArrayPropertyProps } from './types.js';
2
+ declare const NodeArrayProperty: import("svelte").Component<NodeArrayPropertyProps, {}, "">;
3
+ type NodeArrayProperty = ReturnType<typeof NodeArrayProperty>;
1
4
  export default NodeArrayProperty;
2
- type NodeArrayProperty = {
3
- $on?(type: string, callback: (e: any) => void): () => void;
4
- $set?(props: Partial<NodeArrayPropertyProps>): void;
5
- };
6
- declare const NodeArrayProperty: import("svelte").Component<import("./types.d.ts").NodeArrayPropertyProps, {}, "">;
7
5
  //# sourceMappingURL=NodeArrayProperty.svelte.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"NodeArrayProperty.svelte.d.ts","sourceRoot":"","sources":["../src/lib/NodeArrayProperty.svelte.js"],"names":[],"mappings":";;;;;AAuLA,mHAAgE"}
1
+ {"version":3,"file":"NodeArrayProperty.svelte.d.ts","sourceRoot":"","sources":["../src/lib/NodeArrayProperty.svelte.ts"],"names":[],"mappings":"AAQA,OAAO,KAAK,EACV,sBAAsB,EAQtB,MAAM,YAAY,CAAC;AAwLrB,QAAA,MAAM,iBAAiB,4DAAwC,CAAC;AAChE,KAAK,iBAAiB,GAAG,UAAU,CAAC,OAAO,iBAAiB,CAAC,CAAC;AAC9D,eAAe,iBAAiB,CAAC"}
@@ -1,4 +1,4 @@
1
- <script>
1
+ <script lang="ts">
2
2
  /**
3
3
  * Visual insertion caret rendered inside the active insertion marker.
4
4
  *
@@ -30,7 +30,7 @@
30
30
  --_cp: var(--node-caret-row-inline-position, 50%);
31
31
  content: '';
32
32
  position: absolute;
33
- background: var(--node-caret-bg, var(--svedit-editing-stroke));
33
+ background: var(--node-caret-bg, var(--editing));
34
34
  /* Increase the visibility of the caret by contrasting it with a box shadow that's the inverted brightness of the current text color. */
35
35
  /* Component developers must set their background color and text color on the node itself, not a child element, for this to work. */
36
36
  box-shadow: var(--node-caret-shadow, 0 0 0 0.5px oklch(from currentColor calc(1 - l) c h));
@@ -1,18 +1,5 @@
1
- export default NodeCaret;
2
- type NodeCaret = SvelteComponent<{
3
- [x: string]: never;
4
- }, {
5
- [evt: string]: CustomEvent<any>;
6
- }, {}> & {
7
- $$bindings?: string;
8
- };
9
- declare const NodeCaret: $$__sveltets_2_IsomorphicComponent<{
10
- [x: string]: never;
11
- }, {
12
- [evt: string]: CustomEvent<any>;
13
- }, {}, {}, string>;
14
1
  interface $$__sveltets_2_IsomorphicComponent<Props extends Record<string, any> = any, Events extends Record<string, any> = any, Slots extends Record<string, any> = any, Exports = {}, Bindings = string> {
15
- new (options: import("svelte").ComponentConstructorOptions<Props>): import("svelte").SvelteComponent<Props, Events, Slots> & {
2
+ new (options: import('svelte').ComponentConstructorOptions<Props>): import('svelte').SvelteComponent<Props, Events, Slots> & {
16
3
  $$bindings?: Bindings;
17
4
  } & Exports;
18
5
  (internal: unknown, props: {
@@ -24,4 +11,9 @@ interface $$__sveltets_2_IsomorphicComponent<Props extends Record<string, any> =
24
11
  };
25
12
  z_$$bindings?: Bindings;
26
13
  }
14
+ declare const NodeCaret: $$__sveltets_2_IsomorphicComponent<Record<string, never>, {
15
+ [evt: string]: CustomEvent<any>;
16
+ }, {}, {}, string>;
17
+ type NodeCaret = InstanceType<typeof NodeCaret>;
18
+ export default NodeCaret;
27
19
  //# sourceMappingURL=NodeCaret.svelte.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"NodeCaret.svelte.d.ts","sourceRoot":"","sources":["../src/lib/NodeCaret.svelte.js"],"names":[],"mappings":";;;;;;;;AA4BA;;;;mBAAqH;6CATxE,KAAK,SAAS,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,QAAQ,MAAM,SAAS,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,QAAQ,KAAK,SAAS,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,QAAQ,OAAO,OAAO,QAAQ;IAC3L,cAAc,OAAO,QAAQ,EAAE,2BAA2B,CAAC,KAAK,CAAC,GAAG,OAAO,QAAQ,EAAE,eAAe,CAAC,KAAK,EAAE,MAAM,EAAE,KAAK,CAAC,GAAG;QAAE,UAAU,CAAC,EAAE,QAAQ,CAAA;KAAE,GAAG,OAAO,CAAC;IACjK,WAAW,OAAO,SAAS;QAAC,QAAQ,CAAC,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,KAAK,CAAA;KAAC,GAAG,OAAO,GAAG;QAAE,IAAI,CAAC,EAAE,GAAG,CAAC;QAAC,GAAG,CAAC,EAAE,GAAG,CAAA;KAAE,CAAC;IACtG,eAAe,QAAQ,CAAC"}
1
+ {"version":3,"file":"NodeCaret.svelte.d.ts","sourceRoot":"","sources":["../src/lib/NodeCaret.svelte.ts"],"names":[],"mappings":"AAmBA,UAAU,kCAAkC,CAAC,KAAK,SAAS,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,GAAG,EAAE,MAAM,SAAS,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,GAAG,EAAE,KAAK,SAAS,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,GAAG,EAAE,OAAO,GAAG,EAAE,EAAE,QAAQ,GAAG,MAAM;IACpM,KAAK,OAAO,EAAE,OAAO,QAAQ,EAAE,2BAA2B,CAAC,KAAK,CAAC,GAAG,OAAO,QAAQ,EAAE,eAAe,CAAC,KAAK,EAAE,MAAM,EAAE,KAAK,CAAC,GAAG;QAAE,UAAU,CAAC,EAAE,QAAQ,CAAA;KAAE,GAAG,OAAO,CAAC;IACjK,CAAC,QAAQ,EAAE,OAAO,EAAE,KAAK,EAAE;QAAC,QAAQ,CAAC,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,KAAK,CAAA;KAAC,GAAG,OAAO,GAAG;QAAE,IAAI,CAAC,EAAE,GAAG,CAAC;QAAC,GAAG,CAAC,EAAE,GAAG,CAAA;KAAE,CAAC;IACtG,YAAY,CAAC,EAAE,QAAQ,CAAC;CAC3B;AAKD,QAAA,MAAM,SAAS;;kBAA+E,CAAC;AAC7E,KAAK,SAAS,GAAG,YAAY,CAAC,OAAO,SAAS,CAAC,CAAC;AAClD,eAAe,SAAS,CAAC"}