@embedpdf/plugin-interaction-manager 1.4.0 → 1.5.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.
@@ -11,7 +11,7 @@ export declare const useInteractionManagerCapability: () => {
11
11
  };
12
12
  export declare function useInteractionManager(): {
13
13
  readonly provides: Readonly<import('../../lib/index.ts').InteractionManagerCapability> | null;
14
- readonly state: InteractionManagerState;
14
+ state: InteractionManagerState;
15
15
  };
16
16
  export declare function useCursor(): {
17
17
  setCursor: (token: string, cursor: string, prio?: number) => void;
@@ -21,13 +21,13 @@ interface UsePointerHandlersOptions {
21
21
  modeId?: string | string[];
22
22
  pageIndex?: number;
23
23
  }
24
- export declare function usePointerHandlers({ modeId, pageIndex }: UsePointerHandlersOptions): {
24
+ export declare function usePointerHandlers({ modeId, pageIndex }?: UsePointerHandlersOptions): {
25
25
  register: (handlers: PointerEventHandlersWithLifecycle, options?: {
26
26
  modeId?: string | string[];
27
27
  pageIndex?: number;
28
28
  }) => (() => void) | undefined;
29
29
  };
30
30
  export declare function useIsPageExclusive(): {
31
- readonly isPageExclusive: boolean;
31
+ isPageExclusive: boolean;
32
32
  };
33
33
  export {};
@@ -1,2 +1,2 @@
1
- "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"}),require("svelte/internal/disclose-version");const e=require("svelte/internal/client"),t=require("@embedpdf/plugin-interaction-manager"),n=require("@embedpdf/core/svelte"),o=require("@embedpdf/models");function r(e){const t=Object.create(null,{[Symbol.toStringTag]:{value:"Module"}});if(e)for(const n in e)if("default"!==n){const o=Object.getOwnPropertyDescriptor(e,n);Object.defineProperty(t,n,o.get?o:{enumerable:!0,get:()=>e[n]})}return t.default=e,Object.freeze(t)}const i=r(e),s=()=>n.useCapability(t.InteractionManagerPlugin.id);function l(){const e=i.derived(s),t=i.derived((()=>i.get(e).provides));let n=i.derived((()=>{var e;const n=null==(e=i.get(t))?void 0:e.getActiveInteractionMode();return"page"===(null==n?void 0:n.scope)&&!!n.exclusive}));return i.user_effect((()=>{if(i.get(t))return i.get(t).onModeChange((()=>{const e=i.get(t).getActiveInteractionMode();i.set(n,"page"===(null==e?void 0:e.scope)&&!!(null==e?void 0:e.exclusive))}))})),{get isPageExclusive(){return i.get(n)}}}const a={pointerdown:"onPointerDown",pointerup:"onPointerUp",pointermove:"onPointerMove",pointerenter:"onPointerEnter",pointerleave:"onPointerLeave",pointercancel:"onPointerCancel",mousedown:"onMouseDown",mouseup:"onMouseUp",mousemove:"onMouseMove",mouseenter:"onMouseEnter",mouseleave:"onMouseLeave",mousecancel:"onMouseCancel",click:"onClick",dblclick:"onDoubleClick",touchstart:"onPointerDown",touchend:"onPointerUp",touchmove:"onPointerMove",touchcancel:"onPointerCancel"},c=["pointerdown","pointerup","pointermove","pointerenter","pointerleave","pointercancel","mousedown","mouseup","mousemove","mouseenter","mouseleave","mousecancel","click","dblclick"],u="undefined"!=typeof PointerEvent?c:[...c,"touchstart","touchend","touchmove","touchcancel"];function d(e){return"undefined"!=typeof TouchEvent&&e instanceof TouchEvent}function p(e,t,n,o){let r=e.getHandlersForScope(t);const i=()=>{var t;return!1!==(null==(t=e.getActiveInteractionMode())?void 0:t.wantsRawTouch)},s={};let l=i();const c=e=>{u.forEach((t=>{const o=s[t]??(s[t]=b);var r;n.addEventListener(t,o,(r=e,t.startsWith("touch")?{passive:!r}:{passive:!1}))}))},p=()=>{u.forEach((e=>{const t=s[e];t&&n.removeEventListener(e,t)}))};c(l),n.style.touchAction=l?"none":"";const g=e.onModeChange((()=>{if("global"===t.type){const t=e.getActiveInteractionMode();n.style.cursor="global"===(null==t?void 0:t.scope)?t.cursor??"auto":"auto"}r=e.getHandlersForScope(t);const o=i();o!==l&&(p(),c(o),l=o,n.style.touchAction=l?"none":"")})),v=e.onHandlerChange((()=>{r=e.getHandlersForScope(t)})),f=e.getActiveInteractionMode(),h=e.getCurrentCursor();n.style.cursor="global"===t.type&&"global"!==(null==f?void 0:f.scope)?"auto":h;const y=e.onCursorChange((o=>{var r;"global"===t.type&&"global"!==(null==(r=e.getActiveInteractionMode())?void 0:r.scope)||(n.style.cursor=o)})),m=(e,t)=>{if(o)return o(e,t);const n=t.getBoundingClientRect();return{x:e.clientX-n.left,y:e.clientY-n.top}};function b(t){var o;if(e.isPaused())return;const i=e.getExclusionRules();if(t.target&&function(e,t){var n,o,r;if(!e)return!1;let i=e;for(;i;){if(null==(n=t.classes)?void 0:n.length)for(const e of t.classes)if(null==(o=i.classList)?void 0:o.contains(e))return!0;if(null==(r=t.dataAttributes)?void 0:r.length)for(const e of t.dataAttributes)if(i.hasAttribute(e))return!0;i=i.parentElement}return!1}(t.target,i))return;const s=a[t.type];if(!s||!(null==r?void 0:r[s]))return;let c,u;if(d(t)&&l&&("touchmove"===t.type||"touchcancel"===t.type)&&t.preventDefault(),d(t)){const e="touchend"===t.type||"touchcancel"===t.type?t.changedTouches[0]:t.touches[0];if(!e)return;c=m(e,n),u={clientX:e.clientX,clientY:e.clientY,ctrlKey:t.ctrlKey,shiftKey:t.shiftKey,altKey:t.altKey,metaKey:t.metaKey,target:t.target,currentTarget:t.currentTarget,setPointerCapture:()=>{},releasePointerCapture:()=>{}}}else{const e=t;c=m(e,n),u={clientX:e.clientX,clientY:e.clientY,ctrlKey:e.ctrlKey,shiftKey:e.shiftKey,altKey:e.altKey,metaKey:e.metaKey,target:e.target,currentTarget:e.currentTarget,setPointerCapture:()=>{var t,n;null==(n=null==(t=e.target)?void 0:t.setPointerCapture)||n.call(t,e.pointerId)},releasePointerCapture:()=>{var t,n;null==(n=null==(t=e.target)?void 0:t.releasePointerCapture)||n.call(t,e.pointerId)}}}null==(o=r[s])||o.call(r,c,u,e.getActiveMode())}return()=>{p(),g(),y(),v()}}var g=i.from_html("<div><!></div>");var v=i.from_html("<div></div>"),f=i.from_html("<div><!> <!></div>");exports.GlobalPointerProvider=function(e,t){i.push(t,!0);let n=i.rest_props(t,["$$slots","$$events","$$legacy","children","class"]),o=i.state(null);const r=i.derived(s),l=i.derived((()=>i.get(r).provides));i.user_effect((()=>{if(i.get(l)&&i.get(o))return p(i.get(l),{type:"global"},i.get(o))}));var a=g();i.attribute_effect(a,(()=>({class:t.class,...n,[i.STYLE]:{width:"100%",height:"100%"}})));var c=i.child(a);i.snippet(c,(()=>t.children)),i.reset(a),i.bind_this(a,(e=>i.set(o,e)),(()=>i.get(o))),i.append(e,a),i.pop()},exports.PagePointerProvider=function(e,t){i.push(t,!0);let n=i.rest_props(t,["$$slots","$$events","$$legacy","pageIndex","children","pageWidth","pageHeight","rotation","scale","convertEventToPoint","class"]),r=i.state(null);const a=i.derived(s),c=i.derived((()=>i.get(a).provides)),u=i.derived(l),d=i.derived((()=>(e,n)=>{const r=n.getBoundingClientRect(),i={x:e.clientX-r.left,y:e.clientY-r.top},s=o.transformSize({width:t.pageWidth,height:t.pageHeight},t.rotation,1);return o.restorePosition(s,i,t.rotation,t.scale)}));i.user_effect((()=>{if(i.get(c)&&i.get(r))return p(i.get(c),{type:"page",pageIndex:t.pageIndex},i.get(r),t.convertEventToPoint||i.get(d))}));var g=f();i.attribute_effect(g,(e=>({class:t.class,...n,[i.STYLE]:e})),[()=>({position:"relative",width:`${t.pageWidth}px`,height:`${t.pageHeight}px`})]);var h=i.child(g);i.snippet(h,(()=>t.children));var y=i.sibling(h,2),m=e=>{var t=v();i.set_style(t,"",{},{position:"absolute",top:"0",left:"0",right:"0",bottom:"0","z-index":"10"}),i.append(e,t)};i.if(y,(e=>{i.get(u)&&e(m)})),i.reset(g),i.bind_this(g,(e=>i.set(r,e)),(()=>i.get(r))),i.append(e,g),i.pop()},exports.useCursor=function(){const e=i.derived(s),t=i.derived((()=>i.get(e).provides));return{setCursor:(e,n,o=0)=>{var r;null==(r=i.get(t))||r.setCursor(e,n,o)},removeCursor:e=>{var n;null==(n=i.get(t))||n.removeCursor(e)}}},exports.useInteractionManager=function(){const e=i.derived(s),n=i.derived((()=>i.get(e).provides));let o=i.state(i.proxy(t.initialState));return i.user_effect((()=>{if(i.get(n))return i.get(n).onStateChange((e=>{i.set(o,e,!0)}))})),{get provides(){return i.get(n)},get state(){return i.get(o)}}},exports.useInteractionManagerCapability=s,exports.useInteractionManagerPlugin=()=>n.usePlugin(t.InteractionManagerPlugin.id),exports.useIsPageExclusive=l,exports.usePointerHandlers=function({modeId:e,pageIndex:t}){const n=i.derived(s),o=i.derived((()=>i.get(n).provides));return{register:(n,r)=>{var s,l;const a=(null==r?void 0:r.modeId)??e,c=(null==r?void 0:r.pageIndex)??t;return a?null==(s=i.get(o))?void 0:s.registerHandlers({modeId:a,handlers:n,pageIndex:c}):null==(l=i.get(o))?void 0:l.registerAlways({scope:void 0!==c?{type:"page",pageIndex:c}:{type:"global"},handlers:n})}}},Object.keys(t).forEach((e=>{"default"===e||Object.prototype.hasOwnProperty.call(exports,e)||Object.defineProperty(exports,e,{enumerable:!0,get:()=>t[e]})}));
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"}),require("svelte/internal/disclose-version");const e=require("svelte/internal/client"),t=require("@embedpdf/plugin-interaction-manager"),n=require("@embedpdf/core/svelte"),o=require("@embedpdf/models");function r(e){const t=Object.create(null,{[Symbol.toStringTag]:{value:"Module"}});if(e)for(const n in e)if("default"!==n){const o=Object.getOwnPropertyDescriptor(e,n);Object.defineProperty(t,n,o.get?o:{enumerable:!0,get:()=>e[n]})}return t.default=e,Object.freeze(t)}const i=r(e),s=()=>n.useCapability(t.InteractionManagerPlugin.id);function l(){const e=s(),t=i.proxy({isPageExclusive:!1});return i.user_effect((()=>{if(!e.provides)return;const n=e.provides.getActiveInteractionMode();return t.isPageExclusive="page"===(null==n?void 0:n.scope)&&!!n.exclusive,e.provides.onModeChange((()=>{var n;const o=null==(n=e.provides)?void 0:n.getActiveInteractionMode();t.isPageExclusive="page"===(null==o?void 0:o.scope)&&!!(null==o?void 0:o.exclusive)}))})),t}const a={pointerdown:"onPointerDown",pointerup:"onPointerUp",pointermove:"onPointerMove",pointerenter:"onPointerEnter",pointerleave:"onPointerLeave",pointercancel:"onPointerCancel",mousedown:"onMouseDown",mouseup:"onMouseUp",mousemove:"onMouseMove",mouseenter:"onMouseEnter",mouseleave:"onMouseLeave",mousecancel:"onMouseCancel",click:"onClick",dblclick:"onDoubleClick",touchstart:"onPointerDown",touchend:"onPointerUp",touchmove:"onPointerMove",touchcancel:"onPointerCancel"},c=["pointerdown","pointerup","pointermove","pointerenter","pointerleave","pointercancel","mousedown","mouseup","mousemove","mouseenter","mouseleave","mousecancel","click","dblclick"],u="undefined"!=typeof PointerEvent?c:[...c,"touchstart","touchend","touchmove","touchcancel"];function p(e){return"undefined"!=typeof TouchEvent&&e instanceof TouchEvent}function d(e,t,n,o){let r=e.getHandlersForScope(t);const i=()=>{var t;return!1!==(null==(t=e.getActiveInteractionMode())?void 0:t.wantsRawTouch)},s={};let l=i();const c=e=>{u.forEach((t=>{const o=s[t]??(s[t]=P);var r;n.addEventListener(t,o,(r=e,t.startsWith("touch")?{passive:!r}:{passive:!1}))}))},d=()=>{u.forEach((e=>{const t=s[e];t&&n.removeEventListener(e,t)}))};c(l),n.style.touchAction=l?"none":"";const v=e.onModeChange((()=>{if("global"===t.type){const t=e.getActiveInteractionMode();n.style.cursor="global"===(null==t?void 0:t.scope)?t.cursor??"auto":"auto"}r=e.getHandlersForScope(t);const o=i();o!==l&&(d(),c(o),l=o,n.style.touchAction=l?"none":"")})),g=e.onHandlerChange((()=>{r=e.getHandlersForScope(t)})),f=e.getActiveInteractionMode(),h=e.getCurrentCursor();n.style.cursor="global"===t.type&&"global"!==(null==f?void 0:f.scope)?"auto":h;const y=e.onCursorChange((o=>{var r;"global"===t.type&&"global"!==(null==(r=e.getActiveInteractionMode())?void 0:r.scope)||(n.style.cursor=o)})),m=(e,t)=>{if(o)return o(e,t);const n=t.getBoundingClientRect();return{x:e.clientX-n.left,y:e.clientY-n.top}};function P(t){var o;if(e.isPaused())return;const i=e.getExclusionRules();if(t.target&&function(e,t){var n,o,r;if(!e)return!1;let i=e;for(;i;){if(null==(n=t.classes)?void 0:n.length)for(const e of t.classes)if(null==(o=i.classList)?void 0:o.contains(e))return!0;if(null==(r=t.dataAttributes)?void 0:r.length)for(const e of t.dataAttributes)if(i.hasAttribute(e))return!0;i=i.parentElement}return!1}(t.target,i))return;const s=a[t.type];if(!s||!(null==r?void 0:r[s]))return;let c,u;if(p(t)&&l&&("touchmove"===t.type||"touchcancel"===t.type)&&t.preventDefault(),p(t)){const e="touchend"===t.type||"touchcancel"===t.type?t.changedTouches[0]:t.touches[0];if(!e)return;c=m(e,n),u={clientX:e.clientX,clientY:e.clientY,ctrlKey:t.ctrlKey,shiftKey:t.shiftKey,altKey:t.altKey,metaKey:t.metaKey,target:t.target,currentTarget:t.currentTarget,setPointerCapture:()=>{},releasePointerCapture:()=>{}}}else{const e=t;c=m(e,n),u={clientX:e.clientX,clientY:e.clientY,ctrlKey:e.ctrlKey,shiftKey:e.shiftKey,altKey:e.altKey,metaKey:e.metaKey,target:e.target,currentTarget:e.currentTarget,setPointerCapture:()=>{var t,n;null==(n=null==(t=e.target)?void 0:t.setPointerCapture)||n.call(t,e.pointerId)},releasePointerCapture:()=>{var t,n;null==(n=null==(t=e.target)?void 0:t.releasePointerCapture)||n.call(t,e.pointerId)}}}null==(o=r[s])||o.call(r,c,u,e.getActiveMode())}return()=>{d(),v(),y(),g()}}var v=i.from_html("<div><!></div>");var g=i.from_html("<div></div>"),f=i.from_html("<div><!> <!></div>");exports.GlobalPointerProvider=function(e,t){i.push(t,!0);let n=i.rest_props(t,["$$slots","$$events","$$legacy","children","class"]),o=i.state(null);const r=s();i.user_effect((()=>{if(r.provides&&i.get(o))return d(r.provides,{type:"global"},i.get(o))}));var l=v();i.attribute_effect(l,(()=>({class:t.class,...n,[i.STYLE]:{width:"100%",height:"100%"}})));var a=i.child(l);i.snippet(a,(()=>t.children)),i.reset(l),i.bind_this(l,(e=>i.set(o,e)),(()=>i.get(o))),i.append(e,l),i.pop()},exports.PagePointerProvider=function(e,t){i.push(t,!0);let n=i.rest_props(t,["$$slots","$$events","$$legacy","pageIndex","children","pageWidth","pageHeight","rotation","scale","convertEventToPoint","class"]),r=i.state(null);const a=s(),c=l(),u=i.derived((()=>(e,n)=>{const r=n.getBoundingClientRect(),i={x:e.clientX-r.left,y:e.clientY-r.top},s=o.transformSize({width:t.pageWidth,height:t.pageHeight},t.rotation,1);return o.restorePosition(s,i,t.rotation,t.scale)}));i.user_effect((()=>{if(a.provides&&i.get(r))return d(a.provides,{type:"page",pageIndex:t.pageIndex},i.get(r),t.convertEventToPoint||i.get(u))}));var p=f();i.attribute_effect(p,(e=>({class:t.class,...n,[i.STYLE]:e})),[()=>({position:"relative",width:`${t.pageWidth}px`,height:`${t.pageHeight}px`})]);var v=i.child(p);i.snippet(v,(()=>t.children));var h=i.sibling(v,2),y=e=>{var t=g();i.set_style(t,"",{},{position:"absolute",top:"0",left:"0",right:"0",bottom:"0","z-index":"10"}),i.append(e,t)};i.if(h,(e=>{c&&e(y)})),i.reset(p),i.bind_this(p,(e=>i.set(r,e)),(()=>i.get(r))),i.append(e,p),i.pop()},exports.useCursor=function(){const e=s();return i.proxy({setCursor:(t,n,o=0)=>{var r;null==(r=e.provides)||r.setCursor(t,n,o)},removeCursor:t=>{var n;null==(n=e.provides)||n.removeCursor(t)}})},exports.useInteractionManager=function(){const e=s(),n=i.proxy({get provides(){return e.provides},state:t.initialState});return i.user_effect((()=>{if(e.provides)return e.provides.onStateChange((e=>{n.state=e}))})),n},exports.useInteractionManagerCapability=s,exports.useInteractionManagerPlugin=()=>n.usePlugin(t.InteractionManagerPlugin.id),exports.useIsPageExclusive=l,exports.usePointerHandlers=function({modeId:e,pageIndex:t}={}){const n=s();return{register:(o,r)=>{var i,s;const l=(null==r?void 0:r.modeId)??e,a=(null==r?void 0:r.pageIndex)??t;return l?null==(i=n.provides)?void 0:i.registerHandlers({modeId:l,handlers:o,pageIndex:a}):null==(s=n.provides)?void 0:s.registerAlways({scope:void 0!==a?{type:"page",pageIndex:a}:{type:"global"},handlers:o})}}},Object.keys(t).forEach((e=>{"default"===e||Object.prototype.hasOwnProperty.call(exports,e)||Object.defineProperty(exports,e,{enumerable:!0,get:()=>t[e]})}));
2
2
  //# sourceMappingURL=index.cjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.cjs","sources":["../../src/svelte/hooks/use-interaction-manager.svelte.ts","../../src/shared/utils.ts","../../src/svelte/components/GlobalPointerProvider.svelte","../../src/svelte/components/PagePointerProvider.svelte"],"sourcesContent":["import {\n initialState,\n InteractionManagerPlugin,\n InteractionManagerState,\n PointerEventHandlersWithLifecycle,\n} from '@embedpdf/plugin-interaction-manager';\nimport { useCapability, usePlugin } from '@embedpdf/core/svelte';\n\nexport const useInteractionManagerPlugin = () =>\n usePlugin<InteractionManagerPlugin>(InteractionManagerPlugin.id);\nexport const useInteractionManagerCapability = () =>\n useCapability<InteractionManagerPlugin>(InteractionManagerPlugin.id);\n\nexport function useInteractionManager() {\n const { provides } = $derived(useInteractionManagerCapability());\n let interactionManagerState = $state<InteractionManagerState>(initialState);\n\n $effect(() => {\n if (!provides) return;\n return provides.onStateChange((state) => {\n interactionManagerState = state;\n });\n });\n\n return {\n get provides() {\n return provides;\n },\n get state() {\n return interactionManagerState;\n },\n };\n}\n\nexport function useCursor() {\n const { provides } = $derived(useInteractionManagerCapability());\n return {\n setCursor: (token: string, cursor: string, prio = 0) => {\n provides?.setCursor(token, cursor, prio);\n },\n removeCursor: (token: string) => {\n provides?.removeCursor(token);\n },\n };\n}\n\ninterface UsePointerHandlersOptions {\n modeId?: string | string[];\n pageIndex?: number;\n}\n\nexport function usePointerHandlers({ modeId, pageIndex }: UsePointerHandlersOptions) {\n const { provides } = $derived(useInteractionManagerCapability());\n return {\n register: (\n handlers: PointerEventHandlersWithLifecycle,\n options?: { modeId?: string | string[]; pageIndex?: number },\n ) => {\n // Use provided options or fall back to hook-level options\n const finalModeId = options?.modeId ?? modeId;\n const finalPageIndex = options?.pageIndex ?? pageIndex;\n\n return finalModeId\n ? provides?.registerHandlers({\n modeId: finalModeId,\n handlers,\n pageIndex: finalPageIndex,\n })\n : provides?.registerAlways({\n scope:\n finalPageIndex !== undefined\n ? { type: 'page', pageIndex: finalPageIndex }\n : { type: 'global' },\n handlers,\n });\n },\n };\n}\n\nexport function useIsPageExclusive() {\n const { provides: cap } = $derived(useInteractionManagerCapability());\n let isPageExclusive = $derived.by(() => {\n const m = cap?.getActiveInteractionMode();\n return m?.scope === 'page' && !!m.exclusive;\n });\n\n $effect(() => {\n if (!cap) return;\n\n return cap.onModeChange(() => {\n const mode = cap.getActiveInteractionMode();\n isPageExclusive = mode?.scope === 'page' && !!mode?.exclusive;\n });\n });\n\n return {\n get isPageExclusive() {\n return isPageExclusive;\n },\n };\n}\n","import { Position } from '@embedpdf/models';\nimport type {\n InteractionManagerCapability,\n InteractionScope,\n PointerEventHandlers,\n EmbedPdfPointerEvent,\n InteractionExclusionRules,\n} from '@embedpdf/plugin-interaction-manager';\n\n/* -------------------------------------------------- */\n/* event → handler key lookup */\n/* -------------------------------------------------- */\ntype K = keyof PointerEventHandlers;\nconst domEventMap: Record<string, K> = {\n pointerdown: 'onPointerDown',\n pointerup: 'onPointerUp',\n pointermove: 'onPointerMove',\n pointerenter: 'onPointerEnter',\n pointerleave: 'onPointerLeave',\n pointercancel: 'onPointerCancel',\n\n mousedown: 'onMouseDown',\n mouseup: 'onMouseUp',\n mousemove: 'onMouseMove',\n mouseenter: 'onMouseEnter',\n mouseleave: 'onMouseLeave',\n mousecancel: 'onMouseCancel',\n\n click: 'onClick',\n dblclick: 'onDoubleClick',\n\n /* touch → pointer fallback for very old browsers */\n touchstart: 'onPointerDown',\n touchend: 'onPointerUp',\n touchmove: 'onPointerMove',\n touchcancel: 'onPointerCancel',\n};\n\nconst pointerEventTypes = [\n 'pointerdown',\n 'pointerup',\n 'pointermove',\n 'pointerenter',\n 'pointerleave',\n 'pointercancel',\n 'mousedown',\n 'mouseup',\n 'mousemove',\n 'mouseenter',\n 'mouseleave',\n 'mousecancel',\n 'click',\n 'dblclick',\n];\n\nconst touchEventTypes = ['touchstart', 'touchend', 'touchmove', 'touchcancel'];\nconst HAS_POINTER = typeof PointerEvent !== 'undefined';\n// If the browser supports Pointer Events, don't attach legacy touch events to avoid double-dispatch.\nconst allEventTypes = HAS_POINTER ? pointerEventTypes : [...pointerEventTypes, ...touchEventTypes];\n\n/* -------------------------------------------------- */\n/* helper: decide listener options per event type */\n/* -------------------------------------------------- */\nfunction listenerOpts(eventType: string, wantsRawTouch: boolean): AddEventListenerOptions {\n // Only touch events are toggled; pointer/mouse stay non-passive\n return eventType.startsWith('touch') ? { passive: !wantsRawTouch } : { passive: false };\n}\n\nfunction isTouchEvent(evt: Event): evt is TouchEvent {\n return typeof TouchEvent !== 'undefined' && evt instanceof TouchEvent;\n}\n\n/**\n * Check if an element should be excluded based on rules\n * This is in the framework layer, not the plugin\n */\nfunction shouldExcludeElement(element: Element | null, rules: InteractionExclusionRules): boolean {\n if (!element) return false;\n\n let current: Element | null = element;\n\n while (current) {\n // Check classes\n if (rules.classes?.length) {\n for (const className of rules.classes) {\n if (current.classList?.contains(className)) {\n return true;\n }\n }\n }\n\n // Check data attributes\n if (rules.dataAttributes?.length) {\n for (const attr of rules.dataAttributes) {\n if (current.hasAttribute(attr)) {\n return true;\n }\n }\n }\n\n // Move up the DOM tree\n current = current.parentElement;\n }\n\n return false;\n}\n\n/* -------------------------------------------------- */\n/* createPointerProvider */\n/* -------------------------------------------------- */\nexport function createPointerProvider(\n cap: InteractionManagerCapability,\n scope: InteractionScope,\n element: HTMLElement,\n convertEventToPoint?: (evt: PointerEvent, host: HTMLElement) => Position,\n) {\n /* ---------- live handler set --------------------------------------------------- */\n let active: PointerEventHandlers | null = cap.getHandlersForScope(scope);\n\n /* ---------- helper to compute current wantsRawTouch (defaults to true) --------- */\n const wantsRawTouchNow = () => cap.getActiveInteractionMode()?.wantsRawTouch !== false; // default → true\n\n /* ---------- dynamic listener (re)attachment ------------------------------------ */\n const listeners: Record<string, (evt: Event) => void> = {};\n let attachedWithRawTouch = wantsRawTouchNow(); // remember current mode’s wish\n\n const addListeners = (raw: boolean) => {\n allEventTypes.forEach((type) => {\n const fn = (listeners[type] ??= handleEvent);\n element.addEventListener(type, fn, listenerOpts(type, raw));\n });\n };\n const removeListeners = () => {\n allEventTypes.forEach((type) => {\n const fn = listeners[type];\n if (fn) element.removeEventListener(type, fn);\n });\n };\n\n /* attach for the first time */\n addListeners(attachedWithRawTouch);\n element.style.touchAction = attachedWithRawTouch ? 'none' : '';\n\n /* ---------- mode & handler change hooks --------------------------------------- */\n const stopMode = cap.onModeChange(() => {\n /* cursor baseline update for global wrapper */\n if (scope.type === 'global') {\n const mode = cap.getActiveInteractionMode();\n element.style.cursor = mode?.scope === 'global' ? (mode.cursor ?? 'auto') : 'auto';\n }\n\n active = cap.getHandlersForScope(scope);\n\n /* re-attach listeners if wantsRawTouch toggled */\n const raw = wantsRawTouchNow();\n if (raw !== attachedWithRawTouch) {\n removeListeners();\n addListeners(raw);\n attachedWithRawTouch = raw;\n element.style.touchAction = attachedWithRawTouch ? 'none' : '';\n }\n });\n\n const stopHandler = cap.onHandlerChange(() => {\n active = cap.getHandlersForScope(scope);\n });\n\n /* ---------- cursor sync -------------------------------------------------------- */\n const initialMode = cap.getActiveInteractionMode();\n const initialCursor = cap.getCurrentCursor();\n element.style.cursor =\n scope.type === 'global' && initialMode?.scope !== 'global' ? 'auto' : initialCursor;\n\n const stopCursor = cap.onCursorChange((c) => {\n if (scope.type === 'global' && cap.getActiveInteractionMode()?.scope !== 'global') return;\n element.style.cursor = c;\n });\n\n /* ---------- point conversion --------------------------------------------------- */\n const toPos = (e: { clientX: number; clientY: number }, host: HTMLElement): Position => {\n if (convertEventToPoint) return convertEventToPoint(e as PointerEvent, host);\n const r = host.getBoundingClientRect();\n return { x: e.clientX - r.left, y: e.clientY - r.top };\n };\n\n /* ---------- central event handler --------------------------------------------- */\n function handleEvent(evt: Event) {\n if (cap.isPaused()) return;\n\n // Get exclusion rules from capability and check in framework layer\n const exclusionRules = cap.getExclusionRules();\n if (evt.target && shouldExcludeElement(evt.target as Element, exclusionRules)) {\n return; // Skip processing this event\n }\n\n const handlerKey = domEventMap[evt.type];\n if (!handlerKey || !active?.[handlerKey]) return;\n\n /* preventDefault only when mode really wants raw touch */\n if (\n isTouchEvent(evt) &&\n attachedWithRawTouch &&\n (evt.type === 'touchmove' || evt.type === 'touchcancel')\n ) {\n evt.preventDefault();\n }\n\n // ----- normalise ----------------------------------------------------------------\n let pos!: Position;\n let normEvt!: EmbedPdfPointerEvent & {\n target: EventTarget | null;\n currentTarget: EventTarget | null;\n };\n\n if (isTouchEvent(evt)) {\n const tp =\n evt.type === 'touchend' || evt.type === 'touchcancel'\n ? evt.changedTouches[0]\n : evt.touches[0];\n if (!tp) return;\n\n pos = toPos(tp, element);\n normEvt = {\n clientX: tp.clientX,\n clientY: tp.clientY,\n ctrlKey: evt.ctrlKey,\n shiftKey: evt.shiftKey,\n altKey: evt.altKey,\n metaKey: evt.metaKey,\n target: evt.target,\n currentTarget: evt.currentTarget,\n setPointerCapture: () => {},\n releasePointerCapture: () => {},\n };\n } else {\n const pe = evt as PointerEvent;\n pos = toPos(pe, element);\n normEvt = {\n clientX: pe.clientX,\n clientY: pe.clientY,\n ctrlKey: pe.ctrlKey,\n shiftKey: pe.shiftKey,\n altKey: pe.altKey,\n metaKey: pe.metaKey,\n target: pe.target,\n currentTarget: pe.currentTarget,\n setPointerCapture: () => {\n (pe.target as HTMLElement)?.setPointerCapture?.(pe.pointerId);\n },\n releasePointerCapture: () => {\n (pe.target as HTMLElement)?.releasePointerCapture?.(pe.pointerId);\n },\n };\n }\n\n active[handlerKey]?.(pos, normEvt, cap.getActiveMode());\n }\n\n /* ---------- teardown ----------------------------------------------------------- */\n return () => {\n removeListeners();\n stopMode();\n stopCursor();\n stopHandler();\n };\n}\n","<script lang=\"ts\">\n import type { Snippet } from 'svelte';\n import { useInteractionManagerCapability } from '../hooks';\n import { createPointerProvider } from '../../shared/utils';\n import type { HTMLAttributes } from 'svelte/elements';\n\n interface GlobalPointerProviderProps extends HTMLAttributes<HTMLDivElement> {\n children: Snippet;\n class?: string;\n }\n\n let { children, class: propsClass, ...restProps }: GlobalPointerProviderProps = $props();\n\n let ref = $state<HTMLDivElement | null>(null);\n const { provides: cap } = $derived(useInteractionManagerCapability());\n\n $effect(() => {\n if (!cap || !ref) return;\n\n return createPointerProvider(cap, { type: 'global' }, ref);\n });\n</script>\n\n<div bind:this={ref} style:width=\"100%\" style:height=\"100%\" class={propsClass} {...restProps}>\n {@render children()}\n</div>\n","<script lang=\"ts\">\n import { type Position, restorePosition, type Size, transformSize } from '@embedpdf/models';\n import type { Snippet } from 'svelte';\n import type { HTMLAttributes } from 'svelte/elements';\n import { createPointerProvider } from '../../shared/utils';\n import { useInteractionManagerCapability, useIsPageExclusive } from '../hooks';\n\n interface PagePointerProviderProps extends HTMLAttributes<HTMLDivElement> {\n children: Snippet;\n pageIndex: number;\n pageWidth: number;\n pageHeight: number;\n rotation: number;\n scale: number;\n class?: string;\n convertEventToPoint?: (event: PointerEvent, element: HTMLElement) => Position;\n }\n\n let {\n pageIndex,\n children,\n pageWidth,\n pageHeight,\n rotation,\n scale,\n convertEventToPoint,\n class: propsClass,\n ...restProps\n }: PagePointerProviderProps = $props();\n\n let ref = $state<HTMLDivElement | null>(null);\n\n const { provides: cap } = $derived(useInteractionManagerCapability());\n const isPageExclusive = $derived(useIsPageExclusive());\n\n // Memoize the default conversion function\n const defaultConvertEventToPoint = $derived.by(() => {\n return (event: PointerEvent, element: HTMLElement): Position => {\n const rect = element.getBoundingClientRect();\n const displayPoint = {\n x: event.clientX - rect.left,\n y: event.clientY - rect.top,\n };\n\n const displaySize: Size = transformSize(\n { width: pageWidth, height: pageHeight },\n rotation,\n 1,\n );\n\n return restorePosition(displaySize, displayPoint, rotation, scale);\n };\n });\n\n $effect(() => {\n if (!cap || !ref) return;\n\n return createPointerProvider(\n cap,\n { type: 'page', pageIndex },\n ref,\n convertEventToPoint || defaultConvertEventToPoint,\n );\n });\n</script>\n\n<div\n bind:this={ref}\n style:position=\"relative\"\n style:width={`${pageWidth}px`}\n style:height={`${pageHeight}px`}\n class={propsClass}\n {...restProps}\n>\n {@render children()}\n {#if isPageExclusive}\n <div\n style:position=\"absolute\"\n style:top=\"0\"\n style:left=\"0\"\n style:right=\"0\"\n style:bottom=\"0\"\n style:z-index=\"10\"\n ></div>\n {/if}\n</div>\n"],"names":["useInteractionManagerCapability","useCapability","InteractionManagerPlugin","id","useIsPageExclusive","cap","provides","isPageExclusive","m","$","get","_a","getActiveInteractionMode","scope","exclusive","user_effect","onModeChange","mode","domEventMap","pointerdown","pointerup","pointermove","pointerenter","pointerleave","pointercancel","mousedown","mouseup","mousemove","mouseenter","mouseleave","mousecancel","click","dblclick","touchstart","touchend","touchmove","touchcancel","pointerEventTypes","allEventTypes","PointerEvent","isTouchEvent","evt","TouchEvent","createPointerProvider","element","convertEventToPoint","active","getHandlersForScope","wantsRawTouchNow","wantsRawTouch","listeners","attachedWithRawTouch","addListeners","raw","forEach","type","fn","handleEvent","addEventListener","startsWith","passive","removeListeners","removeEventListener","style","touchAction","stopMode","cursor","stopHandler","onHandlerChange","initialMode","initialCursor","getCurrentCursor","stopCursor","onCursorChange","c","toPos","e","host","r","getBoundingClientRect","x","clientX","left","y","clientY","top","isPaused","exclusionRules","getExclusionRules","target","rules","current","classes","length","className","_b","classList","contains","_c","dataAttributes","attr","hasAttribute","parentElement","shouldExcludeElement","handlerKey","pos","normEvt","preventDefault","tp","changedTouches","touches","ctrlKey","shiftKey","altKey","metaKey","currentTarget","setPointerCapture","releasePointerCapture","pe","call","pointerId","getActiveMode","restProps","rest_props","$$props","ref","bind_this","div","$$value","set","defaultConvertEventToPoint","derived","event","rect","displayPoint","displaySize","transformSize","width","pageWidth","height","restorePosition","rotation","scale","pageIndex","STYLE","$0","consequent","setCursor","token","prio","removeCursor","interactionManagerState","initialState","onStateChange","state","$__namespace","usePlugin","modeId","register","handlers","options","finalModeId","finalPageIndex","registerHandlers","registerAlways"],"mappings":"ijBAUaA,EACX,IAAAC,gBAAwCC,EAAAA,yBAAyBC,IAoEnD,SAAAC,sBACqBJ,GAAjBK,0BAAVC,WACJ,IAAAC,8BACIC,EAAAC,OAAAA,EAAAA,EAAAC,IAAIL,SAAK,EAAAM,EAAAC,2BACR,MAAa,UAAV,MAAHJ,OAAG,EAAAA,EAAAK,UAAsBL,EAAEM,SAAA,WAGpCL,EAAAM,2BACOV,gBAEEA,GAAIW,yBACHC,EAAAR,EAAAC,IAAOL,GAAIO,iCACjBL,EAAkC,UAAV,MAANU,OAAM,EAAAA,EAAAJ,iBAAsBI,WAAMH,WAAA,GACrD,KAIG,mBAAAP,gBACKA,IAGb,CCvFA,MAAMW,EAAiC,CACrCC,YAAa,gBACbC,UAAW,cACXC,YAAa,gBACbC,aAAc,iBACdC,aAAc,iBACdC,cAAe,kBAEfC,UAAW,cACXC,QAAS,YACTC,UAAW,cACXC,WAAY,eACZC,WAAY,eACZC,YAAa,gBAEbC,MAAO,UACPC,SAAU,gBAGVC,WAAY,gBACZC,SAAU,cACVC,UAAW,gBACXC,YAAa,mBAGTC,EAAoB,CACxB,cACA,YACA,cACA,eACA,eACA,gBACA,YACA,UACA,YACA,aACA,aACA,cACA,QACA,YAMIC,EAFsC,oBAAjBC,aAESF,EAAoB,IAAIA,EAHnC,aAAc,WAAY,YAAa,eAahE,SAASG,EAAaC,GACb,MAAsB,oBAAfC,YAA8BD,aAAeC,UAC7D,CAwCO,SAASC,EACdtC,EACAQ,EACA+B,EACAC,GAGI,IAAAC,EAAsCzC,EAAI0C,oBAAoBlC,GAGlE,MAAMmC,EAAmB,WAAU,OAA8C,KAAlD,OAAIrC,EAAAN,EAAAO,iCAAJ,EAAAD,EAAgCsC,cAAkB,EAG3EC,EAAkD,CAAC,EACzD,IAAIC,EAAuBH,IAErB,MAAAI,EAAgBC,IACNf,EAAAgB,SAASC,IACf,MAAAC,EAAMN,EAAoBK,KAAAL,EAAAK,GAAAE,GAjEtC,IAAyCR,EAkEnCL,EAAQc,iBAAiBH,EAAMC,GAlEIP,EAkEmBI,EAANE,EAhEnCI,WAAW,SAAW,CAAEC,SAAUX,GAAkB,CAAEW,SAAS,IAgElB,GAC3D,EAEGC,EAAkB,KACRvB,EAAAgB,SAASC,IACf,MAAAC,EAAKN,EAAUK,GACjBC,GAAIZ,EAAQkB,oBAAoBP,EAAMC,EAAE,GAC7C,EAIHJ,EAAaD,GACLP,EAAAmB,MAAMC,YAAcb,EAAuB,OAAS,GAGtD,MAAAc,EAAW5D,EAAIW,cAAa,KAE5B,GAAe,WAAfH,EAAM0C,KAAmB,CACrB,MAAAtC,EAAOZ,EAAIO,2BACjBgC,EAAQmB,MAAMG,OAAyB,YAAhB,MAAAjD,OAAA,EAAAA,EAAMJ,OAAsBI,EAAKiD,QAAU,OAAU,MAAA,CAGrEpB,EAAAzC,EAAI0C,oBAAoBlC,GAGjC,MAAMwC,EAAML,IACRK,IAAQF,IACMU,IAChBT,EAAaC,GACUF,EAAAE,EACfT,EAAAmB,MAAMC,YAAcb,EAAuB,OAAS,GAAA,IAI1DgB,EAAc9D,EAAI+D,iBAAgB,KAC7BtB,EAAAzC,EAAI0C,oBAAoBlC,EAAK,IAIlCwD,EAAchE,EAAIO,2BAClB0D,EAAgBjE,EAAIkE,mBAClB3B,EAAAmB,MAAMG,OACG,WAAfrD,EAAM0C,MAA4C,YAAV,MAAbc,OAAa,EAAAA,EAAAxD,OAAqB,OAASyD,EAExE,MAAME,EAAanE,EAAIoE,gBAAgBC,UAClB,WAAf7D,EAAM0C,MAA+D,YAA1C,OAAA5C,EAAAN,EAAIO,iCAAJ,EAAAD,EAAgCE,SAC/D+B,EAAQmB,MAAMG,OAASQ,EAAA,IAInBC,EAAQ,CAACC,EAAyCC,KACtD,GAAIhC,EAAqB,OAAOA,EAAoB+B,EAAmBC,GACjE,MAAAC,EAAID,EAAKE,wBACR,MAAA,CAAEC,EAAGJ,EAAEK,QAAUH,EAAEI,KAAMC,EAAGP,EAAEQ,QAAUN,EAAEO,IAAI,EAIvD,SAAS5B,EAAYhB,SACf,GAAApC,EAAIiF,WAAY,OAGd,MAAAC,EAAiBlF,EAAImF,oBAC3B,GAAI/C,EAAIgD,QAnHZ,SAA8B7C,EAAyB8C,aACjD,IAAC9C,EAAgB,OAAA,EAErB,IAAI+C,EAA0B/C,EAE9B,KAAO+C,GAAS,CAEV,GAAA,OAAAhF,EAAA+E,EAAME,cAAN,EAAAjF,EAAekF,OACN,IAAA,MAAAC,KAAaJ,EAAME,QAC5B,GAAI,OAAAG,EAAQJ,EAAAK,gBAAW,EAAAD,EAAAE,SAASH,GACvB,OAAA,EAMT,GAAA,OAAAI,EAAAR,EAAMS,qBAAN,EAAAD,EAAsBL,OACb,IAAA,MAAAO,KAAQV,EAAMS,eACnB,GAAAR,EAAQU,aAAaD,GAChB,OAAA,EAMbT,EAAUA,EAAQW,aAAA,CAGb,OAAA,CACT,CAsFsBC,CAAqB9D,EAAIgD,OAAmBF,GAC5D,OAGI,MAAAiB,EAAatF,EAAYuB,EAAIc,MACnC,IAAKiD,KAAe,MAAA1D,OAAA,EAAAA,EAAS0D,IAAa,OAYtC,IAAAC,EACAC,EAKA,GAdFlE,EAAaC,IACbU,IACc,cAAbV,EAAIc,MAAqC,gBAAbd,EAAIc,OAEjCd,EAAIkE,iBAUFnE,EAAaC,GAAM,CACrB,MAAMmE,EACS,aAAbnE,EAAIc,MAAoC,gBAAbd,EAAIc,KAC3Bd,EAAIoE,eAAe,GACnBpE,EAAIqE,QAAQ,GAClB,IAAKF,EAAI,OAEHH,EAAA9B,EAAMiC,EAAIhE,GACN8D,EAAA,CACRzB,QAAS2B,EAAG3B,QACZG,QAASwB,EAAGxB,QACZ2B,QAAStE,EAAIsE,QACbC,SAAUvE,EAAIuE,SACdC,OAAQxE,EAAIwE,OACZC,QAASzE,EAAIyE,QACbzB,OAAQhD,EAAIgD,OACZ0B,cAAe1E,EAAI0E,cACnBC,kBAAmB,OACnBC,sBAAuB,OACzB,KACK,CACL,MAAMC,EAAK7E,EACLgE,EAAA9B,EAAM2C,EAAI1E,GACN8D,EAAA,CACRzB,QAASqC,EAAGrC,QACZG,QAASkC,EAAGlC,QACZ2B,QAASO,EAAGP,QACZC,SAAUM,EAAGN,SACbC,OAAQK,EAAGL,OACXC,QAASI,EAAGJ,QACZzB,OAAQ6B,EAAG7B,OACX0B,cAAeG,EAAGH,cAClBC,kBAAmB,aAChB,OAAAzG,EAAA,OAAAA,EAAA2G,EAAG7B,aAAH,EAAA9E,EAA2ByG,oBAA3BrB,EAAAwB,KAAA5G,EAA+C2G,EAAGE,UAAA,EAErDH,sBAAuB,aACpB,OAAA1G,EAAA,OAAAA,EAAA2G,EAAG7B,aAAH,EAAA9E,EAA2B0G,wBAA3BtB,EAAAwB,KAAA5G,EAAmD2G,EAAGE,UAAA,EAE3D,CAGF,OAAA7G,EAAAmC,EAAO0D,KAAP7F,EAAA4G,KAAAzE,EAAqB2D,EAAKC,EAASrG,EAAIoH,gBAAe,CAIxD,MAAO,KACW5D,IACPI,IACEO,IACCL,GAAA,CAEhB,mKC9PwC,IAAAuD,EAASjH,EAAAkH,WAAAC,EAAA,CAAA,UAAA,WAAA,WAAA,WAAA,UAE3CC,UAAoC,wBACL7H,GAAjBK,0BAAVC,WAERG,EAAAM,aAAc,KACP,GAAAN,EAAAC,IAAAL,UAAQwH,GAEN,OAAAlF,QAAsBtC,GAAG,CAAIkD,KAAM,gBAAYsE,GAAG,2DAIsBH,uGAAnEjH,EAAAqH,UAAAC,GAAAC,GAAAvH,EAAAwH,IAAAJ,iBAAAA,0BAFhB,yDCMO,IAAAH,EAAQjH,EAAAkH,WAAAC,EAAA,oIAGTC,UAAoC,wBAEL7H,GAAjBK,0BAAVC,WACFC,YAA2BH,GAG3B8H,EAA+CzH,EAAA0H,SAAA,KAC3CC,EAAqBxF,KACrB,MAAAyF,EAAOzF,EAAQmC,wBACfuD,GACJtD,EAAGoD,EAAMnD,QAAUoD,EAAKnD,KACxBC,EAAGiD,EAAMhD,QAAUiD,EAAKhD,KAGpBkD,EAAoBC,EAAaA,cAAA,CACnCC,MAAkBb,EAAAc,UAAAC,gCAEpB,UAGKC,EAAAA,gBAAgBL,EAAaD,EAAYV,EAAAiB,SAAAjB,EAAAkB,MAAA,IAIpDrI,EAAAM,aAAc,KACP,GAAAN,EAAAC,IAAAL,UAAQwH,GAEN,OAAAlF,EAAqBlC,EAAAC,IAC1BL,GAAG,CACDkD,KAAM,OAAQwF,UAASnB,EAAAmB,WAAAtI,EAAAC,IACzBmH,GAAGD,EAAA/E,qBAAApC,EAAAC,IACoBwH,GAA0B,0DAWjDR,EAAS,CAAAjH,EAAAuI,OAAAC,KAAA,wSAGR1I,MAAe2I,EAAA,eARTzI,EAAAqH,UAAAC,GAAAC,GAAAvH,EAAAwH,IAAAJ,iBAAAA,0BAHb,oBH9BgB,6BACgB7H,GAAtBM,0BAAAA,kBAEN6I,UAAW,CAACC,EAAelF,EAAgBmF,EAAO,WACtC5I,OAAAA,EAAAA,EAAAC,IAAAJ,KAAAK,EAAAwI,UAAUC,EAAOlF,EAAQmF,EAAA,EAErCC,aAAeF,yBACb9I,OAAUgJ,aAAaF,EAAA,EAG7B,gCA/BgB,6BACgBpJ,GAAtBM,0BAAAA,WACJ,IAAAiJ,kBAA0DC,EAAAA,sBAE9D/I,EAAAM,2BACOT,GACE,OAAAG,EAAAC,IAAAJ,GAASmJ,eAAeC,IACHC,EAAA1B,IAAAsB,EAAAG,GAAA,EAAA,GAC3B,KAIG,YAAApJ,gBACKA,EACT,EACI,SAAAoJ,gBACKH,IAGb,gFAvBE,IAAAK,YAAoC1J,EAAAA,yBAAyBC,4DA0C/C,UAAqB0J,OAAAA,EAAQd,UAAAA,sBACb/I,GAAtBM,0BAAAA,kBAENwJ,SACE,CAAAC,EACAC,aAGM,MAAAC,SAAcD,WAASH,SAAUA,EACjCK,SAAiBF,WAASjB,YAAaA,SAEtCkB,iBACH3J,aAAU6J,iBAAiB,CACzBN,OAAQI,EACRF,WACAhB,UAAWmB,IAEbzJ,OAAAA,EAAAA,EAAAC,IAAAJ,aAAU8J,eAAe,CACvBvJ,WACqB,IAAnBqJ,EACM,CAAA3G,KAAM,OAAQwF,UAAWmB,GACzB,CAAA3G,KAAM,UACdwG,cAIZ"}
