@embedpdf/plugin-interaction 3.0.0-next.14 → 3.0.0-next.15

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.
@@ -1,239 +0,0 @@
1
- import { PageObjectNumber } from "@embedpdf/core";
2
- import { PageRotation, Point } from "@embedpdf/core-geometry";
3
- //#region src/types.d.ts
4
- type ToolId = string;
5
- type Cursor = string;
6
- interface Modifiers {
7
- shift: boolean;
8
- alt: boolean;
9
- ctrl: boolean;
10
- meta: boolean;
11
- }
12
- /**
13
- * The single active arbiter of what the pointer does. `pan` and `pointer` are
14
- * built in; features add more (`highlight`, `square`, `redact`…) via
15
- * `registerTool`. A tool carries no behaviour itself — it turns on capability
16
- * TAGS that handlers opt into (`enables`), so tools compose features without
17
- * coupling to them.
18
- */
19
- interface Tool {
20
- id: ToolId;
21
- cursor: Cursor;
22
- /**
23
- * Cursor over the viewport's page GAPS. A tool's cursor answers "what would
24
- * a click do here" — and most tools act only on pages, so gaps fall back to
25
- * the neutral arrow (`'default'`). A tool that works anywhere (pan) declares
26
- * its own (`'grab'`). Hover claims still outrank both.
27
- */
28
- gapCursor?: Cursor;
29
- enables: ReadonlySet<string>;
30
- /**
31
- * TOUCH CONSENT, rung 1 — "arming this tool is consent to create with a
32
- * finger": while it is active, single-finger touch routes to the hub
33
- * wholesale (draw/markup/redact tools), and navigation moves to two
34
- * fingers — the drawing-app convention. Default false: a finger navigates
35
- * first, and only per-point claims ({@link InteractionHandler.claimsTouch})
36
- * carve out tool gestures.
37
- */
38
- touchDirect?: boolean;
39
- }
40
- type Phase = 'down' | 'move' | 'up' | 'cancel';
41
- /** The physical device class behind a sample — `PointerEvent.pointerType`.
42
- * Adapters fill it so handlers (and arbitration above the hub) can apply
43
- * modality policy: touch navigates first, pen/mouse are tool-first. */
44
- type PointerKind = 'mouse' | 'pen' | 'touch';
45
- /**
46
- * One normalized pointer event. `viewport` is the source container's px (the pan
47
- * handler uses the delta). `page` is the resolved page hit — its `pon` + content
48
- * point (y-down, PDF units, via the page's transform) — present when the pointer
49
- * is over a page, absent over gaps. A viewport source (Stage) resolves `page` per
50
- * event (so a drag can cross pages); a per-page source (PageView) always sets it.
51
- */
52
- interface PointerSample {
53
- phase: Phase;
54
- viewport: Point;
55
- /** `scale` is the hit page's VIEW px per content unit — handlers use it to
56
- * convert screen-px chrome settings into content-space tolerances, so grab
57
- * zones stay screen-constant across zoom. `rotation` is the hit page's TOTAL
58
- * display rotation (document /Rotate + view rotation) — per-event
59
- * environmental context like `scale`, for placement rules that depend on how
60
- * the page is DISPLAYED (an upright stamp). `zoom` is the page's zoom
61
- * RELATIVE to its 100% baseline (`transform.zoom` — dimensionless, 1 =
62
- * Acrobat's 100%), for zoom-relative policies (the `/F` NoZoom exemption);
63
- * distinct from `scale`, which is a units conversion. Absent when the
64
- * source can't say. */
65
- page?: {
66
- pon: PageObjectNumber;
67
- point: Point;
68
- scale?: number;
69
- rotation?: PageRotation;
70
- zoom?: number;
71
- };
72
- modifiers: Modifiers;
73
- /**
74
- * Click count for a `down` (1 = single, 2 = double, 3 = triple), from the
75
- * browser's native multi-click detection (`MouseEvent.detail`). Lets handlers
76
- * do word/line selection without re-implementing timing. Defaults to 1.
77
- */
78
- clickCount?: number;
79
- /** The device class that produced this sample (see {@link PointerKind}).
80
- * Absent when the source can't say — treat as 'mouse'. */
81
- pointerType?: PointerKind;
82
- /**
83
- * Present when the sample was SYNTHESIZED from a recognized gesture rather
84
- * than a raw press. 'long-press': a touch contact held still — the gesture
85
- * controller forwards it as a down (with `clickCount: 2`, so word-selection
86
- * keeps working unchanged), and this marker is the honest signal for
87
- * handlers that must tell a long-press from a genuine double-click
88
- * (haptics, pickup affordances). Absent on every raw pointer sample.
89
- */
90
- gesture?: 'long-press';
91
- /**
92
- * The LENS this sample came from — the stage plugin id the emitting surface
93
- * binding was attached to (a document may be viewed through several stage
94
- * lenses at once). Handlers registered with a matching `source` scope only
95
- * see their own lens's input, so one lens's drag can never be captured by
96
- * another lens's handler. Absent when the source doesn't say (custom
97
- * dispatchers, single-lens embeds) — such samples route to every handler.
98
- */
99
- source?: string;
100
- /**
101
- * Project this event onto a SPECIFIC page's content space, unclamped — valid
102
- * (and expected) outside the page's bounds. `page` answers "what is under the
103
- * cursor" and re-resolves per event; `project` answers "where is the cursor
104
- * in MY page's frame" for a gesture anchored to the page it started on (an
105
- * annotation drag sliding along the page edge). Null when the source can't
106
- * project onto that page (not laid out / a per-page source's foreign page).
107
- */
108
- project?(pon: PageObjectNumber): Point | null;
109
- }
110
- /**
111
- * A pointer handler contributed by a feature plugin. The ONE registration
112
- * mechanism (replacing v2's registerMode / registerHandlers / registerAlways /
113
- * enableForMode quartet): a handler declares which tools it's live under and a
114
- * priority; the hub routes each gesture to the first handler that captures it.
115
- */
116
- interface InteractionHandler {
117
- id: string;
118
- /** Higher wins the gesture. */
119
- priority: number;
120
- /** Usually `tool.enables.has('my-tag')`. */
121
- enabledFor(tool: Tool): boolean;
122
- /** Return true to CAPTURE: subsequent move/up route here until pointer-up. */
123
- onDown(sample: PointerSample): boolean;
124
- onMove?(sample: PointerSample): void;
125
- onUp?(sample: PointerSample): void;
126
- /**
127
- * The gesture was ABORTED, not completed — the pointer was cancelled by the
128
- * system, or navigation took it over (a second finger converted the drag
129
- * into a pinch). Discard the in-flight work instead of committing it (a
130
- * half-drawn shape, a mid-drag selection). Falls back to {@link onUp} when
131
- * absent, since committing is the lesser evil to a stuck gesture.
132
- */
133
- onCancel?(sample: PointerSample): void;
134
- /** Pointer moved with no active gesture — cursor feedback only. */
135
- onHover?(sample: PointerSample): void;
136
- /**
137
- * TOUCH CONSENT, rung 2 — "the selected thing owns its drags". Touch
138
- * navigation asks this BEFORE a contact is classified: return true and the
139
- * whole contact routes to the hub as a tool gesture (down/move/up) instead
140
- * of pan/pinch/tap. Implement it ONLY where the user has already narrowed
141
- * intent to this point — the annotation handler claims the selected
142
- * annotation's body and its handles, nothing else. A pure read: it must
143
- * not mutate anything (the down that follows does the mutating). Handlers
144
- * without it never claim, so plain surfaces keep navigating.
145
- */
146
- claimsTouch?(sample: PointerSample): boolean;
147
- }
148
- /**
149
- * A tool's runtime cursor skin: "while THIS tool is armed, keyword X looks
150
- * like Y." Everything cursor-shaped in the hub speaks KEYWORDS — a tool
151
- * declares its base ('crosshair', 'copy'), hover claims name what is under
152
- * the pointer ('text' over text, 'move' over an annotation) — and the skin
153
- * restyles those keywords, typically as image cursors carrying the tool's
154
- * icon. Applied uniformly to the winning claim and to the declared base, so
155
- * same keyword = same meaning = same look. Unmapped keywords render as-is (a
156
- * foreign 'move' over an annotation drops the tool identity), and page gaps
157
- * are never skinned — the identity appears exactly where the action is
158
- * possible, and the skin can only restyle where the tool already acts.
159
- */
160
- type ToolCursorSkin = Record<Cursor, Cursor>;
161
- interface InteractionState {
162
- activeToolId: ToolId;
163
- cursor: Cursor;
164
- }
165
- type InteractionAction = {
166
- type: 'SET_TOOL';
167
- toolId: ToolId;
168
- } | {
169
- type: 'SET_CURSOR';
170
- cursor: Cursor;
171
- };
172
- interface InteractionCapability {
173
- activeTool(): Tool;
174
- activeToolId(): ToolId;
175
- cursor(): Cursor;
176
- tools(): Tool[];
177
- activateTool(id: ToolId): void;
178
- /** Fires after the active tool changes — lets a feature react (e.g. a markup
179
- * tool taking over the selection visual). Returns an unsubscribe fn. */
180
- onToolChange(cb: () => void): () => void;
181
- /**
182
- * Reskin a tool's cursor keywords at runtime — how an app gives the armed
183
- * tool an image cursor built from its own toolbar icon (`Cursor` is any CSS
184
- * cursor string, `url(data:…) x y, crosshair` included). See
185
- * {@link ToolCursorSkin} for what the map means. `null` removes the skin.
186
- */
187
- setToolCursor(id: ToolId, skin: ToolCursorSkin | null): void;
188
- registerTool(tool: Tool): () => void;
189
- /**
190
- * Register a pointer handler. `source` scopes it to ONE lens: the handler
191
- * then only sees samples stamped with that source (see
192
- * {@link PointerSample.source}) — mandatory for per-lens handlers like the
193
- * stage's pan-scroll, or two stages on one document would capture each
194
- * other's drags. UNSTAMPED samples still route everywhere (only a definite
195
- * mismatch filters), so custom dispatchers keep working.
196
- */
197
- registerHandler(handler: InteractionHandler, options?: {
198
- source?: string;
199
- }): () => void;
200
- setCursor(token: string, cursor: Cursor | null, priority?: number): void;
201
- dispatch(sample: PointerSample): void;
202
- /**
203
- * The touch-arbitration pre-flight: would any eligible handler claim a
204
- * contact at this sample ({@link InteractionHandler.claimsTouch})? Walked
205
- * in the same priority order `dispatch` uses, first claim wins. Pure —
206
- * nothing is captured or mutated; the gesture controller calls it at
207
- * touch-down to route the contact (tool vs navigation), then dispatches
208
- * normally.
209
- */
210
- wouldClaimTouch(sample: PointerSample): boolean;
211
- }
212
- declare const InteractionToken: import("@embedpdf/core").CapabilityToken<InteractionCapability>;
213
- /**
214
- * Resolve a sample against a gesture's HOME page. Page-anchored gestures track
215
- * the page they started on even when the cursor wanders off it — `s.page`
216
- * re-resolves per event (a foreign page is a DIFFERENT coordinate frame), so
217
- * prefer the source's unclamped projection and fall back to the page hit only
218
- * when it is the same page. Null → this sample can't speak for the home page.
219
- * Shared by every gesture owner (annotation edit/draw, form placement).
220
- */
221
- declare const samplePointOn: (s: PointerSample, pon: PageObjectNumber) => Point | null;
222
- interface InteractionConfig {
223
- /** Tool active when a document opens. Default `'pointer'`. */
224
- defaultTool?: ToolId;
225
- }
226
- //#endregion
227
- //#region src/feedback.types.d.ts
228
- interface PlatformFeedback {
229
- selection(): void;
230
- impact(weight?: 'light' | 'medium' | 'heavy'): void;
231
- notify(kind: 'success' | 'warning' | 'error'): void;
232
- }
233
- declare const FeedbackToken: import("@embedpdf/core").CapabilityToken<PlatformFeedback>;
234
- interface FeedbackPluginOptions {
235
- provider?: PlatformFeedback;
236
- }
237
- //#endregion
238
- export { samplePointOn as _, InteractionAction as a, InteractionHandler as c, Modifiers as d, Phase as f, ToolId as g, Tool as h, Cursor as i, InteractionState as l, PointerSample as m, FeedbackToken as n, InteractionCapability as o, PointerKind as p, PlatformFeedback as r, InteractionConfig as s, FeedbackPluginOptions as t, InteractionToken as u };
239
- //# sourceMappingURL=contract-F3gsFtSf.d.ts.map