@signality/core 0.1.2 → 0.1.3
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.
- package/browser/file-dialog/index.d.ts +1 -2
- package/browser/text-selection/index.d.ts +9 -2
- package/fesm2022/signality-core-browser-clipboard.mjs +2 -1
- package/fesm2022/signality-core-browser-clipboard.mjs.map +1 -1
- package/fesm2022/signality-core-browser-file-dialog.mjs +2 -1
- package/fesm2022/signality-core-browser-file-dialog.mjs.map +1 -1
- package/fesm2022/signality-core-browser-fullscreen.mjs +2 -1
- package/fesm2022/signality-core-browser-fullscreen.mjs.map +1 -1
- package/fesm2022/signality-core-browser-listener.mjs +2 -1
- package/fesm2022/signality-core-browser-listener.mjs.map +1 -1
- package/fesm2022/signality-core-browser-media-query.mjs +2 -1
- package/fesm2022/signality-core-browser-media-query.mjs.map +1 -1
- package/fesm2022/signality-core-browser-picture-in-picture.mjs +2 -1
- package/fesm2022/signality-core-browser-picture-in-picture.mjs.map +1 -1
- package/fesm2022/signality-core-browser-speech-recognition.mjs +2 -1
- package/fesm2022/signality-core-browser-speech-recognition.mjs.map +1 -1
- package/fesm2022/signality-core-browser-speech-synthesis.mjs +2 -1
- package/fesm2022/signality-core-browser-speech-synthesis.mjs.map +1 -1
- package/fesm2022/signality-core-browser-storage.mjs +40 -45
- package/fesm2022/signality-core-browser-storage.mjs.map +1 -1
- package/fesm2022/signality-core-browser-text-direction.mjs +2 -1
- package/fesm2022/signality-core-browser-text-direction.mjs.map +1 -1
- package/fesm2022/signality-core-browser-text-selection.mjs +36 -4
- package/fesm2022/signality-core-browser-text-selection.mjs.map +1 -1
- package/fesm2022/signality-core-browser-vibration.mjs +2 -1
- package/fesm2022/signality-core-browser-vibration.mjs.map +1 -1
- package/fesm2022/signality-core-browser-web-notification.mjs +2 -1
- package/fesm2022/signality-core-browser-web-notification.mjs.map +1 -1
- package/fesm2022/signality-core-browser-web-worker.mjs +2 -1
- package/fesm2022/signality-core-browser-web-worker.mjs.map +1 -1
- package/fesm2022/signality-core-elements-dropzone.mjs +2 -1
- package/fesm2022/signality-core-elements-dropzone.mjs.map +1 -1
- package/fesm2022/signality-core-elements-element-focus-within.mjs +2 -1
- package/fesm2022/signality-core-elements-element-focus-within.mjs.map +1 -1
- package/fesm2022/signality-core-elements-element-focus.mjs +2 -1
- package/fesm2022/signality-core-elements-element-focus.mjs.map +1 -1
- package/fesm2022/signality-core-elements-element-size.mjs +2 -1
- package/fesm2022/signality-core-elements-element-size.mjs.map +1 -1
- package/fesm2022/signality-core-elements-on-click-outside.mjs +2 -1
- package/fesm2022/signality-core-elements-on-click-outside.mjs.map +1 -1
- package/fesm2022/signality-core-elements-on-disconnect.mjs +2 -1
- package/fesm2022/signality-core-elements-on-disconnect.mjs.map +1 -1
- package/fesm2022/signality-core-elements-on-long-press.mjs +2 -1
- package/fesm2022/signality-core-elements-on-long-press.mjs.map +1 -1
- package/fesm2022/signality-core-elements-scroll-position.mjs +2 -1
- package/fesm2022/signality-core-elements-scroll-position.mjs.map +1 -1
- package/fesm2022/signality-core-internal.mjs +2 -26
- package/fesm2022/signality-core-internal.mjs.map +1 -1
- package/fesm2022/signality-core-observers-intersection-observer.mjs +2 -1
- package/fesm2022/signality-core-observers-intersection-observer.mjs.map +1 -1
- package/fesm2022/signality-core-observers-mutation-observer.mjs +2 -1
- package/fesm2022/signality-core-observers-mutation-observer.mjs.map +1 -1
- package/fesm2022/signality-core-observers-resize-observer.mjs +2 -1
- package/fesm2022/signality-core-observers-resize-observer.mjs.map +1 -1
- package/fesm2022/signality-core-reactivity-debounced.mjs +2 -1
- package/fesm2022/signality-core-reactivity-debounced.mjs.map +1 -1
- package/fesm2022/signality-core-reactivity-throttled.mjs +2 -1
- package/fesm2022/signality-core-reactivity-throttled.mjs.map +1 -1
- package/fesm2022/signality-core-scheduling-debounce-callback.mjs +2 -1
- package/fesm2022/signality-core-scheduling-debounce-callback.mjs.map +1 -1
- package/fesm2022/signality-core-scheduling-interval.mjs +2 -1
- package/fesm2022/signality-core-scheduling-interval.mjs.map +1 -1
- package/fesm2022/signality-core-scheduling-throttle-callback.mjs +2 -1
- package/fesm2022/signality-core-scheduling-throttle-callback.mjs.map +1 -1
- package/fesm2022/signality-core-utilities.mjs +64 -0
- package/fesm2022/signality-core-utilities.mjs.map +1 -0
- package/fesm2022/signality-core.mjs +1 -0
- package/fesm2022/signality-core.mjs.map +1 -1
- package/index.d.ts +1 -0
- package/internal/utils/index.d.ts +0 -2
- package/package.json +9 -5
- package/utilities/generate-id.d.ts +29 -0
- package/utilities/index.d.ts +3 -0
- /package/{internal/utils → utilities}/to-element.d.ts +0 -0
- /package/{internal/utils → utilities}/to-value.d.ts +0 -0
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"signality-core-elements-element-focus-within.mjs","sources":["../../../projects/core/elements/element-focus-within/index.ts","../../../projects/core/elements/element-focus-within/signality-core-elements-element-focus-within.ts"],"sourcesContent":["import { type CreateSignalOptions, signal, type Signal } from '@angular/core';\nimport { constSignal, setupContext
|
|
1
|
+
{"version":3,"file":"signality-core-elements-element-focus-within.mjs","sources":["../../../projects/core/elements/element-focus-within/index.ts","../../../projects/core/elements/element-focus-within/signality-core-elements-element-focus-within.ts"],"sourcesContent":["import { type CreateSignalOptions, signal, type Signal } from '@angular/core';\nimport { constSignal, setupContext } from '@signality/core/internal';\nimport { toElement } from '@signality/core/utilities';\nimport type { MaybeElementSignal, WithInjector } from '@signality/core/types';\nimport { listener } from '@signality/core/browser/listener';\nimport { onDisconnect } from '@signality/core/elements/on-disconnect';\n\nexport type ElementFocusWithinOptions = CreateSignalOptions<boolean> & WithInjector;\n\n/**\n * Reactive tracking of focus-within state on an element.\n * Detects when focus is inside an element or any of its descendants,\n * analogous to the CSS `:focus-within` pseudo-class.\n *\n * @param target - The element to track focus-within state on\n * @param options - Optional configuration including signal options and injector\n * @returns A signal that is `true` when focus is within the element\n *\n * @example\n * ```typescript\n * @Component({\n * template: `\n * <div #container [class.focused]=\"isFocusedWithin()\">\n * <input placeholder=\"First\" />\n * <input placeholder=\"Second\" />\n * </div>\n * `\n * })\n * export class FocusWithinDemo {\n * readonly container = viewChild<ElementRef>('container');\n * readonly isFocusedWithin = elementFocusWithin(this.container);\n * }\n * ```\n */\nexport function elementFocusWithin(\n target: MaybeElementSignal<HTMLElement>,\n options?: ElementFocusWithinOptions\n): Signal<boolean> {\n const { runInContext } = setupContext(options?.injector, elementFocusWithin);\n\n return runInContext(({ isServer }) => {\n if (isServer) {\n return constSignal(false);\n }\n\n const focused = signal<boolean>(false, options);\n\n listener(target, 'focusin', () => focused.set(true));\n\n listener(target, 'focusout', e => {\n const el = toElement(target);\n\n if (el && e.relatedTarget instanceof Node && el.contains(e.relatedTarget)) {\n return;\n }\n\n focused.set(false);\n });\n\n onDisconnect(target, () => focused.set(false));\n\n return focused.asReadonly();\n });\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":[],"mappings":";;;;;;AASA;;;;;;;;;;;;;;;;;;;;;;;;AAwBG;AACG,SAAU,kBAAkB,CAChC,MAAuC,EACvC,OAAmC,EAAA;AAEnC,IAAA,MAAM,EAAE,YAAY,EAAE,GAAG,YAAY,CAAC,OAAO,EAAE,QAAQ,EAAE,kBAAkB,CAAC;AAE5E,IAAA,OAAO,YAAY,CAAC,CAAC,EAAE,QAAQ,EAAE,KAAI;QACnC,IAAI,QAAQ,EAAE;AACZ,YAAA,OAAO,WAAW,CAAC,KAAK,CAAC;QAC3B;QAEA,MAAM,OAAO,GAAG,MAAM,CAAU,KAAK,EAAE,OAAO,CAAC;AAE/C,QAAA,QAAQ,CAAC,MAAM,EAAE,SAAS,EAAE,MAAM,OAAO,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;AAEpD,QAAA,QAAQ,CAAC,MAAM,EAAE,UAAU,EAAE,CAAC,IAAG;AAC/B,YAAA,MAAM,EAAE,GAAG,SAAS,CAAC,MAAM,CAAC;AAE5B,YAAA,IAAI,EAAE,IAAI,CAAC,CAAC,aAAa,YAAY,IAAI,IAAI,EAAE,CAAC,QAAQ,CAAC,CAAC,CAAC,aAAa,CAAC,EAAE;gBACzE;YACF;AAEA,YAAA,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC;AACpB,QAAA,CAAC,CAAC;AAEF,QAAA,YAAY,CAAC,MAAM,EAAE,MAAM,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC;AAE9C,QAAA,OAAO,OAAO,CAAC,UAAU,EAAE;AAC7B,IAAA,CAAC,CAAC;AACJ;;AC/DA;;AAEG;;;;"}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { signal } from '@angular/core';
|
|
2
|
-
import { setupContext, proxySignal
|
|
2
|
+
import { setupContext, proxySignal } from '@signality/core/internal';
|
|
3
|
+
import { toElement } from '@signality/core/utilities';
|
|
3
4
|
import { listener } from '@signality/core/browser/listener';
|
|
4
5
|
import { onDisconnect } from '@signality/core/elements/on-disconnect';
|
|
5
6
|
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"signality-core-elements-element-focus.mjs","sources":["../../../projects/core/elements/element-focus/index.ts","../../../projects/core/elements/element-focus/signality-core-elements-element-focus.ts"],"sourcesContent":["import { type CreateSignalOptions, signal, type WritableSignal } from '@angular/core';\nimport { proxySignal, setupContext
|
|
1
|
+
{"version":3,"file":"signality-core-elements-element-focus.mjs","sources":["../../../projects/core/elements/element-focus/index.ts","../../../projects/core/elements/element-focus/signality-core-elements-element-focus.ts"],"sourcesContent":["import { type CreateSignalOptions, signal, type WritableSignal } from '@angular/core';\nimport { proxySignal, setupContext } from '@signality/core/internal';\nimport { toElement } from '@signality/core/utilities';\nimport type { MaybeElementSignal, WithInjector } from '@signality/core/types';\nimport { listener } from '@signality/core/browser/listener';\nimport { onDisconnect } from '@signality/core/elements/on-disconnect';\n\nexport interface ElementFocusOptions extends CreateSignalOptions<boolean>, WithInjector {\n /**\n * Track focus using the `:focus-visible` pseudo-class.\n * The browser uses heuristics to determine when focus should be visually indicated\n * (e.g., keyboard navigation, programmatic focus, or when the element requires user attention).\n *\n * @see {@link https://developer.mozilla.org/en-US/docs/Web/CSS/Reference/Selectors/:focus-visible MDN: :focus-visible}\n * @default false\n */\n readonly focusVisible?: boolean;\n\n /**\n * Prevent scrolling to the element when it is focused.\n * @default false\n */\n readonly preventScroll?: boolean;\n}\n\n/**\n * Reactive tracking of focus state on an element.\n * Detects when an element gains or loses focus, and allows programmatically setting focus.\n *\n * @param target - The element to track focus state on\n * @param options - Optional configuration including focusVisible, preventScroll and injector\n * @returns A writable signal that is `true` when the element has focus\n *\n * @example\n * ```typescript\n * @Component({\n * template: `\n * <input #input [class.focused]=\"isFocused()\" />\n * <button (click)=\"isFocused.set(true)\">Focus Input</button>\n * <button (click)=\"isFocused.set(false)\">Blur Input</button>\n * `\n * })\n * export class FocusDemo {\n * readonly input = viewChild<ElementRef>('input');\n * readonly isFocused = elementFocus(this.input);\n * }\n * ```\n */\nexport function elementFocus(\n target: MaybeElementSignal<HTMLElement>,\n options?: ElementFocusOptions\n): WritableSignal<boolean> {\n const { runInContext } = setupContext(options?.injector, elementFocus);\n\n return runInContext(({ isServer }) => {\n if (isServer) {\n return signal(false, options);\n }\n\n const focusVisible = options?.focusVisible ?? false;\n const preventScroll = options?.preventScroll ?? false;\n\n const focused = signal<boolean>(false, options);\n\n listener(target, 'focus', e => {\n focused.set(focusVisible ? (e.target as HTMLElement).matches(':focus-visible') : true);\n });\n\n listener(target, 'blur', () => {\n focused.set(false);\n });\n\n onDisconnect(target, () => {\n focused.set(false);\n });\n\n return proxySignal(focused, {\n set: (value: boolean) => {\n const el = toElement(target);\n const hasFocus = el?.matches(':focus') ?? false;\n\n if (value && !hasFocus) {\n el?.focus({ preventScroll });\n } else if (!value && hasFocus) {\n el?.blur();\n }\n },\n });\n });\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":[],"mappings":";;;;;;AAyBA;;;;;;;;;;;;;;;;;;;;;;AAsBG;AACG,SAAU,YAAY,CAC1B,MAAuC,EACvC,OAA6B,EAAA;AAE7B,IAAA,MAAM,EAAE,YAAY,EAAE,GAAG,YAAY,CAAC,OAAO,EAAE,QAAQ,EAAE,YAAY,CAAC;AAEtE,IAAA,OAAO,YAAY,CAAC,CAAC,EAAE,QAAQ,EAAE,KAAI;QACnC,IAAI,QAAQ,EAAE;AACZ,YAAA,OAAO,MAAM,CAAC,KAAK,EAAE,OAAO,CAAC;QAC/B;AAEA,QAAA,MAAM,YAAY,GAAG,OAAO,EAAE,YAAY,IAAI,KAAK;AACnD,QAAA,MAAM,aAAa,GAAG,OAAO,EAAE,aAAa,IAAI,KAAK;QAErD,MAAM,OAAO,GAAG,MAAM,CAAU,KAAK,EAAE,OAAO,CAAC;AAE/C,QAAA,QAAQ,CAAC,MAAM,EAAE,OAAO,EAAE,CAAC,IAAG;YAC5B,OAAO,CAAC,GAAG,CAAC,YAAY,GAAI,CAAC,CAAC,MAAsB,CAAC,OAAO,CAAC,gBAAgB,CAAC,GAAG,IAAI,CAAC;AACxF,QAAA,CAAC,CAAC;AAEF,QAAA,QAAQ,CAAC,MAAM,EAAE,MAAM,EAAE,MAAK;AAC5B,YAAA,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC;AACpB,QAAA,CAAC,CAAC;AAEF,QAAA,YAAY,CAAC,MAAM,EAAE,MAAK;AACxB,YAAA,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC;AACpB,QAAA,CAAC,CAAC;QAEF,OAAO,WAAW,CAAC,OAAO,EAAE;AAC1B,YAAA,GAAG,EAAE,CAAC,KAAc,KAAI;AACtB,gBAAA,MAAM,EAAE,GAAG,SAAS,CAAC,MAAM,CAAC;gBAC5B,MAAM,QAAQ,GAAG,EAAE,EAAE,OAAO,CAAC,QAAQ,CAAC,IAAI,KAAK;AAE/C,gBAAA,IAAI,KAAK,IAAI,CAAC,QAAQ,EAAE;AACtB,oBAAA,EAAE,EAAE,KAAK,CAAC,EAAE,aAAa,EAAE,CAAC;gBAC9B;AAAO,qBAAA,IAAI,CAAC,KAAK,IAAI,QAAQ,EAAE;oBAC7B,EAAE,EAAE,IAAI,EAAE;gBACZ;YACF,CAAC;AACF,SAAA,CAAC;AACJ,IAAA,CAAC,CAAC;AACJ;;ACzFA;;AAEG;;;;"}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { signal } from '@angular/core';
|
|
2
|
-
import { setupContext, constSignal
|
|
2
|
+
import { setupContext, constSignal } from '@signality/core/internal';
|
|
3
|
+
import { toValue } from '@signality/core/utilities';
|
|
3
4
|
import { resizeObserver } from '@signality/core/observers/resize-observer';
|
|
4
5
|
import { onDisconnect } from '@signality/core/elements/on-disconnect';
|
|
5
6
|
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"signality-core-elements-element-size.mjs","sources":["../../../projects/core/elements/element-size/index.ts","../../../projects/core/elements/element-size/signality-core-elements-element-size.ts"],"sourcesContent":["import { type CreateSignalOptions, signal, type Signal } from '@angular/core';\nimport { constSignal, setupContext
|
|
1
|
+
{"version":3,"file":"signality-core-elements-element-size.mjs","sources":["../../../projects/core/elements/element-size/index.ts","../../../projects/core/elements/element-size/signality-core-elements-element-size.ts"],"sourcesContent":["import { type CreateSignalOptions, signal, type Signal } from '@angular/core';\nimport { constSignal, setupContext } from '@signality/core/internal';\nimport { toValue } from '@signality/core/utilities';\nimport type { MaybeElementSignal, MaybeSignal, WithInjector } from '@signality/core/types';\nimport { resizeObserver } from '@signality/core/observers/resize-observer';\nimport { onDisconnect } from '@signality/core/elements/on-disconnect';\n\nexport interface ElementSizeValue {\n readonly width: number;\n readonly height: number;\n}\n\nexport interface ElementSizeOptions extends CreateSignalOptions<ElementSizeValue>, WithInjector {\n /**\n * Which box model to observe. Can be a reactive signal.\n *\n * @default 'border-box'\n */\n readonly box?: MaybeSignal<ResizeObserverBoxOptions>;\n\n /**\n * Initial value for SSR and before the first measurement.\n *\n * @default { width: 0, height: 0 }\n */\n readonly initialValue?: ElementSizeValue;\n}\n\n/**\n * Signal-based wrapper around the [ResizeObserver API](https://developer.mozilla.org/en-US/docs/Web/API/ResizeObserver).\n *\n * @param target - The element to observe\n * @param options - Optional configuration including signal options (equal, debugName), box model, and injector\n * @returns A signal containing the current element dimensions\n *\n * @example\n * ```typescript\n * @Component({\n * template: `\n * <div #box>\n * Size: {{ size().width }} × {{ size().height }}px\n * </div>\n * `\n * })\n * export class ElementSizeDemo {\n * readonly box = viewChild<ElementRef>('box');\n * readonly size = elementSize(this.box);\n * }\n * ```\n */\nexport function elementSize(\n target: MaybeElementSignal<HTMLElement>,\n options?: ElementSizeOptions\n): Signal<ElementSizeValue> {\n const { runInContext } = setupContext(options?.injector, elementSize);\n const initialValue = options?.initialValue ?? DEFAULT_SIZE;\n\n return runInContext(({ isServer }) => {\n if (isServer) {\n return constSignal(initialValue);\n }\n\n const size = signal<ElementSizeValue>(initialValue, options);\n\n const updateSize = ([entry]: readonly ResizeObserverEntry[]) => {\n const box = toValue(options?.box) ?? 'border-box';\n\n if (box === 'content-box') {\n const contentBoxSize = entry.contentBoxSize?.[0];\n size.set({\n width: contentBoxSize?.inlineSize ?? entry.contentRect.width,\n height: contentBoxSize?.blockSize ?? entry.contentRect.height,\n });\n } else {\n const borderBoxSize = entry.borderBoxSize?.[0];\n size.set({\n width: borderBoxSize?.inlineSize ?? entry.contentRect.width,\n height: borderBoxSize?.blockSize ?? entry.contentRect.height,\n });\n }\n };\n\n resizeObserver(target, updateSize, options);\n\n onDisconnect(target, () => size.set(DEFAULT_SIZE));\n\n return size;\n });\n}\n\nconst DEFAULT_SIZE: ElementSizeValue = {\n width: 0,\n height: 0,\n};\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":[],"mappings":";;;;;;AA4BA;;;;;;;;;;;;;;;;;;;;;AAqBG;AACG,SAAU,WAAW,CACzB,MAAuC,EACvC,OAA4B,EAAA;AAE5B,IAAA,MAAM,EAAE,YAAY,EAAE,GAAG,YAAY,CAAC,OAAO,EAAE,QAAQ,EAAE,WAAW,CAAC;AACrE,IAAA,MAAM,YAAY,GAAG,OAAO,EAAE,YAAY,IAAI,YAAY;AAE1D,IAAA,OAAO,YAAY,CAAC,CAAC,EAAE,QAAQ,EAAE,KAAI;QACnC,IAAI,QAAQ,EAAE;AACZ,YAAA,OAAO,WAAW,CAAC,YAAY,CAAC;QAClC;QAEA,MAAM,IAAI,GAAG,MAAM,CAAmB,YAAY,EAAE,OAAO,CAAC;AAE5D,QAAA,MAAM,UAAU,GAAG,CAAC,CAAC,KAAK,CAAiC,KAAI;YAC7D,MAAM,GAAG,GAAG,OAAO,CAAC,OAAO,EAAE,GAAG,CAAC,IAAI,YAAY;AAEjD,YAAA,IAAI,GAAG,KAAK,aAAa,EAAE;gBACzB,MAAM,cAAc,GAAG,KAAK,CAAC,cAAc,GAAG,CAAC,CAAC;gBAChD,IAAI,CAAC,GAAG,CAAC;oBACP,KAAK,EAAE,cAAc,EAAE,UAAU,IAAI,KAAK,CAAC,WAAW,CAAC,KAAK;oBAC5D,MAAM,EAAE,cAAc,EAAE,SAAS,IAAI,KAAK,CAAC,WAAW,CAAC,MAAM;AAC9D,iBAAA,CAAC;YACJ;iBAAO;gBACL,MAAM,aAAa,GAAG,KAAK,CAAC,aAAa,GAAG,CAAC,CAAC;gBAC9C,IAAI,CAAC,GAAG,CAAC;oBACP,KAAK,EAAE,aAAa,EAAE,UAAU,IAAI,KAAK,CAAC,WAAW,CAAC,KAAK;oBAC3D,MAAM,EAAE,aAAa,EAAE,SAAS,IAAI,KAAK,CAAC,WAAW,CAAC,MAAM;AAC7D,iBAAA,CAAC;YACJ;AACF,QAAA,CAAC;AAED,QAAA,cAAc,CAAC,MAAM,EAAE,UAAU,EAAE,OAAO,CAAC;AAE3C,QAAA,YAAY,CAAC,MAAM,EAAE,MAAM,IAAI,CAAC,GAAG,CAAC,YAAY,CAAC,CAAC;AAElD,QAAA,OAAO,IAAI;AACb,IAAA,CAAC,CAAC;AACJ;AAEA,MAAM,YAAY,GAAqB;AACrC,IAAA,KAAK,EAAE,CAAC;AACR,IAAA,MAAM,EAAE,CAAC;CACV;;AC7FD;;AAEG;;;;"}
|
|
@@ -1,4 +1,5 @@
|
|
|
1
|
-
import { setupContext, NOOP_EFFECT_REF
|
|
1
|
+
import { setupContext, NOOP_EFFECT_REF } from '@signality/core/internal';
|
|
2
|
+
import { toElement } from '@signality/core/utilities';
|
|
2
3
|
import { setupSync, listener } from '@signality/core/browser/listener';
|
|
3
4
|
|
|
4
5
|
/**
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"signality-core-elements-on-click-outside.mjs","sources":["../../../projects/core/elements/on-click-outside/index.ts","../../../projects/core/elements/on-click-outside/signality-core-elements-on-click-outside.ts"],"sourcesContent":["import { NOOP_EFFECT_REF, setupContext
|
|
1
|
+
{"version":3,"file":"signality-core-elements-on-click-outside.mjs","sources":["../../../projects/core/elements/on-click-outside/index.ts","../../../projects/core/elements/on-click-outside/signality-core-elements-on-click-outside.ts"],"sourcesContent":["import { NOOP_EFFECT_REF, setupContext } from '@signality/core/internal';\nimport { toElement } from '@signality/core/utilities';\nimport type { MaybeElementSignal, WithInjector } from '@signality/core/types';\nimport { listener, setupSync } from '@signality/core/browser/listener';\n\nexport interface OnClickOutsideOptions extends WithInjector {\n /**\n * Elements that should not trigger the outside click handler.\n */\n readonly ignore?: MaybeElementSignal<Element>[];\n}\n\nexport interface OnClickOutsideRef {\n /** Stops listening for outside clicks. */\n readonly destroy: () => void;\n}\n\n/**\n * Detects clicks outside a target element and invokes a callback.\n * Useful for closing dropdowns, modals, and popovers when the user clicks elsewhere.\n *\n * @param target - Element to detect clicks outside of\n * @param handler - Callback invoked when a click outside the target is detected\n * @param options - Optional configuration including ignore list and injector\n * @returns An OnClickOutsideRef with a destroy method to stop detection\n *\n * @example\n * ```typescript\n * @Component({\n * template: `\n * <div #dropdown class=\"dropdown\">\n * <p>Dropdown content</p>\n * </div>\n * `\n * })\n * export class Dropdown {\n * readonly dropdown = viewChild<ElementRef>('dropdown');\n * readonly isOpen = signal(true);\n *\n * constructor() {\n * onClickOutside(this.dropdown, () => {\n * this.isOpen.set(false);\n * });\n * }\n * }\n * ```\n */\nexport function onClickOutside(\n target: MaybeElementSignal<HTMLElement>,\n handler: (event: PointerEvent | FocusEvent) => void,\n options?: OnClickOutsideOptions\n): OnClickOutsideRef {\n const { runInContext } = setupContext(options?.injector, onClickOutside);\n\n return runInContext(({ isServer }) => {\n if (isServer) {\n return NOOP_EFFECT_REF;\n }\n\n const ignoreList = options?.ignore ?? [];\n\n let shouldFire = false;\n\n function isOutside(event: Event): boolean {\n const el = toElement(target);\n const path = event.composedPath();\n\n if (el && path.includes(el)) {\n return false;\n }\n\n if (ignoreList.length) {\n return !ignoreList.some(ignored => {\n const ignoredEl = toElement(ignored);\n return ignoredEl && path.includes(ignoredEl);\n });\n }\n\n return true;\n }\n\n const pointerDownListener = setupSync(() =>\n listener.capture(window, 'pointerdown', (e: PointerEvent) => {\n shouldFire = isOutside(e);\n })\n );\n\n const clickListener = setupSync(() =>\n listener.capture(window, 'pointerup', (e: PointerEvent) => {\n if (!shouldFire) {\n return;\n }\n\n shouldFire = false;\n\n if (!isOutside(e)) {\n return;\n }\n\n handler(e);\n })\n );\n\n const blurListener = setupSync(() =>\n listener(window, 'blur', (e: FocusEvent) => {\n setTimeout(() => {\n const active = document.activeElement;\n\n if (active?.tagName !== 'IFRAME') {\n return;\n }\n\n const el = toElement(target);\n\n if (el?.contains(active)) {\n return;\n }\n\n handler(e);\n }, 0);\n })\n );\n\n return {\n destroy: () => {\n pointerDownListener.destroy();\n clickListener.destroy();\n blurListener.destroy();\n },\n };\n });\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":[],"mappings":";;;;AAiBA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AA6BG;SACa,cAAc,CAC5B,MAAuC,EACvC,OAAmD,EACnD,OAA+B,EAAA;AAE/B,IAAA,MAAM,EAAE,YAAY,EAAE,GAAG,YAAY,CAAC,OAAO,EAAE,QAAQ,EAAE,cAAc,CAAC;AAExE,IAAA,OAAO,YAAY,CAAC,CAAC,EAAE,QAAQ,EAAE,KAAI;QACnC,IAAI,QAAQ,EAAE;AACZ,YAAA,OAAO,eAAe;QACxB;AAEA,QAAA,MAAM,UAAU,GAAG,OAAO,EAAE,MAAM,IAAI,EAAE;QAExC,IAAI,UAAU,GAAG,KAAK;QAEtB,SAAS,SAAS,CAAC,KAAY,EAAA;AAC7B,YAAA,MAAM,EAAE,GAAG,SAAS,CAAC,MAAM,CAAC;AAC5B,YAAA,MAAM,IAAI,GAAG,KAAK,CAAC,YAAY,EAAE;YAEjC,IAAI,EAAE,IAAI,IAAI,CAAC,QAAQ,CAAC,EAAE,CAAC,EAAE;AAC3B,gBAAA,OAAO,KAAK;YACd;AAEA,YAAA,IAAI,UAAU,CAAC,MAAM,EAAE;AACrB,gBAAA,OAAO,CAAC,UAAU,CAAC,IAAI,CAAC,OAAO,IAAG;AAChC,oBAAA,MAAM,SAAS,GAAG,SAAS,CAAC,OAAO,CAAC;oBACpC,OAAO,SAAS,IAAI,IAAI,CAAC,QAAQ,CAAC,SAAS,CAAC;AAC9C,gBAAA,CAAC,CAAC;YACJ;AAEA,YAAA,OAAO,IAAI;QACb;AAEA,QAAA,MAAM,mBAAmB,GAAG,SAAS,CAAC,MACpC,QAAQ,CAAC,OAAO,CAAC,MAAM,EAAE,aAAa,EAAE,CAAC,CAAe,KAAI;AAC1D,YAAA,UAAU,GAAG,SAAS,CAAC,CAAC,CAAC;QAC3B,CAAC,CAAC,CACH;AAED,QAAA,MAAM,aAAa,GAAG,SAAS,CAAC,MAC9B,QAAQ,CAAC,OAAO,CAAC,MAAM,EAAE,WAAW,EAAE,CAAC,CAAe,KAAI;YACxD,IAAI,CAAC,UAAU,EAAE;gBACf;YACF;YAEA,UAAU,GAAG,KAAK;AAElB,YAAA,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,EAAE;gBACjB;YACF;YAEA,OAAO,CAAC,CAAC,CAAC;QACZ,CAAC,CAAC,CACH;AAED,QAAA,MAAM,YAAY,GAAG,SAAS,CAAC,MAC7B,QAAQ,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAa,KAAI;YACzC,UAAU,CAAC,MAAK;AACd,gBAAA,MAAM,MAAM,GAAG,QAAQ,CAAC,aAAa;AAErC,gBAAA,IAAI,MAAM,EAAE,OAAO,KAAK,QAAQ,EAAE;oBAChC;gBACF;AAEA,gBAAA,MAAM,EAAE,GAAG,SAAS,CAAC,MAAM,CAAC;AAE5B,gBAAA,IAAI,EAAE,EAAE,QAAQ,CAAC,MAAM,CAAC,EAAE;oBACxB;gBACF;gBAEA,OAAO,CAAC,CAAC,CAAC;YACZ,CAAC,EAAE,CAAC,CAAC;QACP,CAAC,CAAC,CACH;QAED,OAAO;YACL,OAAO,EAAE,MAAK;gBACZ,mBAAmB,CAAC,OAAO,EAAE;gBAC7B,aAAa,CAAC,OAAO,EAAE;gBACvB,YAAY,CAAC,OAAO,EAAE;YACxB,CAAC;SACF;AACH,IAAA,CAAC,CAAC;AACJ;;ACnIA;;AAEG;;;;"}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { inject, ElementRef, DestroyRef, afterRenderEffect, afterEveryRender } from '@angular/core';
|
|
2
|
-
import { setupContext, NOOP_EFFECT_REF,
|
|
2
|
+
import { setupContext, NOOP_EFFECT_REF, isQuerySignal } from '@signality/core/internal';
|
|
3
|
+
import { toElement } from '@signality/core/utilities';
|
|
3
4
|
|
|
4
5
|
/**
|
|
5
6
|
* Executes a callback when an element is disconnected from the DOM.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"signality-core-elements-on-disconnect.mjs","sources":["../../../projects/core/elements/on-disconnect/index.ts","../../../projects/core/elements/on-disconnect/signality-core-elements-on-disconnect.ts"],"sourcesContent":["import { afterEveryRender, afterRenderEffect, DestroyRef, ElementRef, inject } from '@angular/core';\nimport { isQuerySignal, NOOP_EFFECT_REF, setupContext
|
|
1
|
+
{"version":3,"file":"signality-core-elements-on-disconnect.mjs","sources":["../../../projects/core/elements/on-disconnect/index.ts","../../../projects/core/elements/on-disconnect/signality-core-elements-on-disconnect.ts"],"sourcesContent":["import { afterEveryRender, afterRenderEffect, DestroyRef, ElementRef, inject } from '@angular/core';\nimport { isQuerySignal, NOOP_EFFECT_REF, setupContext } from '@signality/core/internal';\nimport { toElement } from '@signality/core/utilities';\nimport type { MaybeElementSignal, WithInjector } from '@signality/core/types';\n\nexport type OnDisconnectOptions = WithInjector;\n\nexport interface OnDisconnectRef {\n readonly destroy: () => void;\n}\n\n/**\n * Executes a callback when an element is disconnected from the DOM.\n *\n * @param target - The element to watch for disconnection\n * @param callback - Callback to execute when the element is disconnected\n * @param options - Optional configuration including injector\n * @returns OnDisconnectRef with a destroy method to stop watching for disconnection\n *\n * @example\n * ```typescript\n * @Component({\n * template: `\n * <div #box>Content</div>\n * <button (click)=\"remove()\">Remove</button>\n * `\n * })\n * export class OnDisconnectDemo {\n * readonly box = viewChild<ElementRef>('box');\n *\n * constructor() {\n * onDisconnect(this.box, el => {\n * console.log('Element disconnected: ', el.tagName);\n * // perform cleanup without storing the reference\n * });\n * }\n * }\n * ```\n *\n * @example\n * ```typescript\n * // Manual cleanup\n * const disconnectRef = onDisconnect(element, () => {\n * console.log('Disconnected');\n * });\n *\n * // Stop watching before disconnection\n * disconnectRef.destroy();\n * ```\n */\nexport function onDisconnect<T extends Element>(\n target: MaybeElementSignal<T>,\n callback: (element: T) => void,\n options?: OnDisconnectOptions\n): OnDisconnectRef {\n const { runInContext } = setupContext(options?.injector, onDisconnect);\n\n return runInContext(({ isServer }) => {\n if (isServer) {\n return NOOP_EFFECT_REF;\n }\n\n // (1) Host element check\n // if we are inside a directive and the target element is its host,\n // then we hook into the directive's lifecycle via its DestroyRef\n const hostElRef = inject(ElementRef, { optional: true, self: true });\n if (hostElRef) {\n const targetEl = toElement(target);\n if (targetEl && hostElRef.nativeElement === targetEl) {\n return {\n destroy: inject(DestroyRef).onDestroy(() => callback(targetEl)),\n };\n }\n }\n\n // (2) Query signal check (viewChild/contentChild)\n // if target is a query signal, we rely on its automatic state transition\n // managed by Angular's change detection, calling callback at render completion timing\n if (isQuerySignal(target)) {\n const effectRef = afterRenderEffect({\n read: onCleanup => {\n const targetEl = toElement(target);\n\n if (targetEl) {\n onCleanup(() => {\n if (!targetEl.isConnected) callback(targetEl);\n });\n }\n },\n });\n\n return { destroy: () => effectRef.destroy() };\n }\n\n // (3) Fallback\n // for any DOM target (reactive or non-reactive), we assume the value was\n // manually read from the DOM. Therefore, we perform isConnected check after\n // every render cycle to detect disconnection\n // @TODO: document the behavior of state transitions when the target is reactive\n const afterRenderRef = afterEveryRender({\n read: () => {\n const targetEl = toElement(target);\n if (targetEl && !targetEl.isConnected) callback(targetEl);\n },\n });\n\n return { destroy: () => afterRenderRef.destroy() };\n });\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":[],"mappings":";;;;AAWA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAsCG;SACa,YAAY,CAC1B,MAA6B,EAC7B,QAA8B,EAC9B,OAA6B,EAAA;AAE7B,IAAA,MAAM,EAAE,YAAY,EAAE,GAAG,YAAY,CAAC,OAAO,EAAE,QAAQ,EAAE,YAAY,CAAC;AAEtE,IAAA,OAAO,YAAY,CAAC,CAAC,EAAE,QAAQ,EAAE,KAAI;QACnC,IAAI,QAAQ,EAAE;AACZ,YAAA,OAAO,eAAe;QACxB;;;;AAKA,QAAA,MAAM,SAAS,GAAG,MAAM,CAAC,UAAU,EAAE,EAAE,QAAQ,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC;QACpE,IAAI,SAAS,EAAE;AACb,YAAA,MAAM,QAAQ,GAAG,SAAS,CAAC,MAAM,CAAC;YAClC,IAAI,QAAQ,IAAI,SAAS,CAAC,aAAa,KAAK,QAAQ,EAAE;gBACpD,OAAO;AACL,oBAAA,OAAO,EAAE,MAAM,CAAC,UAAU,CAAC,CAAC,SAAS,CAAC,MAAM,QAAQ,CAAC,QAAQ,CAAC,CAAC;iBAChE;YACH;QACF;;;;AAKA,QAAA,IAAI,aAAa,CAAC,MAAM,CAAC,EAAE;YACzB,MAAM,SAAS,GAAG,iBAAiB,CAAC;gBAClC,IAAI,EAAE,SAAS,IAAG;AAChB,oBAAA,MAAM,QAAQ,GAAG,SAAS,CAAC,MAAM,CAAC;oBAElC,IAAI,QAAQ,EAAE;wBACZ,SAAS,CAAC,MAAK;4BACb,IAAI,CAAC,QAAQ,CAAC,WAAW;gCAAE,QAAQ,CAAC,QAAQ,CAAC;AAC/C,wBAAA,CAAC,CAAC;oBACJ;gBACF,CAAC;AACF,aAAA,CAAC;YAEF,OAAO,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC,OAAO,EAAE,EAAE;QAC/C;;;;;;QAOA,MAAM,cAAc,GAAG,gBAAgB,CAAC;YACtC,IAAI,EAAE,MAAK;AACT,gBAAA,MAAM,QAAQ,GAAG,SAAS,CAAC,MAAM,CAAC;AAClC,gBAAA,IAAI,QAAQ,IAAI,CAAC,QAAQ,CAAC,WAAW;oBAAE,QAAQ,CAAC,QAAQ,CAAC;YAC3D,CAAC;AACF,SAAA,CAAC;QAEF,OAAO,EAAE,OAAO,EAAE,MAAM,cAAc,CAAC,OAAO,EAAE,EAAE;AACpD,IAAA,CAAC,CAAC;AACJ;;AC5GA;;AAEG;;;;"}
|
|
@@ -1,4 +1,5 @@
|
|
|
1
|
-
import { setupContext, NOOP_EFFECT_REF
|
|
1
|
+
import { setupContext, NOOP_EFFECT_REF } from '@signality/core/internal';
|
|
2
|
+
import { toValue } from '@signality/core/utilities';
|
|
2
3
|
import { listener } from '@signality/core/browser/listener';
|
|
3
4
|
|
|
4
5
|
/**
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"signality-core-elements-on-long-press.mjs","sources":["../../../projects/core/elements/on-long-press/index.ts","../../../projects/core/elements/on-long-press/signality-core-elements-on-long-press.ts"],"sourcesContent":["import { NOOP_EFFECT_REF, setupContext, type Timer
|
|
1
|
+
{"version":3,"file":"signality-core-elements-on-long-press.mjs","sources":["../../../projects/core/elements/on-long-press/index.ts","../../../projects/core/elements/on-long-press/signality-core-elements-on-long-press.ts"],"sourcesContent":["import { NOOP_EFFECT_REF, setupContext, type Timer } from '@signality/core/internal';\nimport { toValue } from '@signality/core/utilities';\nimport type { MaybeElementSignal, MaybeSignal, WithInjector } from '@signality/core/types';\nimport { listener } from '@signality/core/browser/listener';\n\nexport interface OnLongPressOptions extends WithInjector {\n /**\n * Time in ms before the callback is triggered.\n * @default 500\n */\n readonly delay?: MaybeSignal<number>;\n\n /**\n * Maximum distance (in pixels) the pointer can move before cancelling.\n * Set to `false` to disable distance checking.\n * @default 10\n */\n readonly distanceThreshold?: number | false;\n}\n\nexport interface OnLongPressRef {\n readonly destroy: () => void;\n}\n\n/**\n * Detect long press gestures on an element.\n * Calls a callback after a configurable delay if the pointer stays down\n * without moving beyond the distance threshold.\n *\n * @param target - The element to detect long presses on\n * @param handler - Callback invoked when a long press is detected\n * @param options - Optional configuration including delay, distance threshold, and injector\n * @returns A OnLongPressRef with a destroy method to stop detection\n *\n * @example\n * ```typescript\n * @Component({\n * template: `<button #btn>Hold me</button>`\n * })\n * export class OnLongPressDemo {\n * readonly btn = viewChild<ElementRef>('btn');\n *\n * constructor() {\n * onLongPress(this.btn, () => {\n * console.log('Long press detected!');\n * });\n * }\n * }\n * ```\n */\nexport function onLongPress(\n target: MaybeElementSignal<HTMLElement>,\n handler: (event: PointerEvent) => void,\n options?: OnLongPressOptions\n): OnLongPressRef {\n const { runInContext } = setupContext(options?.injector, onLongPress);\n\n return runInContext(({ isServer, onCleanup }) => {\n if (isServer) {\n return NOOP_EFFECT_REF;\n }\n\n const distanceThreshold = options?.distanceThreshold;\n\n let startX = 0;\n let startY = 0;\n let longPressTimeout: Timer;\n\n function abortPendingPress(): void {\n clearTimeout(longPressTimeout);\n longPressTimeout = undefined;\n }\n\n const downListener = listener(target, 'pointerdown', (e: PointerEvent) => {\n startX = e.clientX;\n startY = e.clientY;\n\n const delay = toValue(options?.delay) ?? 500;\n\n longPressTimeout = setTimeout(() => {\n handler(e);\n longPressTimeout = undefined;\n }, delay);\n });\n\n const moveListener = listener(target, 'pointermove', (e: PointerEvent) => {\n if (!longPressTimeout || distanceThreshold === false) {\n return;\n }\n\n const threshold = distanceThreshold ?? 10;\n const dx = e.clientX - startX;\n const dy = e.clientY - startY;\n\n if (Math.sqrt(dx * dx + dy * dy) > threshold) {\n abortPendingPress();\n }\n });\n\n const upListener = listener(target, 'pointerup', abortPendingPress);\n const leaveListener = listener(target, 'pointerleave', abortPendingPress);\n\n onCleanup(abortPendingPress);\n\n return {\n destroy: () => {\n abortPendingPress();\n upListener.destroy();\n downListener.destroy();\n moveListener.destroy();\n leaveListener.destroy();\n },\n };\n });\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":[],"mappings":";;;;AAwBA;;;;;;;;;;;;;;;;;;;;;;;;;AAyBG;SACa,WAAW,CACzB,MAAuC,EACvC,OAAsC,EACtC,OAA4B,EAAA;AAE5B,IAAA,MAAM,EAAE,YAAY,EAAE,GAAG,YAAY,CAAC,OAAO,EAAE,QAAQ,EAAE,WAAW,CAAC;IAErE,OAAO,YAAY,CAAC,CAAC,EAAE,QAAQ,EAAE,SAAS,EAAE,KAAI;QAC9C,IAAI,QAAQ,EAAE;AACZ,YAAA,OAAO,eAAe;QACxB;AAEA,QAAA,MAAM,iBAAiB,GAAG,OAAO,EAAE,iBAAiB;QAEpD,IAAI,MAAM,GAAG,CAAC;QACd,IAAI,MAAM,GAAG,CAAC;AACd,QAAA,IAAI,gBAAuB;AAE3B,QAAA,SAAS,iBAAiB,GAAA;YACxB,YAAY,CAAC,gBAAgB,CAAC;YAC9B,gBAAgB,GAAG,SAAS;QAC9B;QAEA,MAAM,YAAY,GAAG,QAAQ,CAAC,MAAM,EAAE,aAAa,EAAE,CAAC,CAAe,KAAI;AACvE,YAAA,MAAM,GAAG,CAAC,CAAC,OAAO;AAClB,YAAA,MAAM,GAAG,CAAC,CAAC,OAAO;YAElB,MAAM,KAAK,GAAG,OAAO,CAAC,OAAO,EAAE,KAAK,CAAC,IAAI,GAAG;AAE5C,YAAA,gBAAgB,GAAG,UAAU,CAAC,MAAK;gBACjC,OAAO,CAAC,CAAC,CAAC;gBACV,gBAAgB,GAAG,SAAS;YAC9B,CAAC,EAAE,KAAK,CAAC;AACX,QAAA,CAAC,CAAC;QAEF,MAAM,YAAY,GAAG,QAAQ,CAAC,MAAM,EAAE,aAAa,EAAE,CAAC,CAAe,KAAI;AACvE,YAAA,IAAI,CAAC,gBAAgB,IAAI,iBAAiB,KAAK,KAAK,EAAE;gBACpD;YACF;AAEA,YAAA,MAAM,SAAS,GAAG,iBAAiB,IAAI,EAAE;AACzC,YAAA,MAAM,EAAE,GAAG,CAAC,CAAC,OAAO,GAAG,MAAM;AAC7B,YAAA,MAAM,EAAE,GAAG,CAAC,CAAC,OAAO,GAAG,MAAM;AAE7B,YAAA,IAAI,IAAI,CAAC,IAAI,CAAC,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,CAAC,GAAG,SAAS,EAAE;AAC5C,gBAAA,iBAAiB,EAAE;YACrB;AACF,QAAA,CAAC,CAAC;QAEF,MAAM,UAAU,GAAG,QAAQ,CAAC,MAAM,EAAE,WAAW,EAAE,iBAAiB,CAAC;QACnE,MAAM,aAAa,GAAG,QAAQ,CAAC,MAAM,EAAE,cAAc,EAAE,iBAAiB,CAAC;QAEzE,SAAS,CAAC,iBAAiB,CAAC;QAE5B,OAAO;YACL,OAAO,EAAE,MAAK;AACZ,gBAAA,iBAAiB,EAAE;gBACnB,UAAU,CAAC,OAAO,EAAE;gBACpB,YAAY,CAAC,OAAO,EAAE;gBACtB,YAAY,CAAC,OAAO,EAAE;gBACtB,aAAa,CAAC,OAAO,EAAE;YACzB,CAAC;SACF;AACH,IAAA,CAAC,CAAC;AACJ;;AClHA;;AAEG;;;;"}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { signal } from '@angular/core';
|
|
2
|
-
import { setupContext, constSignal, isWindow
|
|
2
|
+
import { setupContext, constSignal, isWindow } from '@signality/core/internal';
|
|
3
|
+
import { toElement } from '@signality/core/utilities';
|
|
3
4
|
import { throttleCallback } from '@signality/core/scheduling/throttle-callback';
|
|
4
5
|
import { listener } from '@signality/core/browser/listener';
|
|
5
6
|
import { onDisconnect } from '@signality/core/elements/on-disconnect';
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"signality-core-elements-scroll-position.mjs","sources":["../../../projects/core/elements/scroll-position/index.ts","../../../projects/core/elements/scroll-position/signality-core-elements-scroll-position.ts"],"sourcesContent":["import { type Signal, signal } from '@angular/core';\nimport {\n constSignal,\n isWindow,\n setupContext,\n type Timer,\n toElement,\n} from '@signality/core/internal';\nimport type { MaybeElementSignal, WithInjector } from '@signality/core/types';\nimport { throttleCallback } from '@signality/core/scheduling/throttle-callback';\nimport { listener } from '@signality/core/browser/listener';\nimport { onDisconnect } from '@signality/core/elements/on-disconnect';\n\n/**\n * State indicating which edges have been reached.\n */\nexport interface ArrivedState {\n readonly top: boolean;\n readonly bottom: boolean;\n readonly left: boolean;\n readonly right: boolean;\n}\n\n/**\n * Current scroll directions.\n */\nexport interface ScrollDirections {\n readonly top: boolean;\n readonly bottom: boolean;\n readonly left: boolean;\n readonly right: boolean;\n}\n\nexport interface ScrollPositionOptions extends WithInjector {\n /**\n * Element or window to track scroll on.\n * @default window\n */\n readonly target?: MaybeElementSignal<Element> | Window;\n\n /**\n * Throttle scroll events in milliseconds.\n * @default 0\n */\n readonly throttle?: number;\n\n /**\n * Offset for arrived detection.\n */\n readonly offset?: {\n readonly top?: number;\n readonly bottom?: number;\n readonly left?: number;\n readonly right?: number;\n };\n}\n\nexport interface ScrollPositionRef {\n /** Horizontal scroll position */\n readonly x: Signal<number>;\n\n /** Vertical scroll position */\n readonly y: Signal<number>;\n\n /** Whether currently scrolling */\n readonly isScrolling: Signal<boolean>;\n\n /** Which edges have been reached */\n readonly arrivedState: Signal<ArrivedState>;\n\n /** Current scroll direction */\n readonly directions: Signal<ScrollDirections>;\n}\n\n/**\n * Reactive tracking of scroll position.\n * Track scroll offset of window or any scrollable element.\n *\n * @param options - Optional configuration\n * @returns An object with x, y, isScrolling, arrivedState, and directions signals\n *\n * @example\n * ```typescript\n * @Component({\n * template: `\n * <p>Scroll Y: {{ scrollPos.y() }}px</p>\n * @if (scrollPos.isScrolling()) {\n * <p>Scrolling...</p>\n * }\n * @if (scrollPos.arrivedState().bottom) {\n * <p>Reached bottom!</p>\n * }\n * `\n * })\n * export class ScrollTracker {\n * readonly scrollPos = scrollPosition();\n * }\n * ```\n *\n * @example\n * ```typescript\n * // Track scroll on a specific element\n * @Component({\n * template: `\n * <div #scrollable style=\"overflow: auto; height: 200px;\">\n * <div style=\"height: 1000px;\">Long content</div>\n * </div>\n * <p>Scroll position: {{ pos.y() }}</p>\n * `\n * })\n * export class ScrollableComponent {\n * readonly scrollableEl = viewChild<ElementRef>('scrollable');\n * readonly pos = scrollPosition({ target: this.scrollableEl });\n * }\n * ```\n */\nexport function scrollPosition(options?: ScrollPositionOptions): ScrollPositionRef {\n const { runInContext } = setupContext(options?.injector, scrollPosition);\n\n return runInContext(({ isServer, onCleanup }) => {\n if (isServer) {\n return {\n x: constSignal(0),\n y: constSignal(0),\n isScrolling: constSignal(false),\n arrivedState: constSignal(DEFAULT_ARRIVED),\n directions: constSignal(DEFAULT_DIRECTIONS),\n };\n }\n\n const target = options?.target ?? window;\n const targetIsWindow = isWindow(target);\n const offset = options?.offset ?? {};\n const throttleMs = options?.throttle ?? 0;\n\n const x = signal(0);\n const y = signal(0);\n const isScrolling = signal(false);\n const arrivedState = signal(DEFAULT_ARRIVED);\n const directions = signal(DEFAULT_DIRECTIONS);\n\n let lastX = 0;\n let lastY = 0;\n let scrollingTimeout: Timer;\n\n const getScrollPosition = (): { scrollX: number; scrollY: number } => {\n if (targetIsWindow) {\n return { scrollX: target.scrollX, scrollY: target.scrollY };\n }\n\n const el = toElement(target);\n return {\n scrollX: el?.scrollLeft || 0,\n scrollY: el?.scrollTop || 0,\n };\n };\n\n const getScrollSize = (): {\n scrollWidth: number;\n scrollHeight: number;\n clientWidth: number;\n clientHeight: number;\n } => {\n if (targetIsWindow) {\n return {\n scrollWidth: document.documentElement.scrollWidth,\n scrollHeight: document.documentElement.scrollHeight,\n clientWidth: target.innerWidth,\n clientHeight: target.innerHeight,\n };\n }\n\n const el = toElement(target);\n return {\n scrollWidth: el?.scrollWidth || 0,\n scrollHeight: el?.scrollHeight || 0,\n clientWidth: el?.clientWidth || 0,\n clientHeight: el?.clientHeight || 0,\n };\n };\n\n const update = () => {\n const { scrollX, scrollY } = getScrollPosition();\n const { scrollWidth, scrollHeight, clientWidth, clientHeight } = getScrollSize();\n\n directions.set({\n top: scrollY < lastY,\n bottom: scrollY > lastY,\n left: scrollX < lastX,\n right: scrollX > lastX,\n });\n\n lastX = scrollX;\n lastY = scrollY;\n\n x.set(scrollX);\n y.set(scrollY);\n\n const topOffset = offset.top ?? 0;\n const bottomOffset = offset.bottom ?? 0;\n const leftOffset = offset.left ?? 0;\n const rightOffset = offset.right ?? 0;\n\n arrivedState.set({\n top: scrollY <= topOffset,\n bottom: scrollY + clientHeight >= scrollHeight - bottomOffset,\n left: scrollX <= leftOffset,\n right: scrollX + clientWidth >= scrollWidth - rightOffset,\n });\n\n isScrolling.set(true);\n\n if (scrollingTimeout) {\n clearTimeout(scrollingTimeout);\n }\n\n scrollingTimeout = setTimeout(() => {\n isScrolling.set(false);\n }, SCROLL_IDLE_DELAY);\n };\n\n listener(target, 'scroll', throttleMs > 0 ? throttleCallback(update, throttleMs) : update);\n\n if (!targetIsWindow) {\n onDisconnect(target, () => {\n x.set(0);\n y.set(0);\n isScrolling.set(false);\n arrivedState.set(DEFAULT_ARRIVED);\n directions.set(DEFAULT_DIRECTIONS);\n });\n }\n\n onCleanup(() => {\n if (scrollingTimeout) {\n clearTimeout(scrollingTimeout);\n }\n });\n\n update();\n\n return {\n x: x.asReadonly(),\n y: y.asReadonly(),\n isScrolling: isScrolling.asReadonly(),\n arrivedState: arrivedState.asReadonly(),\n directions: directions.asReadonly(),\n };\n });\n}\n\nconst DEFAULT_ARRIVED: ArrivedState = {\n top: true,\n bottom: false,\n left: true,\n right: false,\n};\n\nconst DEFAULT_DIRECTIONS: ScrollDirections = {\n top: false,\n bottom: false,\n left: false,\n right: false,\n};\n\nconst SCROLL_IDLE_DELAY = 150;\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"signality-core-elements-scroll-position.mjs","sources":["../../../projects/core/elements/scroll-position/index.ts","../../../projects/core/elements/scroll-position/signality-core-elements-scroll-position.ts"],"sourcesContent":["import { type Signal, signal } from '@angular/core';\nimport { constSignal, isWindow, setupContext, type Timer } from '@signality/core/internal';\nimport { toElement } from '@signality/core/utilities';\nimport type { MaybeElementSignal, WithInjector } from '@signality/core/types';\nimport { throttleCallback } from '@signality/core/scheduling/throttle-callback';\nimport { listener } from '@signality/core/browser/listener';\nimport { onDisconnect } from '@signality/core/elements/on-disconnect';\n\n/**\n * State indicating which edges have been reached.\n */\nexport interface ArrivedState {\n readonly top: boolean;\n readonly bottom: boolean;\n readonly left: boolean;\n readonly right: boolean;\n}\n\n/**\n * Current scroll directions.\n */\nexport interface ScrollDirections {\n readonly top: boolean;\n readonly bottom: boolean;\n readonly left: boolean;\n readonly right: boolean;\n}\n\nexport interface ScrollPositionOptions extends WithInjector {\n /**\n * Element or window to track scroll on.\n * @default window\n */\n readonly target?: MaybeElementSignal<Element> | Window;\n\n /**\n * Throttle scroll events in milliseconds.\n * @default 0\n */\n readonly throttle?: number;\n\n /**\n * Offset for arrived detection.\n */\n readonly offset?: {\n readonly top?: number;\n readonly bottom?: number;\n readonly left?: number;\n readonly right?: number;\n };\n}\n\nexport interface ScrollPositionRef {\n /** Horizontal scroll position */\n readonly x: Signal<number>;\n\n /** Vertical scroll position */\n readonly y: Signal<number>;\n\n /** Whether currently scrolling */\n readonly isScrolling: Signal<boolean>;\n\n /** Which edges have been reached */\n readonly arrivedState: Signal<ArrivedState>;\n\n /** Current scroll direction */\n readonly directions: Signal<ScrollDirections>;\n}\n\n/**\n * Reactive tracking of scroll position.\n * Track scroll offset of window or any scrollable element.\n *\n * @param options - Optional configuration\n * @returns An object with x, y, isScrolling, arrivedState, and directions signals\n *\n * @example\n * ```typescript\n * @Component({\n * template: `\n * <p>Scroll Y: {{ scrollPos.y() }}px</p>\n * @if (scrollPos.isScrolling()) {\n * <p>Scrolling...</p>\n * }\n * @if (scrollPos.arrivedState().bottom) {\n * <p>Reached bottom!</p>\n * }\n * `\n * })\n * export class ScrollTracker {\n * readonly scrollPos = scrollPosition();\n * }\n * ```\n *\n * @example\n * ```typescript\n * // Track scroll on a specific element\n * @Component({\n * template: `\n * <div #scrollable style=\"overflow: auto; height: 200px;\">\n * <div style=\"height: 1000px;\">Long content</div>\n * </div>\n * <p>Scroll position: {{ pos.y() }}</p>\n * `\n * })\n * export class ScrollableComponent {\n * readonly scrollableEl = viewChild<ElementRef>('scrollable');\n * readonly pos = scrollPosition({ target: this.scrollableEl });\n * }\n * ```\n */\nexport function scrollPosition(options?: ScrollPositionOptions): ScrollPositionRef {\n const { runInContext } = setupContext(options?.injector, scrollPosition);\n\n return runInContext(({ isServer, onCleanup }) => {\n if (isServer) {\n return {\n x: constSignal(0),\n y: constSignal(0),\n isScrolling: constSignal(false),\n arrivedState: constSignal(DEFAULT_ARRIVED),\n directions: constSignal(DEFAULT_DIRECTIONS),\n };\n }\n\n const target = options?.target ?? window;\n const targetIsWindow = isWindow(target);\n const offset = options?.offset ?? {};\n const throttleMs = options?.throttle ?? 0;\n\n const x = signal(0);\n const y = signal(0);\n const isScrolling = signal(false);\n const arrivedState = signal(DEFAULT_ARRIVED);\n const directions = signal(DEFAULT_DIRECTIONS);\n\n let lastX = 0;\n let lastY = 0;\n let scrollingTimeout: Timer;\n\n const getScrollPosition = (): { scrollX: number; scrollY: number } => {\n if (targetIsWindow) {\n return { scrollX: target.scrollX, scrollY: target.scrollY };\n }\n\n const el = toElement(target);\n return {\n scrollX: el?.scrollLeft || 0,\n scrollY: el?.scrollTop || 0,\n };\n };\n\n const getScrollSize = (): {\n scrollWidth: number;\n scrollHeight: number;\n clientWidth: number;\n clientHeight: number;\n } => {\n if (targetIsWindow) {\n return {\n scrollWidth: document.documentElement.scrollWidth,\n scrollHeight: document.documentElement.scrollHeight,\n clientWidth: target.innerWidth,\n clientHeight: target.innerHeight,\n };\n }\n\n const el = toElement(target);\n return {\n scrollWidth: el?.scrollWidth || 0,\n scrollHeight: el?.scrollHeight || 0,\n clientWidth: el?.clientWidth || 0,\n clientHeight: el?.clientHeight || 0,\n };\n };\n\n const update = () => {\n const { scrollX, scrollY } = getScrollPosition();\n const { scrollWidth, scrollHeight, clientWidth, clientHeight } = getScrollSize();\n\n directions.set({\n top: scrollY < lastY,\n bottom: scrollY > lastY,\n left: scrollX < lastX,\n right: scrollX > lastX,\n });\n\n lastX = scrollX;\n lastY = scrollY;\n\n x.set(scrollX);\n y.set(scrollY);\n\n const topOffset = offset.top ?? 0;\n const bottomOffset = offset.bottom ?? 0;\n const leftOffset = offset.left ?? 0;\n const rightOffset = offset.right ?? 0;\n\n arrivedState.set({\n top: scrollY <= topOffset,\n bottom: scrollY + clientHeight >= scrollHeight - bottomOffset,\n left: scrollX <= leftOffset,\n right: scrollX + clientWidth >= scrollWidth - rightOffset,\n });\n\n isScrolling.set(true);\n\n if (scrollingTimeout) {\n clearTimeout(scrollingTimeout);\n }\n\n scrollingTimeout = setTimeout(() => {\n isScrolling.set(false);\n }, SCROLL_IDLE_DELAY);\n };\n\n listener(target, 'scroll', throttleMs > 0 ? throttleCallback(update, throttleMs) : update);\n\n if (!targetIsWindow) {\n onDisconnect(target, () => {\n x.set(0);\n y.set(0);\n isScrolling.set(false);\n arrivedState.set(DEFAULT_ARRIVED);\n directions.set(DEFAULT_DIRECTIONS);\n });\n }\n\n onCleanup(() => {\n if (scrollingTimeout) {\n clearTimeout(scrollingTimeout);\n }\n });\n\n update();\n\n return {\n x: x.asReadonly(),\n y: y.asReadonly(),\n isScrolling: isScrolling.asReadonly(),\n arrivedState: arrivedState.asReadonly(),\n directions: directions.asReadonly(),\n };\n });\n}\n\nconst DEFAULT_ARRIVED: ArrivedState = {\n top: true,\n bottom: false,\n left: true,\n right: false,\n};\n\nconst DEFAULT_DIRECTIONS: ScrollDirections = {\n top: false,\n bottom: false,\n left: false,\n right: false,\n};\n\nconst SCROLL_IDLE_DELAY = 150;\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":[],"mappings":"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"}
|
|
@@ -118,7 +118,7 @@ function assertElement(value, source) {
|
|
|
118
118
|
}
|
|
119
119
|
function assertEventTarget(value, source) {
|
|
120
120
|
if (!isEventTarget(value)) {
|
|
121
|
-
throw new Error(`[${source}] Expected an EventTarget
|
|
121
|
+
throw new Error(`[${source}] Expected an EventTarget, ElementRef but received: ${value.constructor?.name ?? typeof value}. ` +
|
|
122
122
|
`If you are using viewChild/contentChild, specify "{ read: ElementRef }" to avoid implicit directive references.`);
|
|
123
123
|
}
|
|
124
124
|
}
|
|
@@ -250,34 +250,10 @@ function proxySignal(source, handler) {
|
|
|
250
250
|
return proxy;
|
|
251
251
|
}
|
|
252
252
|
|
|
253
|
-
// @TODO: Consider moving it out of internal
|
|
254
|
-
const toValue = (() => {
|
|
255
|
-
const fn = toValueFn;
|
|
256
|
-
fn.untracked = v => toValueFn(v, true);
|
|
257
|
-
return fn;
|
|
258
|
-
})();
|
|
259
|
-
function toValueFn(maybeSignal, untracked$1 = false) {
|
|
260
|
-
if (isSignal(maybeSignal)) {
|
|
261
|
-
return untracked$1 ? untracked(maybeSignal) : maybeSignal();
|
|
262
|
-
}
|
|
263
|
-
return maybeSignal;
|
|
264
|
-
}
|
|
265
|
-
|
|
266
253
|
function unrefElement(value) {
|
|
267
254
|
return value instanceof ElementRef ? value.nativeElement : value;
|
|
268
255
|
}
|
|
269
256
|
|
|
270
|
-
// @TODO: Consider moving it out of internal
|
|
271
|
-
const toElement = (() => {
|
|
272
|
-
const fn = toElementFn;
|
|
273
|
-
fn.untracked = v => toElementFn(v, true);
|
|
274
|
-
return fn;
|
|
275
|
-
})();
|
|
276
|
-
function toElementFn(maybeSignal, untracked = false) {
|
|
277
|
-
const raw = untracked ? toValue.untracked(maybeSignal) : toValue(maybeSignal);
|
|
278
|
-
return unrefElement(raw);
|
|
279
|
-
}
|
|
280
|
-
|
|
281
257
|
/**
|
|
282
258
|
* Checks whether a file matches the given accept patterns.
|
|
283
259
|
* Follows the native HTML
|
|
@@ -311,5 +287,5 @@ function isAcceptedFile(file, accept) {
|
|
|
311
287
|
* Generated bundle index. Do not edit.
|
|
312
288
|
*/
|
|
313
289
|
|
|
314
|
-
export { ALWAYS_FALSE_FN, IS_BROWSER, IS_MOBILE, IS_SERVER, MOBILE_REGEX, NOOP_ASYNC_FN, NOOP_EFFECT_REF, NOOP_FN, assertElement, assertEventTarget, constSignal, createToken, getActiveElement, getEventTarget, getPipElement, getShadowRoot, isAcceptedFile, isElement, isEventTarget, isNodeWithin, isPlainObject, isQuerySignal, isWindow, proxySignal, setupContext,
|
|
290
|
+
export { ALWAYS_FALSE_FN, IS_BROWSER, IS_MOBILE, IS_SERVER, MOBILE_REGEX, NOOP_ASYNC_FN, NOOP_EFFECT_REF, NOOP_FN, assertElement, assertEventTarget, constSignal, createToken, getActiveElement, getEventTarget, getPipElement, getShadowRoot, isAcceptedFile, isElement, isEventTarget, isNodeWithin, isPlainObject, isQuerySignal, isWindow, proxySignal, setupContext, unrefElement };
|
|
315
291
|
//# sourceMappingURL=signality-core-internal.mjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"signality-core-internal.mjs","sources":["../../../projects/core/internal/constants/mobile-regex.ts","../../../projects/core/internal/constants/stubs.ts","../../../projects/core/internal/providers/is-browser.ts","../../../projects/core/internal/providers/is-mobile.ts","../../../projects/core/internal/providers/is-server.ts","../../../projects/core/internal/utils/bom/is-window.ts","../../../projects/core/internal/utils/dom/get-active-element.ts","../../../projects/core/internal/utils/dom/get-event-target.ts","../../../projects/core/internal/utils/dom/get-pip-element.ts","../../../projects/core/internal/utils/dom/get-shadow-root.ts","../../../projects/core/internal/utils/dom/is-element.ts","../../../projects/core/internal/utils/dom/is-event-target.ts","../../../projects/core/internal/utils/dom/is-node-within.ts","../../../projects/core/internal/utils/assert.ts","../../../projects/core/internal/utils/context.ts","../../../projects/core/internal/utils/create-token.ts","../../../projects/core/internal/utils/is-query-signal.ts","../../../projects/core/internal/utils/is-plain-object.ts","../../../projects/core/internal/utils/const-signal.ts","../../../projects/core/internal/utils/proxy-signal.ts","../../../projects/core/internal/utils/to-value.ts","../../../projects/core/internal/utils/unref-element.ts","../../../projects/core/internal/utils/to-element.ts","../../../projects/core/internal/utils/files/is-accepted-file.ts","../../../projects/core/internal/signality-core-internal.ts"],"sourcesContent":["export const MOBILE_REGEX = /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i;\n","/**\n * Empty synchronous function stub.\n * Used for SSR compatibility when returning method functions in Ref objects that should do nothing on the server.\n *\n * Example: `close: NOOP_FN` in {@link WebNotificationRef}\n */\nexport const NOOP_FN: (...args: any[]) => void = () => {\n /* empty */\n};\n\n/**\n * Empty asynchronous function stub that returns a resolved Promise.\n * Used for SSR compatibility when returning async method functions in Ref objects that should do nothing on the server.\n *\n * Example: `share: NOOP_ASYNC_FN` in {@link WebShareRef}\n */\nexport const NOOP_ASYNC_FN = () => Promise.resolve();\n\n/**\n * Frozen EffectRef stub with a no-op destroy method.\n * Used for SSR compatibility when returning EffectRef from observer utilities (ResizeObserver, MutationObserver, etc.)\n * that cannot run on the server. Prevents errors when calling destroy() on server-rendered refs.\n *\n * Example: `return NOOP_EFFECT_REF` in {@link resizeObserver}\n */\nexport const NOOP_EFFECT_REF = { destroy: NOOP_FN };\n\n/**\n * Equality function that always returns false, forcing signal updates on every change.\n * Used for signals that hold mutable objects (like Selection, Range) where reference equality is not sufficient\n * and we need to detect changes even when the object structure appears the same.\n *\n * Example: `signal<Selection | null>(null, { equal: ALWAYS_FALSE_FN })` in {@link textSelection}\n */\nexport const ALWAYS_FALSE_FN = () => false;\n","import { inject, InjectionToken, PLATFORM_ID } from '@angular/core';\nimport { isPlatformBrowser } from '@angular/common';\n\nexport const IS_BROWSER = new InjectionToken<boolean>(ngDevMode ? 'IS_BROWSER' : '', {\n providedIn: 'platform',\n factory: () => isPlatformBrowser(inject(PLATFORM_ID)),\n});\n","import { inject, InjectionToken } from '@angular/core';\nimport { MOBILE_REGEX } from '../constants';\nimport { IS_BROWSER } from './is-browser';\n\nexport const IS_MOBILE = new InjectionToken<boolean>(ngDevMode ? 'IS_MOBILE' : '', {\n providedIn: 'platform',\n factory: () => {\n return inject(IS_BROWSER) ? MOBILE_REGEX.test(navigator.userAgent) : false;\n },\n});\n","import { inject, InjectionToken, PLATFORM_ID } from '@angular/core';\nimport { isPlatformServer } from '@angular/common';\n\nexport const IS_SERVER = new InjectionToken<boolean>(ngDevMode ? 'IS_SERVER' : '', {\n providedIn: 'platform',\n factory: () => isPlatformServer(inject(PLATFORM_ID)),\n});\n","export function isWindow(obj: object | null): obj is Window {\n return !!obj && (obj as Window).window === obj;\n}\n","export function getActiveElement(document: Document): Element | null {\n let activeElement = document.activeElement;\n\n while (activeElement && activeElement.shadowRoot) {\n const newActiveElement = activeElement.shadowRoot.activeElement;\n if (newActiveElement === activeElement) {\n break;\n } else {\n activeElement = newActiveElement;\n }\n }\n\n return activeElement;\n}\n","export function getEventTarget<T extends EventTarget>(event: Event): T | null {\n return (event.composedPath ? event.composedPath()[0] : event.target) as T | null;\n}\n","export function getPipElement(document: Document): Element | null {\n let pipElement = document.pictureInPictureElement;\n\n while (pipElement && pipElement.shadowRoot) {\n const newPipElement = pipElement.shadowRoot.pictureInPictureElement;\n if (newPipElement === pipElement) {\n break;\n } else {\n pipElement = newPipElement;\n }\n }\n\n return pipElement;\n}\n","export function getShadowRoot(element: Element | null): ShadowRoot | null {\n const rootNode = element?.getRootNode ? element.getRootNode() : null;\n\n if (rootNode instanceof ShadowRoot) {\n return rootNode;\n }\n\n return null;\n}\n","export function isElement(value: unknown): value is Element {\n return !!value && (value as Element).nodeType === Node.ELEMENT_NODE;\n}\n","export function isEventTarget(value: unknown): value is EventTarget {\n return typeof (value as EventTarget)?.addEventListener === 'function';\n}\n","export function isNodeWithin(node: Node, root: Element): boolean {\n return root === node || root.contains(node) || (root.shadowRoot?.contains(node) ?? false);\n}\n","import { isElement, isEventTarget } from './dom';\n\nexport function assertElement(value: unknown, source: string): asserts value is Element {\n if (!isElement(value)) {\n throw new Error(\n `[${source}] Expected a DOM Element, ElementRef but received: ${\n (value as object).constructor?.name ?? typeof value\n }. ` +\n `If you are using viewChild/contentChild, make sure to specify \"{ read: ElementRef }\" to avoid implicit directive references.`\n );\n }\n}\n\nexport function assertEventTarget(value: unknown, source: string): asserts value is EventTarget {\n if (!isEventTarget(value)) {\n throw new Error(\n `[${source}] Expected an EventTarget (e.g. window, DOM Element, ElementRef), but received: ${\n (value as object).constructor?.name ?? typeof value\n }. ` +\n `If you are using viewChild/contentChild, specify \"{ read: ElementRef }\" to avoid implicit directive references.`\n );\n }\n}\n","import {\n assertInInjectionContext,\n DestroyRef,\n inject,\n type Injector,\n INJECTOR,\n isSignal,\n runInInjectionContext,\n type Signal,\n untracked,\n} from '@angular/core';\nimport { SIGNAL, type SignalNode } from '@angular/core/primitives/signals';\nimport { IS_BROWSER, IS_MOBILE, IS_SERVER } from '../providers';\n\nexport interface ContextRef {\n readonly injector: Injector;\n readonly isServer: boolean;\n readonly isBrowser: boolean;\n readonly isMobile: boolean;\n readonly onCleanup: (cleanupFn: () => void) => void;\n}\n\nexport interface SetupContextRef {\n runInContext<T>(fn: (context: ContextRef) => T): T;\n}\n\n/**\n * @internal\n *\n * @param injector - injector to use for context\n * @param debugFn - context owner function\n */\nexport function setupContext(\n injector?: Injector,\n debugFn?: (...args: any[]) => any\n): SetupContextRef {\n if (typeof ngDevMode !== 'undefined' && ngDevMode && !injector) {\n assertInInjectionContext(debugFn || setupContext);\n }\n\n const ctxInjector = injector || inject(INJECTOR);\n\n return {\n runInContext<T>(fn: (context: ContextRef) => T): T {\n return runInContextImpl(fn, ctxInjector, debugFn || setupContext);\n },\n };\n}\n\nfunction runInContextImpl<T>(\n fn: (context: ContextRef) => T,\n injector: Injector,\n debugFn: (...args: any[]) => any\n): T {\n const result = runInInjectionContext(injector, () => {\n const isBrowser = inject(IS_BROWSER);\n const isServer = inject(IS_SERVER);\n const isMobile = inject(IS_MOBILE);\n const destroyRef = inject(DestroyRef);\n\n const onCleanup = (cleanupFn: () => void) => {\n destroyRef.onDestroy(cleanupFn);\n };\n\n return untracked(() => fn({ injector, isBrowser, isServer, isMobile, onCleanup }));\n });\n\n if (typeof ngDevMode !== 'undefined' && ngDevMode && result != null) {\n setupDebugInfo(result, debugFn);\n }\n\n return result;\n}\n\nfunction setupDebugInfo<T>(value: T, debugFn: (...args: any[]) => any): T {\n if (isSignal(value)) {\n setDebugName(value, debugFn);\n } else if (value && typeof value === 'object') {\n for (const [postfix, maybeSignal] of Object.entries(value)) {\n if (isSignal(maybeSignal)) {\n setDebugName(maybeSignal, debugFn, postfix);\n }\n }\n }\n\n return value;\n}\n\nfunction setDebugName(\n signal: Signal<unknown>,\n debugFn: (...args: any[]) => any,\n postfix?: string\n): void {\n const node = signal[SIGNAL] as SignalNode<unknown>;\n\n if (node.debugName === undefined) {\n node.debugName = debugFn.name + (postfix ? '.' + postfix : '');\n }\n}\n","import { InjectionToken, type ProviderToken } from '@angular/core';\n\n/**\n * Creates an Angular InjectionToken with a factory function.\n * @internal\n */\nexport function createToken<T>(\n factory: () => T,\n providedIn: ProvidedIn = 'root'\n): ProviderToken<T> {\n return new InjectionToken(ngDevMode ? factory.name : '', { factory, providedIn });\n}\n\ntype ProvidedIn = NonNullable<ConstructorParameters<typeof InjectionToken>[1]>['providedIn'];\n","import { isSignal, type Signal } from '@angular/core';\nimport { SIGNAL } from '@angular/core/primitives/signals';\n\n/**\n * Determines if a signal is a query signal (viewChild, contentChild).\n * Query signals have a special internal structure with a `_dirtyCounter` property that tracks\n * when query results change.\n\n * See: https://github.com/angular/angular/blob/main/packages/core/src/render3/queries/query_reactive.ts#L43\n * @internal\n */\nexport function isQuerySignal(val: unknown): val is Signal<unknown> {\n if (!isSignal(val)) {\n return false;\n }\n\n const node = val[SIGNAL] as object;\n return '_dirtyCounter' in node;\n}\n","export function isPlainObject(value: unknown): value is Record<PropertyKey, unknown> {\n if (typeof value !== 'object' || value === null) {\n return false;\n }\n\n const prototype = Object.getPrototypeOf(value);\n return prototype === null || prototype === Object.prototype;\n}\n","import type { Signal } from '@angular/core';\nimport {\n SIGNAL,\n SIGNAL_NODE,\n type SignalGetter,\n type SignalNode,\n} from '@angular/core/primitives/signals';\n\n/***\n * Creates a lightweight, readonly signal.\n * This is primarily used to provide fallback values for states that cannot be\n * computed in the current environment. For example:\n * - During SSR where browser-only APIs are unavailable\n * - In environments that lack support for specific APIs\n * @internal\n */\nexport function constSignal<T>(value: T): Signal<T> {\n const node: SignalNode<T> = Object.create(SIGNAL_NODE);\n node.value = value;\n\n const getter = (() => node.value) as SignalGetter<T>;\n (getter as any)[SIGNAL] = node;\n\n if (typeof ngDevMode !== 'undefined' && ngDevMode) {\n const debugName = node.debugName ? ' (' + node.debugName + ')' : '';\n getter.toString = () => `[Signal${debugName}: ${String(node.value)}]`;\n }\n\n return getter;\n}\n","import { type Signal, untracked, type WritableSignal } from '@angular/core';\nimport { SIGNAL, type SignalNode } from '@angular/core/primitives/signals';\n\n/**\n * @internal\n */\nexport interface SignalProxyHandler<T> {\n get?(source: Signal<T>): T;\n set?(value: T, source: WritableSignal<T>): void;\n}\n\n/**\n * Creates a proxy wrapper around a {@link Signal}\n * @internal\n */\nexport function proxySignal<T>(\n source: Signal<T>,\n handler: Omit<SignalProxyHandler<T>, 'set'>\n): Signal<T>;\n\n/**\n * Creates a proxy wrapper around a {@link WritableSignal}\n * @internal\n */\nexport function proxySignal<T>(\n source: WritableSignal<T>,\n handler: SignalProxyHandler<T>\n): WritableSignal<T>;\n\nexport function proxySignal<T>(\n source: Signal<T> | WritableSignal<T>,\n handler: SignalProxyHandler<T>\n): Signal<T> | WritableSignal<T> {\n const node = source[SIGNAL] as SignalNode<T>;\n const isWritable = 'set' in source && typeof source.set === 'function';\n\n const proxy = (handler.get ? () => handler.get!(source) : () => source()) as Signal<T>;\n\n proxy[SIGNAL] = node;\n\n // @TODO: consider (original toString internally reads from the original getter, bypassing the proxy)\n proxy.toString = source.toString;\n\n if (isWritable) {\n const set = handler.set\n ? (value: T) => untracked(() => handler.set!(value, source))\n : (value: T) => source.set(value);\n\n const update = (updater: (current: T) => T) => set(updater(node.value));\n\n (proxy as WritableSignal<T>).set = set;\n (proxy as WritableSignal<T>).update = update;\n (proxy as WritableSignal<T>).asReadonly = () => {\n const getter = source.asReadonly();\n return proxySignal(getter, { get: handler.get?.bind(handler) });\n };\n }\n\n return proxy;\n}\n","import { isSignal, untracked as _untracked } from '@angular/core';\nimport type { MaybeSignal } from '@signality/core/types';\n\nexport interface ToValueFn {\n <T>(maybeSignal: MaybeSignal<T>): T;\n untracked: <T>(maybeSignal: MaybeSignal<T>) => T;\n}\n\n// @TODO: Consider moving it out of internal\nexport const toValue: ToValueFn = (() => {\n const fn = toValueFn as ToValueFn;\n fn.untracked = v => toValueFn(v, true);\n return fn;\n})();\n\nfunction toValueFn<T>(maybeSignal: MaybeSignal<T>, untracked = false): T {\n if (isSignal(maybeSignal)) {\n return untracked ? _untracked(maybeSignal) : maybeSignal();\n }\n return maybeSignal;\n}\n","import { ElementRef } from '@angular/core';\n\nexport function unrefElement<T>(value: T | ElementRef<T>): T {\n return value instanceof ElementRef ? value.nativeElement : value;\n}\n","import { type ElementRef, type Signal } from '@angular/core';\nimport type { MaybeElementSignal } from '@signality/core/types';\nimport { toValue } from './to-value';\nimport { unrefElement } from './unref-element';\n\nexport interface ToElementFn extends ToElementBase {\n untracked: ToElementBase;\n}\n\nexport interface ToElementBase {\n <T extends Element>(element: T | ElementRef<T>): T;\n <T extends Element>(element: Signal<T | ElementRef<T> | null>): T | null;\n <T extends Element>(element: Signal<T | ElementRef<T> | undefined>): T | undefined;\n <T extends Element>(element: Signal<T | ElementRef<T> | null | undefined>): T | null | undefined;\n <T extends Element>(element: T | ElementRef<T> | Signal<T | ElementRef<T> | null | undefined>):\n | T\n | null\n | undefined;\n}\n\n// @TODO: Consider moving it out of internal\nexport const toElement: ToElementFn = (() => {\n const fn = toElementFn as ToElementFn;\n fn.untracked = v => toElementFn(v, true);\n return fn;\n})();\n\nfunction toElementFn<T extends Element>(\n maybeSignal: MaybeElementSignal<T>,\n untracked = false\n): T | null | undefined {\n const raw = untracked ? toValue.untracked(maybeSignal) : toValue(maybeSignal);\n return unrefElement(raw);\n}\n","/**\n * Checks whether a file matches the given accept patterns.\n * Follows the native HTML\n * [`accept`](https://developer.mozilla.org/en-US/docs/Web/HTML/Reference/Attributes/accept) attribute format:\n * MIME types (`'image/png'`), wildcards (`'image/*'`), and file extensions (`'.pdf'`).\n *\n * @param file - File to check\n * @param accept - Comma-separated string of accepted patterns (e.g. `'image/*, .pdf'`)\n * @internal\n */\nexport function isAcceptedFile(file: File, accept: string): boolean {\n if (accept === '*') {\n return true;\n }\n\n const patterns = accept.split(',').map(s => s.trim());\n\n if (patterns.length === 0) {\n return true;\n }\n\n return patterns.some(pattern => {\n if (pattern.startsWith('.')) {\n return file.name.toLowerCase().endsWith(pattern.toLowerCase());\n }\n\n if (pattern.endsWith('/*')) {\n return file.type.startsWith(pattern.slice(0, -1));\n }\n\n return file.type === pattern;\n });\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":["untracked","_untracked"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"signality-core-internal.mjs","sources":["../../../projects/core/internal/constants/mobile-regex.ts","../../../projects/core/internal/constants/stubs.ts","../../../projects/core/internal/providers/is-browser.ts","../../../projects/core/internal/providers/is-mobile.ts","../../../projects/core/internal/providers/is-server.ts","../../../projects/core/internal/utils/bom/is-window.ts","../../../projects/core/internal/utils/dom/get-active-element.ts","../../../projects/core/internal/utils/dom/get-event-target.ts","../../../projects/core/internal/utils/dom/get-pip-element.ts","../../../projects/core/internal/utils/dom/get-shadow-root.ts","../../../projects/core/internal/utils/dom/is-element.ts","../../../projects/core/internal/utils/dom/is-event-target.ts","../../../projects/core/internal/utils/dom/is-node-within.ts","../../../projects/core/internal/utils/assert.ts","../../../projects/core/internal/utils/context.ts","../../../projects/core/internal/utils/create-token.ts","../../../projects/core/internal/utils/is-query-signal.ts","../../../projects/core/internal/utils/is-plain-object.ts","../../../projects/core/internal/utils/const-signal.ts","../../../projects/core/internal/utils/proxy-signal.ts","../../../projects/core/internal/utils/unref-element.ts","../../../projects/core/internal/utils/files/is-accepted-file.ts","../../../projects/core/internal/signality-core-internal.ts"],"sourcesContent":["export const MOBILE_REGEX = /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i;\n","/**\n * Empty synchronous function stub.\n * Used for SSR compatibility when returning method functions in Ref objects that should do nothing on the server.\n *\n * Example: `close: NOOP_FN` in {@link WebNotificationRef}\n */\nexport const NOOP_FN: (...args: any[]) => void = () => {\n /* empty */\n};\n\n/**\n * Empty asynchronous function stub that returns a resolved Promise.\n * Used for SSR compatibility when returning async method functions in Ref objects that should do nothing on the server.\n *\n * Example: `share: NOOP_ASYNC_FN` in {@link WebShareRef}\n */\nexport const NOOP_ASYNC_FN = () => Promise.resolve();\n\n/**\n * Frozen EffectRef stub with a no-op destroy method.\n * Used for SSR compatibility when returning EffectRef from observer utilities (ResizeObserver, MutationObserver, etc.)\n * that cannot run on the server. Prevents errors when calling destroy() on server-rendered refs.\n *\n * Example: `return NOOP_EFFECT_REF` in {@link resizeObserver}\n */\nexport const NOOP_EFFECT_REF = { destroy: NOOP_FN };\n\n/**\n * Equality function that always returns false, forcing signal updates on every change.\n * Used for signals that hold mutable objects (like Selection, Range) where reference equality is not sufficient\n * and we need to detect changes even when the object structure appears the same.\n *\n * Example: `signal<Selection | null>(null, { equal: ALWAYS_FALSE_FN })` in {@link textSelection}\n */\nexport const ALWAYS_FALSE_FN = () => false;\n","import { inject, InjectionToken, PLATFORM_ID } from '@angular/core';\nimport { isPlatformBrowser } from '@angular/common';\n\nexport const IS_BROWSER = new InjectionToken<boolean>(ngDevMode ? 'IS_BROWSER' : '', {\n providedIn: 'platform',\n factory: () => isPlatformBrowser(inject(PLATFORM_ID)),\n});\n","import { inject, InjectionToken } from '@angular/core';\nimport { MOBILE_REGEX } from '../constants';\nimport { IS_BROWSER } from './is-browser';\n\nexport const IS_MOBILE = new InjectionToken<boolean>(ngDevMode ? 'IS_MOBILE' : '', {\n providedIn: 'platform',\n factory: () => {\n return inject(IS_BROWSER) ? MOBILE_REGEX.test(navigator.userAgent) : false;\n },\n});\n","import { inject, InjectionToken, PLATFORM_ID } from '@angular/core';\nimport { isPlatformServer } from '@angular/common';\n\nexport const IS_SERVER = new InjectionToken<boolean>(ngDevMode ? 'IS_SERVER' : '', {\n providedIn: 'platform',\n factory: () => isPlatformServer(inject(PLATFORM_ID)),\n});\n","export function isWindow(obj: object | null): obj is Window {\n return !!obj && (obj as Window).window === obj;\n}\n","export function getActiveElement(document: Document): Element | null {\n let activeElement = document.activeElement;\n\n while (activeElement && activeElement.shadowRoot) {\n const newActiveElement = activeElement.shadowRoot.activeElement;\n if (newActiveElement === activeElement) {\n break;\n } else {\n activeElement = newActiveElement;\n }\n }\n\n return activeElement;\n}\n","export function getEventTarget<T extends EventTarget>(event: Event): T | null {\n return (event.composedPath ? event.composedPath()[0] : event.target) as T | null;\n}\n","export function getPipElement(document: Document): Element | null {\n let pipElement = document.pictureInPictureElement;\n\n while (pipElement && pipElement.shadowRoot) {\n const newPipElement = pipElement.shadowRoot.pictureInPictureElement;\n if (newPipElement === pipElement) {\n break;\n } else {\n pipElement = newPipElement;\n }\n }\n\n return pipElement;\n}\n","export function getShadowRoot(element: Element | null): ShadowRoot | null {\n const rootNode = element?.getRootNode ? element.getRootNode() : null;\n\n if (rootNode instanceof ShadowRoot) {\n return rootNode;\n }\n\n return null;\n}\n","export function isElement(value: unknown): value is Element {\n return !!value && (value as Element).nodeType === Node.ELEMENT_NODE;\n}\n","export function isEventTarget(value: unknown): value is EventTarget {\n return typeof (value as EventTarget)?.addEventListener === 'function';\n}\n","export function isNodeWithin(node: Node, root: Element): boolean {\n return root === node || root.contains(node) || (root.shadowRoot?.contains(node) ?? false);\n}\n","import { isElement, isEventTarget } from './dom';\n\nexport function assertElement(value: unknown, source: string): asserts value is Element {\n if (!isElement(value)) {\n throw new Error(\n `[${source}] Expected a DOM Element, ElementRef but received: ${\n (value as object).constructor?.name ?? typeof value\n }. ` +\n `If you are using viewChild/contentChild, make sure to specify \"{ read: ElementRef }\" to avoid implicit directive references.`\n );\n }\n}\n\nexport function assertEventTarget(value: unknown, source: string): asserts value is EventTarget {\n if (!isEventTarget(value)) {\n throw new Error(\n `[${source}] Expected an EventTarget, ElementRef but received: ${\n (value as object).constructor?.name ?? typeof value\n }. ` +\n `If you are using viewChild/contentChild, specify \"{ read: ElementRef }\" to avoid implicit directive references.`\n );\n }\n}\n","import {\n assertInInjectionContext,\n DestroyRef,\n inject,\n type Injector,\n INJECTOR,\n isSignal,\n runInInjectionContext,\n type Signal,\n untracked,\n} from '@angular/core';\nimport { SIGNAL, type SignalNode } from '@angular/core/primitives/signals';\nimport { IS_BROWSER, IS_MOBILE, IS_SERVER } from '../providers';\n\nexport interface ContextRef {\n readonly injector: Injector;\n readonly isServer: boolean;\n readonly isBrowser: boolean;\n readonly isMobile: boolean;\n readonly onCleanup: (cleanupFn: () => void) => void;\n}\n\nexport interface SetupContextRef {\n runInContext<T>(fn: (context: ContextRef) => T): T;\n}\n\n/**\n * @internal\n *\n * @param injector - injector to use for context\n * @param debugFn - context owner function\n */\nexport function setupContext(\n injector?: Injector,\n debugFn?: (...args: any[]) => any\n): SetupContextRef {\n if (typeof ngDevMode !== 'undefined' && ngDevMode && !injector) {\n assertInInjectionContext(debugFn || setupContext);\n }\n\n const ctxInjector = injector || inject(INJECTOR);\n\n return {\n runInContext<T>(fn: (context: ContextRef) => T): T {\n return runInContextImpl(fn, ctxInjector, debugFn || setupContext);\n },\n };\n}\n\nfunction runInContextImpl<T>(\n fn: (context: ContextRef) => T,\n injector: Injector,\n debugFn: (...args: any[]) => any\n): T {\n const result = runInInjectionContext(injector, () => {\n const isBrowser = inject(IS_BROWSER);\n const isServer = inject(IS_SERVER);\n const isMobile = inject(IS_MOBILE);\n const destroyRef = inject(DestroyRef);\n\n const onCleanup = (cleanupFn: () => void) => {\n destroyRef.onDestroy(cleanupFn);\n };\n\n return untracked(() => fn({ injector, isBrowser, isServer, isMobile, onCleanup }));\n });\n\n if (typeof ngDevMode !== 'undefined' && ngDevMode && result != null) {\n setupDebugInfo(result, debugFn);\n }\n\n return result;\n}\n\nfunction setupDebugInfo<T>(value: T, debugFn: (...args: any[]) => any): T {\n if (isSignal(value)) {\n setDebugName(value, debugFn);\n } else if (value && typeof value === 'object') {\n for (const [postfix, maybeSignal] of Object.entries(value)) {\n if (isSignal(maybeSignal)) {\n setDebugName(maybeSignal, debugFn, postfix);\n }\n }\n }\n\n return value;\n}\n\nfunction setDebugName(\n signal: Signal<unknown>,\n debugFn: (...args: any[]) => any,\n postfix?: string\n): void {\n const node = signal[SIGNAL] as SignalNode<unknown>;\n\n if (node.debugName === undefined) {\n node.debugName = debugFn.name + (postfix ? '.' + postfix : '');\n }\n}\n","import { InjectionToken, type ProviderToken } from '@angular/core';\n\n/**\n * Creates an Angular InjectionToken with a factory function.\n * @internal\n */\nexport function createToken<T>(\n factory: () => T,\n providedIn: ProvidedIn = 'root'\n): ProviderToken<T> {\n return new InjectionToken(ngDevMode ? factory.name : '', { factory, providedIn });\n}\n\ntype ProvidedIn = NonNullable<ConstructorParameters<typeof InjectionToken>[1]>['providedIn'];\n","import { isSignal, type Signal } from '@angular/core';\nimport { SIGNAL } from '@angular/core/primitives/signals';\n\n/**\n * Determines if a signal is a query signal (viewChild, contentChild).\n * Query signals have a special internal structure with a `_dirtyCounter` property that tracks\n * when query results change.\n\n * See: https://github.com/angular/angular/blob/main/packages/core/src/render3/queries/query_reactive.ts#L43\n * @internal\n */\nexport function isQuerySignal(val: unknown): val is Signal<unknown> {\n if (!isSignal(val)) {\n return false;\n }\n\n const node = val[SIGNAL] as object;\n return '_dirtyCounter' in node;\n}\n","export function isPlainObject(value: unknown): value is Record<PropertyKey, unknown> {\n if (typeof value !== 'object' || value === null) {\n return false;\n }\n\n const prototype = Object.getPrototypeOf(value);\n return prototype === null || prototype === Object.prototype;\n}\n","import type { Signal } from '@angular/core';\nimport {\n SIGNAL,\n SIGNAL_NODE,\n type SignalGetter,\n type SignalNode,\n} from '@angular/core/primitives/signals';\n\n/***\n * Creates a lightweight, readonly signal.\n * This is primarily used to provide fallback values for states that cannot be\n * computed in the current environment. For example:\n * - During SSR where browser-only APIs are unavailable\n * - In environments that lack support for specific APIs\n * @internal\n */\nexport function constSignal<T>(value: T): Signal<T> {\n const node: SignalNode<T> = Object.create(SIGNAL_NODE);\n node.value = value;\n\n const getter = (() => node.value) as SignalGetter<T>;\n (getter as any)[SIGNAL] = node;\n\n if (typeof ngDevMode !== 'undefined' && ngDevMode) {\n const debugName = node.debugName ? ' (' + node.debugName + ')' : '';\n getter.toString = () => `[Signal${debugName}: ${String(node.value)}]`;\n }\n\n return getter;\n}\n","import { type Signal, untracked, type WritableSignal } from '@angular/core';\nimport { SIGNAL, type SignalNode } from '@angular/core/primitives/signals';\n\n/**\n * @internal\n */\nexport interface SignalProxyHandler<T> {\n get?(source: Signal<T>): T;\n set?(value: T, source: WritableSignal<T>): void;\n}\n\n/**\n * Creates a proxy wrapper around a {@link Signal}\n * @internal\n */\nexport function proxySignal<T>(\n source: Signal<T>,\n handler: Omit<SignalProxyHandler<T>, 'set'>\n): Signal<T>;\n\n/**\n * Creates a proxy wrapper around a {@link WritableSignal}\n * @internal\n */\nexport function proxySignal<T>(\n source: WritableSignal<T>,\n handler: SignalProxyHandler<T>\n): WritableSignal<T>;\n\nexport function proxySignal<T>(\n source: Signal<T> | WritableSignal<T>,\n handler: SignalProxyHandler<T>\n): Signal<T> | WritableSignal<T> {\n const node = source[SIGNAL] as SignalNode<T>;\n const isWritable = 'set' in source && typeof source.set === 'function';\n\n const proxy = (handler.get ? () => handler.get!(source) : () => source()) as Signal<T>;\n\n proxy[SIGNAL] = node;\n\n // @TODO: consider (original toString internally reads from the original getter, bypassing the proxy)\n proxy.toString = source.toString;\n\n if (isWritable) {\n const set = handler.set\n ? (value: T) => untracked(() => handler.set!(value, source))\n : (value: T) => source.set(value);\n\n const update = (updater: (current: T) => T) => set(updater(node.value));\n\n (proxy as WritableSignal<T>).set = set;\n (proxy as WritableSignal<T>).update = update;\n (proxy as WritableSignal<T>).asReadonly = () => {\n const getter = source.asReadonly();\n return proxySignal(getter, { get: handler.get?.bind(handler) });\n };\n }\n\n return proxy;\n}\n","import { ElementRef } from '@angular/core';\n\nexport function unrefElement<T>(value: T | ElementRef<T>): T {\n return value instanceof ElementRef ? value.nativeElement : value;\n}\n","/**\n * Checks whether a file matches the given accept patterns.\n * Follows the native HTML\n * [`accept`](https://developer.mozilla.org/en-US/docs/Web/HTML/Reference/Attributes/accept) attribute format:\n * MIME types (`'image/png'`), wildcards (`'image/*'`), and file extensions (`'.pdf'`).\n *\n * @param file - File to check\n * @param accept - Comma-separated string of accepted patterns (e.g. `'image/*, .pdf'`)\n * @internal\n */\nexport function isAcceptedFile(file: File, accept: string): boolean {\n if (accept === '*') {\n return true;\n }\n\n const patterns = accept.split(',').map(s => s.trim());\n\n if (patterns.length === 0) {\n return true;\n }\n\n return patterns.some(pattern => {\n if (pattern.startsWith('.')) {\n return file.name.toLowerCase().endsWith(pattern.toLowerCase());\n }\n\n if (pattern.endsWith('/*')) {\n return file.type.startsWith(pattern.slice(0, -1));\n }\n\n return file.type === pattern;\n });\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":[],"mappings":"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"}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { afterRenderEffect } from '@angular/core';
|
|
2
|
-
import { setupContext, NOOP_EFFECT_REF,
|
|
2
|
+
import { setupContext, NOOP_EFFECT_REF, assertElement } from '@signality/core/internal';
|
|
3
|
+
import { toElement, toValue } from '@signality/core/utilities';
|
|
3
4
|
|
|
4
5
|
/**
|
|
5
6
|
* Low-level utility for observing element intersection with viewport using the [Intersection Observer API](https://developer.mozilla.org/en-US/docs/Web/API/Intersection_Observer_API).
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"signality-core-observers-intersection-observer.mjs","sources":["../../../projects/core/observers/intersection-observer/index.ts","../../../projects/core/observers/intersection-observer/signality-core-observers-intersection-observer.ts"],"sourcesContent":["import {\n afterRenderEffect,\n type CreateEffectOptions,\n type EffectCleanupRegisterFn,\n} from '@angular/core';\nimport {
|
|
1
|
+
{"version":3,"file":"signality-core-observers-intersection-observer.mjs","sources":["../../../projects/core/observers/intersection-observer/index.ts","../../../projects/core/observers/intersection-observer/signality-core-observers-intersection-observer.ts"],"sourcesContent":["import {\n afterRenderEffect,\n type CreateEffectOptions,\n type EffectCleanupRegisterFn,\n} from '@angular/core';\nimport { assertElement, NOOP_EFFECT_REF, setupContext } from '@signality/core/internal';\nimport { toElement, toValue } from '@signality/core/utilities';\nimport type { MaybeElementSignal, MaybeSignal } from '@signality/core/types';\n\nexport interface IntersectionObserverInitOptions\n extends Omit<CreateEffectOptions, 'allowSignalWrites'> {\n /**\n * Scrollable ancestor used as the intersection viewport.\n * `null` or `undefined` defaults to the browser viewport.\n *\n * @see [IntersectionObserver: root on MDN](https://developer.mozilla.org/en-US/docs/Web/API/IntersectionObserver/root)\n */\n readonly root?: MaybeElementSignal<Element> | Document | null;\n\n /**\n * CSS margin applied around the root before computing intersections.\n * Accepts values in the same format as the CSS `margin` property (e.g. `'10px 0px'`).\n *\n * @see [IntersectionObserver: rootMargin on MDN](https://developer.mozilla.org/en-US/docs/Web/API/IntersectionObserver/rootMargin)\n */\n readonly rootMargin?: MaybeSignal<string>;\n\n /**\n * Fraction(s) of the target element that must be visible to trigger the callback.\n * A single number or an array of thresholds, each between `0` and `1`.\n *\n * @see [IntersectionObserver: thresholds on MDN](https://developer.mozilla.org/en-US/docs/Web/API/IntersectionObserver/thresholds)\n */\n readonly threshold?: MaybeSignal<number | number[]>;\n}\n\nexport interface IntersectionObserverRef {\n /**\n * Stop observing all targets and disconnect the underlying `IntersectionObserver`.\n */\n readonly destroy: () => void;\n}\n\n/**\n * Low-level utility for observing element intersection with viewport using the [Intersection Observer API](https://developer.mozilla.org/en-US/docs/Web/API/Intersection_Observer_API).\n * Provides fine-grained control over the observation lifecycle.\n *\n * @param target - Element(s) to observe\n * @param callback - Callback function called when intersection changes\n * @param options - Optional configuration (see {@link IntersectionObserverInitOptions})\n * @returns An IntersectionObserverRef with a `destroy()` method to stop observing the element(s)\n *\n * @example\n * ```typescript\n * @Component({\n * template: `\n * <div #section>Section content</div>\n * @if (isVisible()) {\n * <p>Section is visible!</p>\n * }\n * `\n * })\n * export class IntersectionDemo {\n * readonly section = viewChild<ElementRef>('section');\n * readonly isVisible = signal(false);\n *\n * constructor() {\n * intersectionObserver(this.section, entries => {\n * this.isVisible.set(entries[0].isIntersecting);\n * }, { threshold: 0.5 });\n * }\n * }\n * ```\n */\nexport function intersectionObserver(\n target: MaybeElementSignal<Element> | MaybeElementSignal<Element>[],\n callback: (entries: readonly IntersectionObserverEntry[], observer: IntersectionObserver) => void,\n options?: IntersectionObserverInitOptions\n): IntersectionObserverRef {\n const { runInContext } = setupContext(options?.injector, intersectionObserver);\n\n return runInContext(({ isServer }) => {\n if (isServer) {\n return NOOP_EFFECT_REF;\n }\n\n const targets = Array.isArray(target) ? target : [target];\n\n const setupObserver = (onCleanup: EffectCleanupRegisterFn) => {\n const els = targets.map(toElement).filter(Boolean);\n\n if (!els.length) {\n return;\n }\n\n const root = options?.root\n ? options.root instanceof Document\n ? options.root\n : toElement(options.root)\n : null;\n const rootMargin = toValue(options?.rootMargin);\n const threshold = toValue(options?.threshold);\n\n const observer = new IntersectionObserver(callback, { root, rootMargin, threshold });\n\n for (const el of els) {\n ngDevMode && assertElement(el, 'intersectionObserver');\n observer.observe(el!);\n }\n\n onCleanup(observer.disconnect.bind(observer));\n };\n\n const effectRef = afterRenderEffect({ read: setupObserver }, options);\n\n return { destroy: () => effectRef.destroy() };\n });\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":[],"mappings":";;;;AA2CA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AA8BG;SACa,oBAAoB,CAClC,MAAmE,EACnE,QAAiG,EACjG,OAAyC,EAAA;AAEzC,IAAA,MAAM,EAAE,YAAY,EAAE,GAAG,YAAY,CAAC,OAAO,EAAE,QAAQ,EAAE,oBAAoB,CAAC;AAE9E,IAAA,OAAO,YAAY,CAAC,CAAC,EAAE,QAAQ,EAAE,KAAI;QACnC,IAAI,QAAQ,EAAE;AACZ,YAAA,OAAO,eAAe;QACxB;AAEA,QAAA,MAAM,OAAO,GAAG,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC,GAAG,MAAM,GAAG,CAAC,MAAM,CAAC;AAEzD,QAAA,MAAM,aAAa,GAAG,CAAC,SAAkC,KAAI;AAC3D,YAAA,MAAM,GAAG,GAAG,OAAO,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC;AAElD,YAAA,IAAI,CAAC,GAAG,CAAC,MAAM,EAAE;gBACf;YACF;AAEA,YAAA,MAAM,IAAI,GAAG,OAAO,EAAE;AACpB,kBAAE,OAAO,CAAC,IAAI,YAAY;sBACtB,OAAO,CAAC;AACV,sBAAE,SAAS,CAAC,OAAO,CAAC,IAAI;kBACxB,IAAI;YACR,MAAM,UAAU,GAAG,OAAO,CAAC,OAAO,EAAE,UAAU,CAAC;YAC/C,MAAM,SAAS,GAAG,OAAO,CAAC,OAAO,EAAE,SAAS,CAAC;AAE7C,YAAA,MAAM,QAAQ,GAAG,IAAI,oBAAoB,CAAC,QAAQ,EAAE,EAAE,IAAI,EAAE,UAAU,EAAE,SAAS,EAAE,CAAC;AAEpF,YAAA,KAAK,MAAM,EAAE,IAAI,GAAG,EAAE;AACpB,gBAAA,SAAS,IAAI,aAAa,CAAC,EAAE,EAAE,sBAAsB,CAAC;AACtD,gBAAA,QAAQ,CAAC,OAAO,CAAC,EAAG,CAAC;YACvB;YAEA,SAAS,CAAC,QAAQ,CAAC,UAAU,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;AAC/C,QAAA,CAAC;AAED,QAAA,MAAM,SAAS,GAAG,iBAAiB,CAAC,EAAE,IAAI,EAAE,aAAa,EAAE,EAAE,OAAO,CAAC;QAErE,OAAO,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC,OAAO,EAAE,EAAE;AAC/C,IAAA,CAAC,CAAC;AACJ;;ACrHA;;AAEG;;;;"}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { afterRenderEffect } from '@angular/core';
|
|
2
|
-
import { setupContext, NOOP_EFFECT_REF,
|
|
2
|
+
import { setupContext, NOOP_EFFECT_REF, assertElement } from '@signality/core/internal';
|
|
3
|
+
import { toElement, toValue } from '@signality/core/utilities';
|
|
3
4
|
|
|
4
5
|
/**
|
|
5
6
|
* Low-level utility for observing DOM tree changes using the [MutationObserver API](https://developer.mozilla.org/en-US/docs/Web/API/MutationObserver).
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"signality-core-observers-mutation-observer.mjs","sources":["../../../projects/core/observers/mutation-observer/index.ts","../../../projects/core/observers/mutation-observer/signality-core-observers-mutation-observer.ts"],"sourcesContent":["import {\n afterRenderEffect,\n type CreateEffectOptions,\n type EffectCleanupRegisterFn,\n} from '@angular/core';\nimport {
|
|
1
|
+
{"version":3,"file":"signality-core-observers-mutation-observer.mjs","sources":["../../../projects/core/observers/mutation-observer/index.ts","../../../projects/core/observers/mutation-observer/signality-core-observers-mutation-observer.ts"],"sourcesContent":["import {\n afterRenderEffect,\n type CreateEffectOptions,\n type EffectCleanupRegisterFn,\n} from '@angular/core';\nimport { assertElement, NOOP_EFFECT_REF, setupContext } from '@signality/core/internal';\nimport { toElement, toValue } from '@signality/core/utilities';\nimport type { MaybeElementSignal, MaybeSignal } from '@signality/core/types';\n\nexport interface MutationObserverInitOptions\n extends Omit<CreateEffectOptions, 'allowSignalWrites'> {\n /**\n * Whether to observe additions and removals of child nodes.\n *\n * @see [MutationObserver.observe(): childList on MDN](https://developer.mozilla.org/en-US/docs/Web/API/MutationObserver/observe#childlist)\n */\n readonly childList?: MaybeSignal<boolean>;\n\n /**\n * Whether to observe attribute changes on the target element.\n * Use `attributeFilter` to limit which attributes are observed.\n *\n * @see [MutationObserver.observe(): attributes on MDN](https://developer.mozilla.org/en-US/docs/Web/API/MutationObserver/observe#attributes)\n */\n readonly attributes?: MaybeSignal<boolean>;\n\n /**\n * Whether to observe changes to the text content (`CharacterData`) of the target.\n *\n * @see [MutationObserver.observe(): characterData on MDN](https://developer.mozilla.org/en-US/docs/Web/API/MutationObserver/observe#characterdata)\n */\n readonly characterData?: MaybeSignal<boolean>;\n\n /**\n * Whether to extend observation to the entire subtree of the target element.\n *\n * @see [MutationObserver.observe(): subtree on MDN](https://developer.mozilla.org/en-US/docs/Web/API/MutationObserver/observe#subtree)\n */\n readonly subtree?: MaybeSignal<boolean>;\n\n /**\n * Whether to record the previous attribute value in each `MutationRecord`.\n * Implicitly sets `attributes` to `true` if not already set.\n *\n * @see [MutationObserver.observe(): attributeOldValue on MDN](https://developer.mozilla.org/en-US/docs/Web/API/MutationObserver/observe#attributeoldvalue)\n */\n readonly attributeOldValue?: MaybeSignal<boolean>;\n\n /**\n * Whether to record the previous character data value in each `MutationRecord`.\n * Implicitly sets `characterData` to `true` if not already set.\n *\n * @see [MutationObserver.observe(): characterDataOldValue on MDN](https://developer.mozilla.org/en-US/docs/Web/API/MutationObserver/observe#characterdataoldvalue)\n */\n readonly characterDataOldValue?: MaybeSignal<boolean>;\n\n /**\n * Array of attribute local names to observe. Only mutations to listed attributes are reported.\n * Implicitly sets `attributes` to `true` if not already set.\n *\n * @see [MutationObserver.observe(): attributeFilter on MDN](https://developer.mozilla.org/en-US/docs/Web/API/MutationObserver/observe#attributefilter)\n */\n readonly attributeFilter?: MaybeSignal<string[]>;\n}\n\nexport interface MutationObserverRef {\n /**\n * Stop observing all targets and disconnect the underlying `MutationObserver`.\n */\n readonly destroy: () => void;\n}\n\n/**\n * Low-level utility for observing DOM tree changes using the [MutationObserver API](https://developer.mozilla.org/en-US/docs/Web/API/MutationObserver).\n * Provides fine-grained control over the observation lifecycle.\n *\n * @param target - Element(s) to observe\n * @param callback - Callback function called when DOM mutations occur\n * @param options - Optional configuration (see {@link MutationObserverInitOptions})\n * @returns MutationObserverRef with a `destroy()` method to stop observing the element(s)\n *\n * @example\n * ```typescript\n * @Component({\n * template: `\n * <div #container>\n * <p>Children: {{ childCount() }}</p>\n * </div>\n * `\n * })\n * export class MutationComponent {\n * readonly container = viewChild<ElementRef>('container');\n * readonly childCount = signal(0);\n *\n * constructor() {\n * mutationObserver(this.container, mutations => {\n * this.childCount.set(mutations[0].target.childNodes.length);\n * }, { childList: true });\n * }\n * }\n * ```\n */\nexport function mutationObserver(\n target: MaybeElementSignal<Element> | MaybeElementSignal<Element>[],\n callback: (mutations: readonly MutationRecord[], observer: MutationObserver) => void,\n options: MutationObserverInitOptions\n): MutationObserverRef {\n const { runInContext } = setupContext(options.injector, mutationObserver);\n\n return runInContext(({ isServer }) => {\n if (isServer) {\n return NOOP_EFFECT_REF;\n }\n\n const targets = Array.isArray(target) ? target : [target];\n\n const setupObserver = (onCleanup: EffectCleanupRegisterFn) => {\n const els = targets.map(toElement).filter(Boolean);\n\n if (!els.length) {\n return;\n }\n\n const childList = toValue(options.childList);\n const attributes = toValue(options.attributes);\n const characterData = toValue(options.characterData);\n const subtree = toValue(options.subtree);\n const attributeOldValue = toValue(options.attributeOldValue);\n const characterDataOldValue = toValue(options.characterDataOldValue);\n const attributeFilter = toValue(options.attributeFilter);\n\n const observer = new MutationObserver(callback);\n\n for (const el of els) {\n ngDevMode && assertElement(el, 'mutationObserver');\n\n observer.observe(el!, {\n childList,\n attributes,\n characterData,\n subtree,\n attributeOldValue,\n characterDataOldValue,\n attributeFilter,\n });\n }\n\n onCleanup(observer.disconnect.bind(observer));\n };\n\n const effectRef = afterRenderEffect({ read: setupObserver }, options);\n\n return { destroy: () => effectRef.destroy() };\n });\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":[],"mappings":";;;;AAwEA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AA6BG;SACa,gBAAgB,CAC9B,MAAmE,EACnE,QAAoF,EACpF,OAAoC,EAAA;AAEpC,IAAA,MAAM,EAAE,YAAY,EAAE,GAAG,YAAY,CAAC,OAAO,CAAC,QAAQ,EAAE,gBAAgB,CAAC;AAEzE,IAAA,OAAO,YAAY,CAAC,CAAC,EAAE,QAAQ,EAAE,KAAI;QACnC,IAAI,QAAQ,EAAE;AACZ,YAAA,OAAO,eAAe;QACxB;AAEA,QAAA,MAAM,OAAO,GAAG,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC,GAAG,MAAM,GAAG,CAAC,MAAM,CAAC;AAEzD,QAAA,MAAM,aAAa,GAAG,CAAC,SAAkC,KAAI;AAC3D,YAAA,MAAM,GAAG,GAAG,OAAO,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC;AAElD,YAAA,IAAI,CAAC,GAAG,CAAC,MAAM,EAAE;gBACf;YACF;YAEA,MAAM,SAAS,GAAG,OAAO,CAAC,OAAO,CAAC,SAAS,CAAC;YAC5C,MAAM,UAAU,GAAG,OAAO,CAAC,OAAO,CAAC,UAAU,CAAC;YAC9C,MAAM,aAAa,GAAG,OAAO,CAAC,OAAO,CAAC,aAAa,CAAC;YACpD,MAAM,OAAO,GAAG,OAAO,CAAC,OAAO,CAAC,OAAO,CAAC;YACxC,MAAM,iBAAiB,GAAG,OAAO,CAAC,OAAO,CAAC,iBAAiB,CAAC;YAC5D,MAAM,qBAAqB,GAAG,OAAO,CAAC,OAAO,CAAC,qBAAqB,CAAC;YACpE,MAAM,eAAe,GAAG,OAAO,CAAC,OAAO,CAAC,eAAe,CAAC;AAExD,YAAA,MAAM,QAAQ,GAAG,IAAI,gBAAgB,CAAC,QAAQ,CAAC;AAE/C,YAAA,KAAK,MAAM,EAAE,IAAI,GAAG,EAAE;AACpB,gBAAA,SAAS,IAAI,aAAa,CAAC,EAAE,EAAE,kBAAkB,CAAC;AAElD,gBAAA,QAAQ,CAAC,OAAO,CAAC,EAAG,EAAE;oBACpB,SAAS;oBACT,UAAU;oBACV,aAAa;oBACb,OAAO;oBACP,iBAAiB;oBACjB,qBAAqB;oBACrB,eAAe;AAChB,iBAAA,CAAC;YACJ;YAEA,SAAS,CAAC,QAAQ,CAAC,UAAU,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;AAC/C,QAAA,CAAC;AAED,QAAA,MAAM,SAAS,GAAG,iBAAiB,CAAC,EAAE,IAAI,EAAE,aAAa,EAAE,EAAE,OAAO,CAAC;QAErE,OAAO,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC,OAAO,EAAE,EAAE;AAC/C,IAAA,CAAC,CAAC;AACJ;;AC1JA;;AAEG;;;;"}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { afterRenderEffect } from '@angular/core';
|
|
2
|
-
import { setupContext, NOOP_EFFECT_REF,
|
|
2
|
+
import { setupContext, NOOP_EFFECT_REF, assertElement } from '@signality/core/internal';
|
|
3
|
+
import { toElement, toValue } from '@signality/core/utilities';
|
|
3
4
|
|
|
4
5
|
/**
|
|
5
6
|
* Low-level utility for observing element size changes using the [ResizeObserver API](https://developer.mozilla.org/en-US/docs/Web/API/ResizeObserver).
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"signality-core-observers-resize-observer.mjs","sources":["../../../projects/core/observers/resize-observer/index.ts","../../../projects/core/observers/resize-observer/signality-core-observers-resize-observer.ts"],"sourcesContent":["import {\n afterRenderEffect,\n type CreateEffectOptions,\n type EffectCleanupRegisterFn,\n} from '@angular/core';\nimport {
|
|
1
|
+
{"version":3,"file":"signality-core-observers-resize-observer.mjs","sources":["../../../projects/core/observers/resize-observer/index.ts","../../../projects/core/observers/resize-observer/signality-core-observers-resize-observer.ts"],"sourcesContent":["import {\n afterRenderEffect,\n type CreateEffectOptions,\n type EffectCleanupRegisterFn,\n} from '@angular/core';\nimport { assertElement, NOOP_EFFECT_REF, setupContext } from '@signality/core/internal';\nimport { toElement, toValue } from '@signality/core/utilities';\nimport type { MaybeElementSignal, MaybeSignal } from '@signality/core/types';\n\nexport interface ResizeObserverInitOptions extends Omit<CreateEffectOptions, 'allowSignalWrites'> {\n /**\n * Box model to measure when reporting size changes.\n *\n * - `'content-box'` — size of the content area, excluding padding and border (default).\n * - `'border-box'` — size including padding and border.\n * - `'device-pixel-content-box'` — content-box size in physical device pixels.\n *\n * @see [ResizeObserver.observe(): box on MDN](https://developer.mozilla.org/en-US/docs/Web/API/ResizeObserver/observe#box)\n */\n readonly box?: MaybeSignal<ResizeObserverBoxOptions>;\n}\n\nexport interface ResizeObserverRef {\n /**\n * Stop observing all targets and disconnect the underlying `ResizeObserver`.\n */\n readonly destroy: () => void;\n}\n\n/**\n * Low-level utility for observing element size changes using the [ResizeObserver API](https://developer.mozilla.org/en-US/docs/Web/API/ResizeObserver).\n * Provides fine-grained control over the observation lifecycle.\n *\n * @param target - Element(s) to observe\n * @param callback - Callback function called when element size changes\n * @param options - Optional configuration (see {@link ResizeObserverInitOptions})\n * @returns ResizeObserverRef with a `destroy()` method to stop observing the element(s)\n *\n * @example\n * ```typescript\n * @Component({\n * template: `\n * <div #resizable>\n * Size: {{ size().width }} × {{ size().height }}px\n * </div>\n * `\n * })\n * export class ResizeComponent {\n * readonly resizable = viewChild<ElementRef>('resizable');\n * readonly size = signal({ width: 0, height: 0 });\n *\n * constructor() {\n * resizeObserver(this.resizable, entries => {\n * const { width, height } = entries[0].contentRect;\n * this.size.set({ width, height });\n * });\n * }\n * }\n * ```\n */\nexport function resizeObserver(\n target: MaybeElementSignal<Element> | MaybeElementSignal<Element>[],\n callback: (entries: readonly ResizeObserverEntry[]) => void,\n options?: ResizeObserverInitOptions\n): ResizeObserverRef {\n const { runInContext } = setupContext(options?.injector, resizeObserver);\n\n return runInContext(({ isServer, onCleanup }) => {\n if (isServer) {\n return NOOP_EFFECT_REF;\n }\n\n const targets = Array.isArray(target) ? target : [target];\n\n let observer: ResizeObserver | null = null;\n\n const setupObserver = (onCleanup: EffectCleanupRegisterFn) => {\n const els = targets.map(toElement).filter(Boolean);\n\n if (!els.length) {\n return;\n }\n\n const box = toValue(options?.box);\n\n observer ??= new ResizeObserver(callback);\n\n for (const el of els) {\n ngDevMode && assertElement(el, 'resizeObserver');\n observer.observe(el!, { box });\n }\n\n onCleanup(() => {\n els.forEach(el => observer?.unobserve(el!));\n });\n };\n\n const destroy = () => observer?.disconnect();\n\n onCleanup(destroy);\n\n afterRenderEffect({ read: setupObserver }, options);\n\n return { destroy };\n });\n}\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './index';\n"],"names":[],"mappings":";;;;AA6BA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AA8BG;SACa,cAAc,CAC5B,MAAmE,EACnE,QAA2D,EAC3D,OAAmC,EAAA;AAEnC,IAAA,MAAM,EAAE,YAAY,EAAE,GAAG,YAAY,CAAC,OAAO,EAAE,QAAQ,EAAE,cAAc,CAAC;IAExE,OAAO,YAAY,CAAC,CAAC,EAAE,QAAQ,EAAE,SAAS,EAAE,KAAI;QAC9C,IAAI,QAAQ,EAAE;AACZ,YAAA,OAAO,eAAe;QACxB;AAEA,QAAA,MAAM,OAAO,GAAG,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC,GAAG,MAAM,GAAG,CAAC,MAAM,CAAC;QAEzD,IAAI,QAAQ,GAA0B,IAAI;AAE1C,QAAA,MAAM,aAAa,GAAG,CAAC,SAAkC,KAAI;AAC3D,YAAA,MAAM,GAAG,GAAG,OAAO,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC;AAElD,YAAA,IAAI,CAAC,GAAG,CAAC,MAAM,EAAE;gBACf;YACF;YAEA,MAAM,GAAG,GAAG,OAAO,CAAC,OAAO,EAAE,GAAG,CAAC;AAEjC,YAAA,QAAQ,KAAK,IAAI,cAAc,CAAC,QAAQ,CAAC;AAEzC,YAAA,KAAK,MAAM,EAAE,IAAI,GAAG,EAAE;AACpB,gBAAA,SAAS,IAAI,aAAa,CAAC,EAAE,EAAE,gBAAgB,CAAC;gBAChD,QAAQ,CAAC,OAAO,CAAC,EAAG,EAAE,EAAE,GAAG,EAAE,CAAC;YAChC;YAEA,SAAS,CAAC,MAAK;AACb,gBAAA,GAAG,CAAC,OAAO,CAAC,EAAE,IAAI,QAAQ,EAAE,SAAS,CAAC,EAAG,CAAC,CAAC;AAC7C,YAAA,CAAC,CAAC;AACJ,QAAA,CAAC;QAED,MAAM,OAAO,GAAG,MAAM,QAAQ,EAAE,UAAU,EAAE;QAE5C,SAAS,CAAC,OAAO,CAAC;QAElB,iBAAiB,CAAC,EAAE,IAAI,EAAE,aAAa,EAAE,EAAE,OAAO,CAAC;QAEnD,OAAO,EAAE,OAAO,EAAE;AACpB,IAAA,CAAC,CAAC;AACJ;;ACzGA;;AAEG;;;;"}
|