1
+ {"version":3,"file":"index.cjs","sources":["../../src/svelte/hooks/use-interaction-manager.svelte.ts","../../src/shared/utils.ts","../../src/svelte/components/GlobalPointerProvider.svelte","../../src/svelte/components/PagePointerProvider.svelte"],"sourcesContent":["import {\n initialState,\n InteractionManagerPlugin,\n InteractionManagerState,\n PointerEventHandlersWithLifecycle,\n} from '@embedpdf/plugin-interaction-manager';\nimport { useCapability, usePlugin } from '@embedpdf/core/svelte';\n\nexport const useInteractionManagerPlugin = () =>\n usePlugin<InteractionManagerPlugin>(InteractionManagerPlugin.id);\nexport const useInteractionManagerCapability = () =>\n useCapability<InteractionManagerPlugin>(InteractionManagerPlugin.id);\n\nexport function useInteractionManager() {\n const capability = useInteractionManagerCapability();\n\n const state = $state({\n get provides() {\n return capability.provides;\n },\n state: initialState as InteractionManagerState,\n });\n\n $effect(() => {\n if (!capability.provides) return;\n return capability.provides.onStateChange((newState) => {\n state.state = newState;\n });\n });\n\n return state;\n}\n\nexport function useCursor() {\n const capability = useInteractionManagerCapability();\n\n const state = $state({\n setCursor: (token: string, cursor: string, prio = 0) => {\n capability.provides?.setCursor(token, cursor, prio);\n },\n removeCursor: (token: string) => {\n capability.provides?.removeCursor(token);\n },\n });\n\n return state;\n}\n\ninterface UsePointerHandlersOptions {\n modeId?: string | string[];\n pageIndex?: number;\n}\n\nexport function usePointerHandlers({ modeId, pageIndex }: UsePointerHandlersOptions = {}) {\n const capability = useInteractionManagerCapability();\n\n return {\n register: (\n handlers: PointerEventHandlersWithLifecycle,\n options?: { modeId?: string | string[]; pageIndex?: number },\n ) => {\n // Use provided options or fall back to hook-level options\n const finalModeId = options?.modeId ?? modeId;\n const finalPageIndex = options?.pageIndex ?? pageIndex;\n\n return finalModeId\n ? capability.provides?.registerHandlers({\n modeId: finalModeId,\n handlers,\n pageIndex: finalPageIndex,\n })\n : capability.provides?.registerAlways({\n scope:\n finalPageIndex !== undefined\n ? { type: 'page', pageIndex: finalPageIndex }\n : { type: 'global' },\n handlers,\n });\n },\n };\n}\n\nexport function useIsPageExclusive() {\n const capability = useInteractionManagerCapability();\n\n const state = $state({\n isPageExclusive: false,\n });\n\n // Initialize and update on changes\n $effect(() => {\n if (!capability.provides) return;\n\n // Set initial value\n const mode = capability.provides.getActiveInteractionMode();\n state.isPageExclusive = mode?.scope === 'page' && !!mode.exclusive;\n\n // Listen for changes\n return capability.provides.onModeChange(() => {\n const mode = capability.provides?.getActiveInteractionMode();\n state.isPageExclusive = mode?.scope === 'page' && !!mode?.exclusive;\n });\n });\n\n return state;\n}\n","import { Position } from '@embedpdf/models';\nimport type {\n InteractionManagerCapability,\n InteractionScope,\n PointerEventHandlers,\n EmbedPdfPointerEvent,\n InteractionExclusionRules,\n} from '@embedpdf/plugin-interaction-manager';\n\n/* -------------------------------------------------- */\n/* event → handler key lookup */\n/* -------------------------------------------------- */\ntype K = keyof PointerEventHandlers;\nconst domEventMap: Record<string, K> = {\n pointerdown: 'onPointerDown',\n pointerup: 'onPointerUp',\n pointermove: 'onPointerMove',\n pointerenter: 'onPointerEnter',\n pointerleave: 'onPointerLeave',\n pointercancel: 'onPointerCancel',\n\n mousedown: 'onMouseDown',\n mouseup: 'onMouseUp',\n mousemove: 'onMouseMove',\n mouseenter: 'onMouseEnter',\n mouseleave: 'onMouseLeave',\n mousecancel: 'onMouseCancel',\n\n click: 'onClick',\n dblclick: 'onDoubleClick',\n\n /* touch → pointer fallback for very old browsers */\n touchstart: 'onPointerDown',\n touchend: 'onPointerUp',\n touchmove: 'onPointerMove',\n touchcancel: 'onPointerCancel',\n};\n\nconst pointerEventTypes = [\n 'pointerdown',\n 'pointerup',\n 'pointermove',\n 'pointerenter',\n 'pointerleave',\n 'pointercancel',\n 'mousedown',\n 'mouseup',\n 'mousemove',\n 'mouseenter',\n 'mouseleave',\n 'mousecancel',\n 'click',\n 'dblclick',\n];\n\nconst touchEventTypes = ['touchstart', 'touchend', 'touchmove', 'touchcancel'];\nconst HAS_POINTER = typeof PointerEvent !== 'undefined';\n// If the browser supports Pointer Events, don't attach legacy touch events to avoid double-dispatch.\nconst allEventTypes = HAS_POINTER ? pointerEventTypes : [...pointerEventTypes, ...touchEventTypes];\n\n/* -------------------------------------------------- */\n/* helper: decide listener options per event type */\n/* -------------------------------------------------- */\nfunction listenerOpts(eventType: string, wantsRawTouch: boolean): AddEventListenerOptions {\n // Only touch events are toggled; pointer/mouse stay non-passive\n return eventType.startsWith('touch') ? { passive: !wantsRawTouch } : { passive: false };\n}\n\nfunction isTouchEvent(evt: Event): evt is TouchEvent {\n return typeof TouchEvent !== 'undefined' && evt instanceof TouchEvent;\n}\n\n/**\n * Check if an element should be excluded based on rules\n * This is in the framework layer, not the plugin\n */\nfunction shouldExcludeElement(element: Element | null, rules: InteractionExclusionRules): boolean {\n if (!element) return false;\n\n let current: Element | null = element;\n\n while (current) {\n // Check classes\n if (rules.classes?.length) {\n for (const className of rules.classes) {\n if (current.classList?.contains(className)) {\n return true;\n }\n }\n }\n\n // Check data attributes\n if (rules.dataAttributes?.length) {\n for (const attr of rules.dataAttributes) {\n if (current.hasAttribute(attr)) {\n return true;\n }\n }\n }\n\n // Move up the DOM tree\n current = current.parentElement;\n }\n\n return false;\n}\n\n/* -------------------------------------------------- */\n/* createPointerProvider */\n/* -------------------------------------------------- */\nexport function createPointerProvider(\n cap: InteractionManagerCapability,\n scope: InteractionScope,\n element: HTMLElement,\n convertEventToPoint?: (evt: PointerEvent, host: HTMLElement) => Position,\n) {\n /* ---------- live handler set --------------------------------------------------- */\n let active: PointerEventHandlers | null = cap.getHandlersForScope(scope);\n\n /* ---------- helper to compute current wantsRawTouch (defaults to true) --------- */\n const wantsRawTouchNow = () => cap.getActiveInteractionMode()?.wantsRawTouch !== false; // default → true\n\n /* ---------- dynamic listener (re)attachment ------------------------------------ */\n const listeners: Record<string, (evt: Event) => void> = {};\n let attachedWithRawTouch = wantsRawTouchNow(); // remember current mode’s wish\n\n const addListeners = (raw: boolean) => {\n allEventTypes.forEach((type) => {\n const fn = (listeners[type] ??= handleEvent);\n element.addEventListener(type, fn, listenerOpts(type, raw));\n });\n };\n const removeListeners = () => {\n allEventTypes.forEach((type) => {\n const fn = listeners[type];\n if (fn) element.removeEventListener(type, fn);\n });\n };\n\n /* attach for the first time */\n addListeners(attachedWithRawTouch);\n element.style.touchAction = attachedWithRawTouch ? 'none' : '';\n\n /* ---------- mode & handler change hooks --------------------------------------- */\n const stopMode = cap.onModeChange(() => {\n /* cursor baseline update for global wrapper */\n if (scope.type === 'global') {\n const mode = cap.getActiveInteractionMode();\n element.style.cursor = mode?.scope === 'global' ? (mode.cursor ?? 'auto') : 'auto';\n }\n\n active = cap.getHandlersForScope(scope);\n\n /* re-attach listeners if wantsRawTouch toggled */\n const raw = wantsRawTouchNow();\n if (raw !== attachedWithRawTouch) {\n removeListeners();\n addListeners(raw);\n attachedWithRawTouch = raw;\n element.style.touchAction = attachedWithRawTouch ? 'none' : '';\n }\n });\n\n const stopHandler = cap.onHandlerChange(() => {\n active = cap.getHandlersForScope(scope);\n });\n\n /* ---------- cursor sync -------------------------------------------------------- */\n const initialMode = cap.getActiveInteractionMode();\n const initialCursor = cap.getCurrentCursor();\n element.style.cursor =\n scope.type === 'global' && initialMode?.scope !== 'global' ? 'auto' : initialCursor;\n\n const stopCursor = cap.onCursorChange((c) => {\n if (scope.type === 'global' && cap.getActiveInteractionMode()?.scope !== 'global') return;\n element.style.cursor = c;\n });\n\n /* ---------- point conversion --------------------------------------------------- */\n const toPos = (e: { clientX: number; clientY: number }, host: HTMLElement): Position => {\n if (convertEventToPoint) return convertEventToPoint(e as PointerEvent, host);\n const r = host.getBoundingClientRect();\n return { x: e.clientX - r.left, y: e.clientY - r.top };\n };\n\n /* ---------- central event handler --------------------------------------------- */\n function handleEvent(evt: Event) {\n if (cap.isPaused()) return;\n\n // Get exclusion rules from capability and check in framework layer\n const exclusionRules = cap.getExclusionRules();\n if (evt.target && shouldExcludeElement(evt.target as Element, exclusionRules)) {\n return; // Skip processing this event\n }\n\n const handlerKey = domEventMap[evt.type];\n if (!handlerKey || !active?.[handlerKey]) return;\n\n /* preventDefault only when mode really wants raw touch */\n if (\n isTouchEvent(evt) &&\n attachedWithRawTouch &&\n (evt.type === 'touchmove' || evt.type === 'touchcancel')\n ) {\n evt.preventDefault();\n }\n\n // ----- normalise ----------------------------------------------------------------\n let pos!: Position;\n let normEvt!: EmbedPdfPointerEvent & {\n target: EventTarget | null;\n currentTarget: EventTarget | null;\n };\n\n if (isTouchEvent(evt)) {\n const tp =\n evt.type === 'touchend' || evt.type === 'touchcancel'\n ? evt.changedTouches[0]\n : evt.touches[0];\n if (!tp) return;\n\n pos = toPos(tp, element);\n normEvt = {\n clientX: tp.clientX,\n clientY: tp.clientY,\n ctrlKey: evt.ctrlKey,\n shiftKey: evt.shiftKey,\n altKey: evt.altKey,\n metaKey: evt.metaKey,\n target: evt.target,\n currentTarget: evt.currentTarget,\n setPointerCapture: () => {},\n releasePointerCapture: () => {},\n };\n } else {\n const pe = evt as PointerEvent;\n pos = toPos(pe, element);\n normEvt = {\n clientX: pe.clientX,\n clientY: pe.clientY,\n ctrlKey: pe.ctrlKey,\n shiftKey: pe.shiftKey,\n altKey: pe.altKey,\n metaKey: pe.metaKey,\n target: pe.target,\n currentTarget: pe.currentTarget,\n setPointerCapture: () => {\n (pe.target as HTMLElement)?.setPointerCapture?.(pe.pointerId);\n },\n releasePointerCapture: () => {\n (pe.target as HTMLElement)?.releasePointerCapture?.(pe.pointerId);\n },\n };\n }\n\n active[handlerKey]?.(pos, normEvt, cap.getActiveMode());\n }\n\n /* ---------- teardown ----------------------------------------------------------- */\n return () => {\n removeListeners();\n stopMode();\n stopCursor();\n stopHandler();\n };\n}\n","<script lang=\"ts\">\n import type { Snippet } from 'svelte';\n import { useInteractionManagerCapability } from '../hooks';\n import { createPointerProvider } from '../../shared/utils';\n import type { HTMLAttributes } from 'svelte/elements';\n\n interface GlobalPointerProviderProps extends HTMLAttributes<HTMLDivElement> {\n children: Snippet;\n class?: string;\n }\n\n let { children, class: propsClass, ...restProps }: GlobalPointerProviderProps = $props();\n\n let ref = $state<HTMLDivElement | null>(null);\n const interactionManagerCapability = useInteractionManagerCapability();\n\n $effect(() => {\n if (!interactionManagerCapability.provides || !ref) return;\n\n return createPointerProvider(interactionManagerCapability.provides, { type: 'global' }, ref);\n });\n</script>\n\n<div bind:this={ref} style:width=\"100%\" style:height=\"100%\" class={propsClass} {...restProps}>\n {@render children()}\n</div>\n","<script lang=\"ts\">\n import { type Position, restorePosition, type Size, transformSize } from '@embedpdf/models';\n import type { Snippet } from 'svelte';\n import type { HTMLAttributes } from 'svelte/elements';\n import { createPointerProvider } from '../../shared/utils';\n import { useInteractionManagerCapability, useIsPageExclusive } from '../hooks';\n\n interface PagePointerProviderProps extends HTMLAttributes<HTMLDivElement> {\n children: Snippet;\n pageIndex: number;\n pageWidth: number;\n pageHeight: number;\n rotation: number;\n scale: number;\n class?: string;\n convertEventToPoint?: (event: PointerEvent, element: HTMLElement) => Position;\n }\n\n let {\n pageIndex,\n children,\n pageWidth,\n pageHeight,\n rotation,\n scale,\n convertEventToPoint,\n class: propsClass,\n ...restProps\n }: PagePointerProviderProps = $props();\n\n let ref = $state<HTMLDivElement | null>(null);\n\n const interactionManagerCapability = useInteractionManagerCapability();\n const isPageExclusive = useIsPageExclusive();\n\n // Memoize the default conversion function\n const defaultConvertEventToPoint = $derived.by(() => {\n return (event: PointerEvent, element: HTMLElement): Position => {\n const rect = element.getBoundingClientRect();\n const displayPoint = {\n x: event.clientX - rect.left,\n y: event.clientY - rect.top,\n };\n\n const displaySize: Size = transformSize(\n { width: pageWidth, height: pageHeight },\n rotation,\n 1,\n );\n\n return restorePosition(displaySize, displayPoint, rotation, scale);\n };\n });\n\n $effect(() => {\n if (!interactionManagerCapability.provides || !ref) return;\n\n return createPointerProvider(\n interactionManagerCapability.provides,\n { type: 'page', pageIndex },\n ref,\n convertEventToPoint || defaultConvertEventToPoint,\n );\n });\n</script>\n\n<div\n bind:this={ref}\n style:position=\"relative\"\n style:width={`${pageWidth}px`}\n style:height={`${pageHeight}px`}\n class={propsClass}\n {...restProps}\n>\n {@render children()}\n {#if isPageExclusive}\n <div\n style:position=\"absolute\"\n style:top=\"0\"\n style:left=\"0\"\n style:right=\"0\"\n style:bottom=\"0\"\n style:z-index=\"10\"\n ></div>\n {/if}\n</div>\n"],"names":["useInteractionManagerCapability","useCapability","InteractionManagerPlugin","id","useIsPageExclusive","capability","state","isPageExclusive","$","user_effect","provides","mode","getActiveInteractionMode","scope","exclusive","onModeChange","_a","mode2","domEventMap","pointerdown","pointerup","pointermove","pointerenter","pointerleave","pointercancel","mousedown","mouseup","mousemove","mouseenter","mouseleave","mousecancel","click","dblclick","touchstart","touchend","touchmove","touchcancel","pointerEventTypes","allEventTypes","PointerEvent","isTouchEvent","evt","TouchEvent","createPointerProvider","cap","element","convertEventToPoint","active","getHandlersForScope","wantsRawTouchNow","wantsRawTouch","listeners","attachedWithRawTouch","addListeners","raw","forEach","type","fn","handleEvent","addEventListener","startsWith","passive","removeListeners","removeEventListener","style","touchAction","stopMode","cursor","stopHandler","onHandlerChange","initialMode","initialCursor","getCurrentCursor","stopCursor","onCursorChange","c","toPos","e","host","r","getBoundingClientRect","x","clientX","left","y","clientY","top","isPaused","exclusionRules","getExclusionRules","target","rules","current","classes","length","className","_b","classList","contains","_c","dataAttributes","attr","hasAttribute","parentElement","shouldExcludeElement","handlerKey","pos","normEvt","preventDefault","tp","changedTouches","touches","ctrlKey","shiftKey","altKey","metaKey","currentTarget","setPointerCapture","releasePointerCapture","pe","call","pointerId","getActiveMode","restProps","rest_props","$$props","ref","interactionManagerCapability","get","bind_this","div","$$value","set","defaultConvertEventToPoint","derived","event","rect","displayPoint","displaySize","transformSize","width","pageWidth","height","restorePosition","rotation","scale","pageIndex","STYLE","$0","consequent","setCursor","token","prio","removeCursor","initialState","onStateChange","newState","usePlugin","modeId","register","handlers","options","finalModeId","finalPageIndex","registerHandlers","registerAlways"],"mappings":"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"}
@@ -7,44 +7,43 @@ import { transformSize, restorePosition } from "@embedpdf/models";
7
7
  const useInteractionManagerPlugin = () => usePlugin(InteractionManagerPlugin.id);
8
8
  const useInteractionManagerCapability = () => useCapability(InteractionManagerPlugin.id);
9
9
  function useInteractionManager() {
10
- const $$d = $.derived(useInteractionManagerCapability), provides = $.derived(() => $.get($$d).provides);
11
- let interactionManagerState = $.state($.proxy(initialState));
10
+ const capability = useInteractionManagerCapability();
11
+ const state = $.proxy({
12
+ get provides() {
13
+ return capability.provides;
14
+ },
15
+ state: initialState
16
+ });
12
17
  $.user_effect(() => {
13
- if (!$.get(provides)) return;
14
- return $.get(provides).onStateChange((state) => {
15
- $.set(interactionManagerState, state, true);
18
+ if (!capability.provides) return;
19
+ return capability.provides.onStateChange((newState) => {
20
+ state.state = newState;
16
21
  });
17
22
  });
18
- return {
19
- get provides() {
20
- return $.get(provides);
21
- },
22
- get state() {
23
- return $.get(interactionManagerState);
24
- }
25
- };
23
+ return state;
26
24
  }
27
25
  function useCursor() {
28
- const $$d_1 = $.derived(useInteractionManagerCapability), provides = $.derived(() => $.get($$d_1).provides);
29
- return {
26
+ const capability = useInteractionManagerCapability();
27
+ const state = $.proxy({
30
28
  setCursor: (token, cursor, prio = 0) => {
31
29
  var _a;
32
- (_a = $.get(provides)) == null ? void 0 : _a.setCursor(token, cursor, prio);
30
+ (_a = capability.provides) == null ? void 0 : _a.setCursor(token, cursor, prio);
33
31
  },
34
32
  removeCursor: (token) => {
35
33
  var _a;
36
- (_a = $.get(provides)) == null ? void 0 : _a.removeCursor(token);
34
+ (_a = capability.provides) == null ? void 0 : _a.removeCursor(token);
37
35
  }
38
- };
36
+ });
37
+ return state;
39
38
  }
40
- function usePointerHandlers({ modeId, pageIndex }) {
41
- const $$d_2 = $.derived(useInteractionManagerCapability), provides = $.derived(() => $.get($$d_2).provides);
39
+ function usePointerHandlers({ modeId, pageIndex } = {}) {
40
+ const capability = useInteractionManagerCapability();
42
41
  return {
43
42
  register: (handlers, options) => {
44
43
  var _a, _b;
45
44
  const finalModeId = (options == null ? void 0 : options.modeId) ?? modeId;
46
45
  const finalPageIndex = (options == null ? void 0 : options.pageIndex) ?? pageIndex;
47
- return finalModeId ? (_a = $.get(provides)) == null ? void 0 : _a.registerHandlers({ modeId: finalModeId, handlers, pageIndex: finalPageIndex }) : (_b = $.get(provides)) == null ? void 0 : _b.registerAlways({
46
+ return finalModeId ? (_a = capability.provides) == null ? void 0 : _a.registerHandlers({ modeId: finalModeId, handlers, pageIndex: finalPageIndex }) : (_b = capability.provides) == null ? void 0 : _b.registerAlways({
48
47
  scope: finalPageIndex !== void 0 ? { type: "page", pageIndex: finalPageIndex } : { type: "global" },
49
48
  handlers
50
49
  });
@@ -52,24 +51,19 @@ function usePointerHandlers({ modeId, pageIndex }) {
52
51
  };
53
52
  }
54
53
  function useIsPageExclusive() {
55
- const $$d_3 = $.derived(useInteractionManagerCapability), cap = $.derived(() => $.get($$d_3).provides);
56
- let isPageExclusive = $.derived(() => {
57
- var _a;
58
- const m = (_a = $.get(cap)) == null ? void 0 : _a.getActiveInteractionMode();
59
- return (m == null ? void 0 : m.scope) === "page" && !!m.exclusive;
60
- });
54
+ const capability = useInteractionManagerCapability();
55
+ const state = $.proxy({ isPageExclusive: false });
61
56
  $.user_effect(() => {
62
- if (!$.get(cap)) return;
63
- return $.get(cap).onModeChange(() => {
64
- const mode = $.get(cap).getActiveInteractionMode();
65
- $.set(isPageExclusive, (mode == null ? void 0 : mode.scope) === "page" && !!(mode == null ? void 0 : mode.exclusive));
57
+ if (!capability.provides) return;
58
+ const mode = capability.provides.getActiveInteractionMode();
59
+ state.isPageExclusive = (mode == null ? void 0 : mode.scope) === "page" && !!mode.exclusive;
60
+ return capability.provides.onModeChange(() => {
61
+ var _a;
62
+ const mode2 = (_a = capability.provides) == null ? void 0 : _a.getActiveInteractionMode();
63
+ state.isPageExclusive = (mode2 == null ? void 0 : mode2.scope) === "page" && !!(mode2 == null ? void 0 : mode2.exclusive);
66
64
  });
67
65
  });
68
- return {
69
- get isPageExclusive() {
70
- return $.get(isPageExclusive);
71
- }
72
- };
66
+ return state;
73
67
  }
74
68
  const domEventMap = {
75
69
  pointerdown: "onPointerDown",
@@ -260,10 +254,10 @@ function GlobalPointerProvider($$anchor, $$props) {
260
254
  $.push($$props, true);
261
255
  let restProps = $.rest_props($$props, ["$$slots", "$$events", "$$legacy", "children", "class"]);
262
256
  let ref = $.state(null);
263
- const $$d = $.derived(useInteractionManagerCapability), cap = $.derived(() => $.get($$d).provides);
257
+ const interactionManagerCapability = useInteractionManagerCapability();
264
258
  $.user_effect(() => {
265
- if (!$.get(cap) || !$.get(ref)) return;
266
- return createPointerProvider($.get(cap), { type: "global" }, $.get(ref));
259
+ if (!interactionManagerCapability.provides || !$.get(ref)) return;
260
+ return createPointerProvider(interactionManagerCapability.provides, { type: "global" }, $.get(ref));
267
261
  });
268
262
  var div = root$1();
269
263
  $.attribute_effect(div, () => ({
@@ -296,8 +290,8 @@ function PagePointerProvider($$anchor, $$props) {
296
290
  "class"
297
291
  ]);
298
292
  let ref = $.state(null);
299
- const $$d = $.derived(useInteractionManagerCapability), cap = $.derived(() => $.get($$d).provides);
300
- const isPageExclusive = $.derived(useIsPageExclusive);
293
+ const interactionManagerCapability = useInteractionManagerCapability();
294
+ const isPageExclusive = useIsPageExclusive();
301
295
  const defaultConvertEventToPoint = $.derived(() => {
302
296
  return (event, element) => {
303
297
  const rect = element.getBoundingClientRect();
@@ -307,8 +301,8 @@ function PagePointerProvider($$anchor, $$props) {
307
301
  };
308
302
  });
309
303
  $.user_effect(() => {
310
- if (!$.get(cap) || !$.get(ref)) return;
311
- return createPointerProvider($.get(cap), { type: "page", pageIndex: $$props.pageIndex }, $.get(ref), $$props.convertEventToPoint || $.get(defaultConvertEventToPoint));
304
+ if (!interactionManagerCapability.provides || !$.get(ref)) return;
305
+ return createPointerProvider(interactionManagerCapability.provides, { type: "page", pageIndex: $$props.pageIndex }, $.get(ref), $$props.convertEventToPoint || $.get(defaultConvertEventToPoint));
312
306
  });
313
307
  var div = root();
314
308
  $.attribute_effect(div, ($0) => ({ class: $$props.class, ...restProps, [$.STYLE]: $0 }), [
@@ -335,7 +329,7 @@ function PagePointerProvider($$anchor, $$props) {
335
329
  $.append($$anchor2, div_1);
336
330
  };
337
331
  $.if(node_1, ($$render) => {
338
- if ($.get(isPageExclusive)) $$render(consequent);
332
+ if (isPageExclusive) $$render(consequent);
339
333
  });
340
334
  }
341
335
  $.reset(div);
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sources":["../../src/svelte/hooks/use-interaction-manager.svelte.ts","../../src/shared/utils.ts","../../src/svelte/components/GlobalPointerProvider.svelte","../../src/svelte/components/PagePointerProvider.svelte"],"sourcesContent":["import {\n initialState,\n InteractionManagerPlugin,\n InteractionManagerState,\n PointerEventHandlersWithLifecycle,\n} from '@embedpdf/plugin-interaction-manager';\nimport { useCapability, usePlugin } from '@embedpdf/core/svelte';\n\nexport const useInteractionManagerPlugin = () =>\n usePlugin<InteractionManagerPlugin>(InteractionManagerPlugin.id);\nexport const useInteractionManagerCapability = () =>\n useCapability<InteractionManagerPlugin>(InteractionManagerPlugin.id);\n\nexport function useInteractionManager() {\n const { provides } = $derived(useInteractionManagerCapability());\n let interactionManagerState = $state<InteractionManagerState>(initialState);\n\n $effect(() => {\n if (!provides) return;\n return provides.onStateChange((state) => {\n interactionManagerState = state;\n });\n });\n\n return {\n get provides() {\n return provides;\n },\n get state() {\n return interactionManagerState;\n },\n };\n}\n\nexport function useCursor() {\n const { provides } = $derived(useInteractionManagerCapability());\n return {\n setCursor: (token: string, cursor: string, prio = 0) => {\n provides?.setCursor(token, cursor, prio);\n },\n removeCursor: (token: string) => {\n provides?.removeCursor(token);\n },\n };\n}\n\ninterface UsePointerHandlersOptions {\n modeId?: string | string[];\n pageIndex?: number;\n}\n\nexport function usePointerHandlers({ modeId, pageIndex }: UsePointerHandlersOptions) {\n const { provides } = $derived(useInteractionManagerCapability());\n return {\n register: (\n handlers: PointerEventHandlersWithLifecycle,\n options?: { modeId?: string | string[]; pageIndex?: number },\n ) => {\n // Use provided options or fall back to hook-level options\n const finalModeId = options?.modeId ?? modeId;\n const finalPageIndex = options?.pageIndex ?? pageIndex;\n\n return finalModeId\n ? provides?.registerHandlers({\n modeId: finalModeId,\n handlers,\n pageIndex: finalPageIndex,\n })\n : provides?.registerAlways({\n scope:\n finalPageIndex !== undefined\n ? { type: 'page', pageIndex: finalPageIndex }\n : { type: 'global' },\n handlers,\n });\n },\n };\n}\n\nexport function useIsPageExclusive() {\n const { provides: cap } = $derived(useInteractionManagerCapability());\n let isPageExclusive = $derived.by(() => {\n const m = cap?.getActiveInteractionMode();\n return m?.scope === 'page' && !!m.exclusive;\n });\n\n $effect(() => {\n if (!cap) return;\n\n return cap.onModeChange(() => {\n const mode = cap.getActiveInteractionMode();\n isPageExclusive = mode?.scope === 'page' && !!mode?.exclusive;\n });\n });\n\n return {\n get isPageExclusive() {\n return isPageExclusive;\n },\n };\n}\n","import { Position } from '@embedpdf/models';\nimport type {\n InteractionManagerCapability,\n InteractionScope,\n PointerEventHandlers,\n EmbedPdfPointerEvent,\n InteractionExclusionRules,\n} from '@embedpdf/plugin-interaction-manager';\n\n/* -------------------------------------------------- */\n/* event → handler key lookup */\n/* -------------------------------------------------- */\ntype K = keyof PointerEventHandlers;\nconst domEventMap: Record<string, K> = {\n pointerdown: 'onPointerDown',\n pointerup: 'onPointerUp',\n pointermove: 'onPointerMove',\n pointerenter: 'onPointerEnter',\n pointerleave: 'onPointerLeave',\n pointercancel: 'onPointerCancel',\n\n mousedown: 'onMouseDown',\n mouseup: 'onMouseUp',\n mousemove: 'onMouseMove',\n mouseenter: 'onMouseEnter',\n mouseleave: 'onMouseLeave',\n mousecancel: 'onMouseCancel',\n\n click: 'onClick',\n dblclick: 'onDoubleClick',\n\n /* touch → pointer fallback for very old browsers */\n touchstart: 'onPointerDown',\n touchend: 'onPointerUp',\n touchmove: 'onPointerMove',\n touchcancel: 'onPointerCancel',\n};\n\nconst pointerEventTypes = [\n 'pointerdown',\n 'pointerup',\n 'pointermove',\n 'pointerenter',\n 'pointerleave',\n 'pointercancel',\n 'mousedown',\n 'mouseup',\n 'mousemove',\n 'mouseenter',\n 'mouseleave',\n 'mousecancel',\n 'click',\n 'dblclick',\n];\n\nconst touchEventTypes = ['touchstart', 'touchend', 'touchmove', 'touchcancel'];\nconst HAS_POINTER = typeof PointerEvent !== 'undefined';\n// If the browser supports Pointer Events, don't attach legacy touch events to avoid double-dispatch.\nconst allEventTypes = HAS_POINTER ? pointerEventTypes : [...pointerEventTypes, ...touchEventTypes];\n\n/* -------------------------------------------------- */\n/* helper: decide listener options per event type */\n/* -------------------------------------------------- */\nfunction listenerOpts(eventType: string, wantsRawTouch: boolean): AddEventListenerOptions {\n // Only touch events are toggled; pointer/mouse stay non-passive\n return eventType.startsWith('touch') ? { passive: !wantsRawTouch } : { passive: false };\n}\n\nfunction isTouchEvent(evt: Event): evt is TouchEvent {\n return typeof TouchEvent !== 'undefined' && evt instanceof TouchEvent;\n}\n\n/**\n * Check if an element should be excluded based on rules\n * This is in the framework layer, not the plugin\n */\nfunction shouldExcludeElement(element: Element | null, rules: InteractionExclusionRules): boolean {\n if (!element) return false;\n\n let current: Element | null = element;\n\n while (current) {\n // Check classes\n if (rules.classes?.length) {\n for (const className of rules.classes) {\n if (current.classList?.contains(className)) {\n return true;\n }\n }\n }\n\n // Check data attributes\n if (rules.dataAttributes?.length) {\n for (const attr of rules.dataAttributes) {\n if (current.hasAttribute(attr)) {\n return true;\n }\n }\n }\n\n // Move up the DOM tree\n current = current.parentElement;\n }\n\n return false;\n}\n\n/* -------------------------------------------------- */\n/* createPointerProvider */\n/* -------------------------------------------------- */\nexport function createPointerProvider(\n cap: InteractionManagerCapability,\n scope: InteractionScope,\n element: HTMLElement,\n convertEventToPoint?: (evt: PointerEvent, host: HTMLElement) => Position,\n) {\n /* ---------- live handler set --------------------------------------------------- */\n let active: PointerEventHandlers | null = cap.getHandlersForScope(scope);\n\n /* ---------- helper to compute current wantsRawTouch (defaults to true) --------- */\n const wantsRawTouchNow = () => cap.getActiveInteractionMode()?.wantsRawTouch !== false; // default → true\n\n /* ---------- dynamic listener (re)attachment ------------------------------------ */\n const listeners: Record<string, (evt: Event) => void> = {};\n let attachedWithRawTouch = wantsRawTouchNow(); // remember current mode’s wish\n\n const addListeners = (raw: boolean) => {\n allEventTypes.forEach((type) => {\n const fn = (listeners[type] ??= handleEvent);\n element.addEventListener(type, fn, listenerOpts(type, raw));\n });\n };\n const removeListeners = () => {\n allEventTypes.forEach((type) => {\n const fn = listeners[type];\n if (fn) element.removeEventListener(type, fn);\n });\n };\n\n /* attach for the first time */\n addListeners(attachedWithRawTouch);\n element.style.touchAction = attachedWithRawTouch ? 'none' : '';\n\n /* ---------- mode & handler change hooks --------------------------------------- */\n const stopMode = cap.onModeChange(() => {\n /* cursor baseline update for global wrapper */\n if (scope.type === 'global') {\n const mode = cap.getActiveInteractionMode();\n element.style.cursor = mode?.scope === 'global' ? (mode.cursor ?? 'auto') : 'auto';\n }\n\n active = cap.getHandlersForScope(scope);\n\n /* re-attach listeners if wantsRawTouch toggled */\n const raw = wantsRawTouchNow();\n if (raw !== attachedWithRawTouch) {\n removeListeners();\n addListeners(raw);\n attachedWithRawTouch = raw;\n element.style.touchAction = attachedWithRawTouch ? 'none' : '';\n }\n });\n\n const stopHandler = cap.onHandlerChange(() => {\n active = cap.getHandlersForScope(scope);\n });\n\n /* ---------- cursor sync -------------------------------------------------------- */\n const initialMode = cap.getActiveInteractionMode();\n const initialCursor = cap.getCurrentCursor();\n element.style.cursor =\n scope.type === 'global' && initialMode?.scope !== 'global' ? 'auto' : initialCursor;\n\n const stopCursor = cap.onCursorChange((c) => {\n if (scope.type === 'global' && cap.getActiveInteractionMode()?.scope !== 'global') return;\n element.style.cursor = c;\n });\n\n /* ---------- point conversion --------------------------------------------------- */\n const toPos = (e: { clientX: number; clientY: number }, host: HTMLElement): Position => {\n if (convertEventToPoint) return convertEventToPoint(e as PointerEvent, host);\n const r = host.getBoundingClientRect();\n return { x: e.clientX - r.left, y: e.clientY - r.top };\n };\n\n /* ---------- central event handler --------------------------------------------- */\n function handleEvent(evt: Event) {\n if (cap.isPaused()) return;\n\n // Get exclusion rules from capability and check in framework layer\n const exclusionRules = cap.getExclusionRules();\n if (evt.target && shouldExcludeElement(evt.target as Element, exclusionRules)) {\n return; // Skip processing this event\n }\n\n const handlerKey = domEventMap[evt.type];\n if (!handlerKey || !active?.[handlerKey]) return;\n\n /* preventDefault only when mode really wants raw touch */\n if (\n isTouchEvent(evt) &&\n attachedWithRawTouch &&\n (evt.type === 'touchmove' || evt.type === 'touchcancel')\n ) {\n evt.preventDefault();\n }\n\n // ----- normalise ----------------------------------------------------------------\n let pos!: Position;\n let normEvt!: EmbedPdfPointerEvent & {\n target: EventTarget | null;\n currentTarget: EventTarget | null;\n };\n\n if (isTouchEvent(evt)) {\n const tp =\n evt.type === 'touchend' || evt.type === 'touchcancel'\n ? evt.changedTouches[0]\n : evt.touches[0];\n if (!tp) return;\n\n pos = toPos(tp, element);\n normEvt = {\n clientX: tp.clientX,\n clientY: tp.clientY,\n ctrlKey: evt.ctrlKey,\n shiftKey: evt.shiftKey,\n altKey: evt.altKey,\n metaKey: evt.metaKey,\n target: evt.target,\n currentTarget: evt.currentTarget,\n setPointerCapture: () => {},\n releasePointerCapture: () => {},\n };\n } else {\n const pe = evt as PointerEvent;\n pos = toPos(pe, element);\n normEvt = {\n clientX: pe.clientX,\n clientY: pe.clientY,\n ctrlKey: pe.ctrlKey,\n shiftKey: pe.shiftKey,\n altKey: pe.altKey,\n metaKey: pe.metaKey,\n target: pe.target,\n currentTarget: pe.currentTarget,\n setPointerCapture: () => {\n (pe.target as HTMLElement)?.setPointerCapture?.(pe.pointerId);\n },\n releasePointerCapture: () => {\n (pe.target as HTMLElement)?.releasePointerCapture?.(pe.pointerId);\n },\n };\n }\n\n active[handlerKey]?.(pos, normEvt, cap.getActiveMode());\n }\n\n /* ---------- teardown ----------------------------------------------------------- */\n return () => {\n removeListeners();\n stopMode();\n stopCursor();\n stopHandler();\n };\n}\n","<script lang=\"ts\">\n import type { Snippet } from 'svelte';\n import { useInteractionManagerCapability } from '../hooks';\n import { createPointerProvider } from '../../shared/utils';\n import type { HTMLAttributes } from 'svelte/elements';\n\n interface GlobalPointerProviderProps extends HTMLAttributes<HTMLDivElement> {\n children: Snippet;\n class?: string;\n }\n\n let { children, class: propsClass, ...restProps }: GlobalPointerProviderProps = $props();\n\n let ref = $state<HTMLDivElement | null>(null);\n const { provides: cap } = $derived(useInteractionManagerCapability());\n\n $effect(() => {\n if (!cap || !ref) return;\n\n return createPointerProvider(cap, { type: 'global' }, ref);\n });\n</script>\n\n<div bind:this={ref} style:width=\"100%\" style:height=\"100%\" class={propsClass} {...restProps}>\n {@render children()}\n</div>\n","<script lang=\"ts\">\n import { type Position, restorePosition, type Size, transformSize } from '@embedpdf/models';\n import type { Snippet } from 'svelte';\n import type { HTMLAttributes } from 'svelte/elements';\n import { createPointerProvider } from '../../shared/utils';\n import { useInteractionManagerCapability, useIsPageExclusive } from '../hooks';\n\n interface PagePointerProviderProps extends HTMLAttributes<HTMLDivElement> {\n children: Snippet;\n pageIndex: number;\n pageWidth: number;\n pageHeight: number;\n rotation: number;\n scale: number;\n class?: string;\n convertEventToPoint?: (event: PointerEvent, element: HTMLElement) => Position;\n }\n\n let {\n pageIndex,\n children,\n pageWidth,\n pageHeight,\n rotation,\n scale,\n convertEventToPoint,\n class: propsClass,\n ...restProps\n }: PagePointerProviderProps = $props();\n\n let ref = $state<HTMLDivElement | null>(null);\n\n const { provides: cap } = $derived(useInteractionManagerCapability());\n const isPageExclusive = $derived(useIsPageExclusive());\n\n // Memoize the default conversion function\n const defaultConvertEventToPoint = $derived.by(() => {\n return (event: PointerEvent, element: HTMLElement): Position => {\n const rect = element.getBoundingClientRect();\n const displayPoint = {\n x: event.clientX - rect.left,\n y: event.clientY - rect.top,\n };\n\n const displaySize: Size = transformSize(\n { width: pageWidth, height: pageHeight },\n rotation,\n 1,\n );\n\n return restorePosition(displaySize, displayPoint, rotation, scale);\n };\n });\n\n $effect(() => {\n if (!cap || !ref) return;\n\n return createPointerProvider(\n cap,\n { type: 'page', pageIndex },\n ref,\n convertEventToPoint || defaultConvertEventToPoint,\n );\n });\n</script>\n\n<div\n bind:this={ref}\n style:position=\"relative\"\n style:width={`${pageWidth}px`}\n style:height={`${pageHeight}px`}\n class={propsClass}\n {...restProps}\n>\n {@render children()}\n {#if isPageExclusive}\n <div\n style:position=\"absolute\"\n style:top=\"0\"\n style:left=\"0\"\n style:right=\"0\"\n style:bottom=\"0\"\n style:z-index=\"10\"\n ></div>\n {/if}\n</div>\n"],"names":["_a"],"mappings":"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"}
1
+ {"version":3,"file":"index.js","sources":["../../src/svelte/hooks/use-interaction-manager.svelte.ts","../../src/shared/utils.ts","../../src/svelte/components/GlobalPointerProvider.svelte","../../src/svelte/components/PagePointerProvider.svelte"],"sourcesContent":["import {\n initialState,\n InteractionManagerPlugin,\n InteractionManagerState,\n PointerEventHandlersWithLifecycle,\n} from '@embedpdf/plugin-interaction-manager';\nimport { useCapability, usePlugin } from '@embedpdf/core/svelte';\n\nexport const useInteractionManagerPlugin = () =>\n usePlugin<InteractionManagerPlugin>(InteractionManagerPlugin.id);\nexport const useInteractionManagerCapability = () =>\n useCapability<InteractionManagerPlugin>(InteractionManagerPlugin.id);\n\nexport function useInteractionManager() {\n const capability = useInteractionManagerCapability();\n\n const state = $state({\n get provides() {\n return capability.provides;\n },\n state: initialState as InteractionManagerState,\n });\n\n $effect(() => {\n if (!capability.provides) return;\n return capability.provides.onStateChange((newState) => {\n state.state = newState;\n });\n });\n\n return state;\n}\n\nexport function useCursor() {\n const capability = useInteractionManagerCapability();\n\n const state = $state({\n setCursor: (token: string, cursor: string, prio = 0) => {\n capability.provides?.setCursor(token, cursor, prio);\n },\n removeCursor: (token: string) => {\n capability.provides?.removeCursor(token);\n },\n });\n\n return state;\n}\n\ninterface UsePointerHandlersOptions {\n modeId?: string | string[];\n pageIndex?: number;\n}\n\nexport function usePointerHandlers({ modeId, pageIndex }: UsePointerHandlersOptions = {}) {\n const capability = useInteractionManagerCapability();\n\n return {\n register: (\n handlers: PointerEventHandlersWithLifecycle,\n options?: { modeId?: string | string[]; pageIndex?: number },\n ) => {\n // Use provided options or fall back to hook-level options\n const finalModeId = options?.modeId ?? modeId;\n const finalPageIndex = options?.pageIndex ?? pageIndex;\n\n return finalModeId\n ? capability.provides?.registerHandlers({\n modeId: finalModeId,\n handlers,\n pageIndex: finalPageIndex,\n })\n : capability.provides?.registerAlways({\n scope:\n finalPageIndex !== undefined\n ? { type: 'page', pageIndex: finalPageIndex }\n : { type: 'global' },\n handlers,\n });\n },\n };\n}\n\nexport function useIsPageExclusive() {\n const capability = useInteractionManagerCapability();\n\n const state = $state({\n isPageExclusive: false,\n });\n\n // Initialize and update on changes\n $effect(() => {\n if (!capability.provides) return;\n\n // Set initial value\n const mode = capability.provides.getActiveInteractionMode();\n state.isPageExclusive = mode?.scope === 'page' && !!mode.exclusive;\n\n // Listen for changes\n return capability.provides.onModeChange(() => {\n const mode = capability.provides?.getActiveInteractionMode();\n state.isPageExclusive = mode?.scope === 'page' && !!mode?.exclusive;\n });\n });\n\n return state;\n}\n","import { Position } from '@embedpdf/models';\nimport type {\n InteractionManagerCapability,\n InteractionScope,\n PointerEventHandlers,\n EmbedPdfPointerEvent,\n InteractionExclusionRules,\n} from '@embedpdf/plugin-interaction-manager';\n\n/* -------------------------------------------------- */\n/* event → handler key lookup */\n/* -------------------------------------------------- */\ntype K = keyof PointerEventHandlers;\nconst domEventMap: Record<string, K> = {\n pointerdown: 'onPointerDown',\n pointerup: 'onPointerUp',\n pointermove: 'onPointerMove',\n pointerenter: 'onPointerEnter',\n pointerleave: 'onPointerLeave',\n pointercancel: 'onPointerCancel',\n\n mousedown: 'onMouseDown',\n mouseup: 'onMouseUp',\n mousemove: 'onMouseMove',\n mouseenter: 'onMouseEnter',\n mouseleave: 'onMouseLeave',\n mousecancel: 'onMouseCancel',\n\n click: 'onClick',\n dblclick: 'onDoubleClick',\n\n /* touch → pointer fallback for very old browsers */\n touchstart: 'onPointerDown',\n touchend: 'onPointerUp',\n touchmove: 'onPointerMove',\n touchcancel: 'onPointerCancel',\n};\n\nconst pointerEventTypes = [\n 'pointerdown',\n 'pointerup',\n 'pointermove',\n 'pointerenter',\n 'pointerleave',\n 'pointercancel',\n 'mousedown',\n 'mouseup',\n 'mousemove',\n 'mouseenter',\n 'mouseleave',\n 'mousecancel',\n 'click',\n 'dblclick',\n];\n\nconst touchEventTypes = ['touchstart', 'touchend', 'touchmove', 'touchcancel'];\nconst HAS_POINTER = typeof PointerEvent !== 'undefined';\n// If the browser supports Pointer Events, don't attach legacy touch events to avoid double-dispatch.\nconst allEventTypes = HAS_POINTER ? pointerEventTypes : [...pointerEventTypes, ...touchEventTypes];\n\n/* -------------------------------------------------- */\n/* helper: decide listener options per event type */\n/* -------------------------------------------------- */\nfunction listenerOpts(eventType: string, wantsRawTouch: boolean): AddEventListenerOptions {\n // Only touch events are toggled; pointer/mouse stay non-passive\n return eventType.startsWith('touch') ? { passive: !wantsRawTouch } : { passive: false };\n}\n\nfunction isTouchEvent(evt: Event): evt is TouchEvent {\n return typeof TouchEvent !== 'undefined' && evt instanceof TouchEvent;\n}\n\n/**\n * Check if an element should be excluded based on rules\n * This is in the framework layer, not the plugin\n */\nfunction shouldExcludeElement(element: Element | null, rules: InteractionExclusionRules): boolean {\n if (!element) return false;\n\n let current: Element | null = element;\n\n while (current) {\n // Check classes\n if (rules.classes?.length) {\n for (const className of rules.classes) {\n if (current.classList?.contains(className)) {\n return true;\n }\n }\n }\n\n // Check data attributes\n if (rules.dataAttributes?.length) {\n for (const attr of rules.dataAttributes) {\n if (current.hasAttribute(attr)) {\n return true;\n }\n }\n }\n\n // Move up the DOM tree\n current = current.parentElement;\n }\n\n return false;\n}\n\n/* -------------------------------------------------- */\n/* createPointerProvider */\n/* -------------------------------------------------- */\nexport function createPointerProvider(\n cap: InteractionManagerCapability,\n scope: InteractionScope,\n element: HTMLElement,\n convertEventToPoint?: (evt: PointerEvent, host: HTMLElement) => Position,\n) {\n /* ---------- live handler set --------------------------------------------------- */\n let active: PointerEventHandlers | null = cap.getHandlersForScope(scope);\n\n /* ---------- helper to compute current wantsRawTouch (defaults to true) --------- */\n const wantsRawTouchNow = () => cap.getActiveInteractionMode()?.wantsRawTouch !== false; // default → true\n\n /* ---------- dynamic listener (re)attachment ------------------------------------ */\n const listeners: Record<string, (evt: Event) => void> = {};\n let attachedWithRawTouch = wantsRawTouchNow(); // remember current mode’s wish\n\n const addListeners = (raw: boolean) => {\n allEventTypes.forEach((type) => {\n const fn = (listeners[type] ??= handleEvent);\n element.addEventListener(type, fn, listenerOpts(type, raw));\n });\n };\n const removeListeners = () => {\n allEventTypes.forEach((type) => {\n const fn = listeners[type];\n if (fn) element.removeEventListener(type, fn);\n });\n };\n\n /* attach for the first time */\n addListeners(attachedWithRawTouch);\n element.style.touchAction = attachedWithRawTouch ? 'none' : '';\n\n /* ---------- mode & handler change hooks --------------------------------------- */\n const stopMode = cap.onModeChange(() => {\n /* cursor baseline update for global wrapper */\n if (scope.type === 'global') {\n const mode = cap.getActiveInteractionMode();\n element.style.cursor = mode?.scope === 'global' ? (mode.cursor ?? 'auto') : 'auto';\n }\n\n active = cap.getHandlersForScope(scope);\n\n /* re-attach listeners if wantsRawTouch toggled */\n const raw = wantsRawTouchNow();\n if (raw !== attachedWithRawTouch) {\n removeListeners();\n addListeners(raw);\n attachedWithRawTouch = raw;\n element.style.touchAction = attachedWithRawTouch ? 'none' : '';\n }\n });\n\n const stopHandler = cap.onHandlerChange(() => {\n active = cap.getHandlersForScope(scope);\n });\n\n /* ---------- cursor sync -------------------------------------------------------- */\n const initialMode = cap.getActiveInteractionMode();\n const initialCursor = cap.getCurrentCursor();\n element.style.cursor =\n scope.type === 'global' && initialMode?.scope !== 'global' ? 'auto' : initialCursor;\n\n const stopCursor = cap.onCursorChange((c) => {\n if (scope.type === 'global' && cap.getActiveInteractionMode()?.scope !== 'global') return;\n element.style.cursor = c;\n });\n\n /* ---------- point conversion --------------------------------------------------- */\n const toPos = (e: { clientX: number; clientY: number }, host: HTMLElement): Position => {\n if (convertEventToPoint) return convertEventToPoint(e as PointerEvent, host);\n const r = host.getBoundingClientRect();\n return { x: e.clientX - r.left, y: e.clientY - r.top };\n };\n\n /* ---------- central event handler --------------------------------------------- */\n function handleEvent(evt: Event) {\n if (cap.isPaused()) return;\n\n // Get exclusion rules from capability and check in framework layer\n const exclusionRules = cap.getExclusionRules();\n if (evt.target && shouldExcludeElement(evt.target as Element, exclusionRules)) {\n return; // Skip processing this event\n }\n\n const handlerKey = domEventMap[evt.type];\n if (!handlerKey || !active?.[handlerKey]) return;\n\n /* preventDefault only when mode really wants raw touch */\n if (\n isTouchEvent(evt) &&\n attachedWithRawTouch &&\n (evt.type === 'touchmove' || evt.type === 'touchcancel')\n ) {\n evt.preventDefault();\n }\n\n // ----- normalise ----------------------------------------------------------------\n let pos!: Position;\n let normEvt!: EmbedPdfPointerEvent & {\n target: EventTarget | null;\n currentTarget: EventTarget | null;\n };\n\n if (isTouchEvent(evt)) {\n const tp =\n evt.type === 'touchend' || evt.type === 'touchcancel'\n ? evt.changedTouches[0]\n : evt.touches[0];\n if (!tp) return;\n\n pos = toPos(tp, element);\n normEvt = {\n clientX: tp.clientX,\n clientY: tp.clientY,\n ctrlKey: evt.ctrlKey,\n shiftKey: evt.shiftKey,\n altKey: evt.altKey,\n metaKey: evt.metaKey,\n target: evt.target,\n currentTarget: evt.currentTarget,\n setPointerCapture: () => {},\n releasePointerCapture: () => {},\n };\n } else {\n const pe = evt as PointerEvent;\n pos = toPos(pe, element);\n normEvt = {\n clientX: pe.clientX,\n clientY: pe.clientY,\n ctrlKey: pe.ctrlKey,\n shiftKey: pe.shiftKey,\n altKey: pe.altKey,\n metaKey: pe.metaKey,\n target: pe.target,\n currentTarget: pe.currentTarget,\n setPointerCapture: () => {\n (pe.target as HTMLElement)?.setPointerCapture?.(pe.pointerId);\n },\n releasePointerCapture: () => {\n (pe.target as HTMLElement)?.releasePointerCapture?.(pe.pointerId);\n },\n };\n }\n\n active[handlerKey]?.(pos, normEvt, cap.getActiveMode());\n }\n\n /* ---------- teardown ----------------------------------------------------------- */\n return () => {\n removeListeners();\n stopMode();\n stopCursor();\n stopHandler();\n };\n}\n","<script lang=\"ts\">\n import type { Snippet } from 'svelte';\n import { useInteractionManagerCapability } from '../hooks';\n import { createPointerProvider } from '../../shared/utils';\n import type { HTMLAttributes } from 'svelte/elements';\n\n interface GlobalPointerProviderProps extends HTMLAttributes<HTMLDivElement> {\n children: Snippet;\n class?: string;\n }\n\n let { children, class: propsClass, ...restProps }: GlobalPointerProviderProps = $props();\n\n let ref = $state<HTMLDivElement | null>(null);\n const interactionManagerCapability = useInteractionManagerCapability();\n\n $effect(() => {\n if (!interactionManagerCapability.provides || !ref) return;\n\n return createPointerProvider(interactionManagerCapability.provides, { type: 'global' }, ref);\n });\n</script>\n\n<div bind:this={ref} style:width=\"100%\" style:height=\"100%\" class={propsClass} {...restProps}>\n {@render children()}\n</div>\n","<script lang=\"ts\">\n import { type Position, restorePosition, type Size, transformSize } from '@embedpdf/models';\n import type { Snippet } from 'svelte';\n import type { HTMLAttributes } from 'svelte/elements';\n import { createPointerProvider } from '../../shared/utils';\n import { useInteractionManagerCapability, useIsPageExclusive } from '../hooks';\n\n interface PagePointerProviderProps extends HTMLAttributes<HTMLDivElement> {\n children: Snippet;\n pageIndex: number;\n pageWidth: number;\n pageHeight: number;\n rotation: number;\n scale: number;\n class?: string;\n convertEventToPoint?: (event: PointerEvent, element: HTMLElement) => Position;\n }\n\n let {\n pageIndex,\n children,\n pageWidth,\n pageHeight,\n rotation,\n scale,\n convertEventToPoint,\n class: propsClass,\n ...restProps\n }: PagePointerProviderProps = $props();\n\n let ref = $state<HTMLDivElement | null>(null);\n\n const interactionManagerCapability = useInteractionManagerCapability();\n const isPageExclusive = useIsPageExclusive();\n\n // Memoize the default conversion function\n const defaultConvertEventToPoint = $derived.by(() => {\n return (event: PointerEvent, element: HTMLElement): Position => {\n const rect = element.getBoundingClientRect();\n const displayPoint = {\n x: event.clientX - rect.left,\n y: event.clientY - rect.top,\n };\n\n const displaySize: Size = transformSize(\n { width: pageWidth, height: pageHeight },\n rotation,\n 1,\n );\n\n return restorePosition(displaySize, displayPoint, rotation, scale);\n };\n });\n\n $effect(() => {\n if (!interactionManagerCapability.provides || !ref) return;\n\n return createPointerProvider(\n interactionManagerCapability.provides,\n { type: 'page', pageIndex },\n ref,\n convertEventToPoint || defaultConvertEventToPoint,\n );\n });\n</script>\n\n<div\n bind:this={ref}\n style:position=\"relative\"\n style:width={`${pageWidth}px`}\n style:height={`${pageHeight}px`}\n class={propsClass}\n {...restProps}\n>\n {@render children()}\n {#if isPageExclusive}\n <div\n style:position=\"absolute\"\n style:top=\"0\"\n style:left=\"0\"\n style:right=\"0\"\n style:bottom=\"0\"\n style:z-index=\"10\"\n ></div>\n {/if}\n</div>\n"],"names":["mode","_a"],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@embedpdf/plugin-interaction-manager",
3
- "version": "1.4.0",
3
+ "version": "1.5.0",
4
4
  "type": "module",
5
5
  "license": "MIT",
6
6
  "main": "./dist/index.cjs",
@@ -35,12 +35,12 @@
35
35
  }
36
36
  },
37
37
  "dependencies": {
38
- "@embedpdf/models": "1.4.0"
38
+ "@embedpdf/models": "1.5.0"
39
39
  },
40
40
  "devDependencies": {
41
41
  "@types/react": "^18.2.0",
42
42
  "typescript": "^5.0.0",
43
- "@embedpdf/core": "1.4.0",
43
+ "@embedpdf/core": "1.5.0",
44
44
  "@embedpdf/build": "1.1.0"
45
45
  },
46
46
  "peerDependencies": {
@@ -49,7 +49,7 @@
49
49
  "preact": "^10.26.4",
50
50
  "vue": ">=3.2.0",
51
51
  "svelte": ">=5 <6",
52
- "@embedpdf/core": "1.4.0"
52
+ "@embedpdf/core": "1.5.0"
53
53
  },
54
54
  "files": [
55
55
  "dist",