@kayelaa/canvas 0.2.0 → 0.2.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,4 +1,4 @@
1
- import { a as LeaGameII, b as LeaTimeout, c as LeaRendererII, d as LeaEventEmitter, V as Vector2, e as LeaTickerII, R as RectLeaEntity, f as LeaSceneII } from './lea-k7IGP_-W.js';
1
+ import { a as LeaGameII, b as LeaTimeout, c as LeaRendererII, d as LeaEventEmitter, V as Vector2, e as LeaTickerII, R as RectLeaEntity, f as LeaSceneII } from './lea-B1DIEiLR.js';
2
2
 
3
3
  /**
4
4
  * Base props that every Kayla functional component can receive.
@@ -352,7 +352,7 @@ declare namespace KaylaInternals {
352
352
  usePaint(onPaint: KaylaFiber["onPaint"][number]): void;
353
353
  useEntity(): KaylaElementRef;
354
354
  useSelf<T>(init: () => T): T;
355
- useInitialization(init: KaylaFiber["onInit"]): void;
355
+ useInitialization(init: KaylaFiber["onInits"][number]): void;
356
356
  useRect(): KaylaRect;
357
357
  useFiber(): UnsafeKaylaFiber;
358
358
  useFiberControl(): KaylaFiberControl;
@@ -367,6 +367,7 @@ declare namespace KaylaInternals {
367
367
  useRef(initialValue: typeof selfSym): KaylaElementRef;
368
368
  useRef<T>(initialValue: T | null): KaylaRef<T>;
369
369
  useEffect(onEffect: KaylaFiber["onEffect"][number]): void;
370
+ useViewportEffect(onEffect: KaylaFiber["onViewportEffect"][number]): void;
370
371
  useExports<T extends FC<any, any>>(_fc: T, onExport: KaylaFiber<PropOfFC<T>, ExportsOfFC<T>>["onExport"]): void;
371
372
  useGlobalClick(onClick: KaylaFiber["onGlobalClick"][number]): void;
372
373
  useClick(onClick: KaylaFiber["onGlobalClick"][number]): void;
@@ -575,9 +576,14 @@ declare namespace KaylaInternals {
575
576
  };
576
577
  get childrenCount(): number;
577
578
  maxSafeChildren: number;
579
+ dynamicChildren: KaylaElement<any>[];
578
580
  constructor(globalKayla: GlobalKayla, scene: KaylaScene, element: KaylaElement<Props>);
579
581
  getChildrenEntities(): KaylaRectEntity[];
580
582
  pointerHook(pos: Vector2, type: KaylaClickType): void;
583
+ resizeHook({ width, height }: {
584
+ width: number;
585
+ height: number;
586
+ }): void;
581
587
  bindEvents(): void;
582
588
  unbindEvents(): void;
583
589
  get key(): string;
@@ -587,9 +593,10 @@ declare namespace KaylaInternals {
587
593
  entity?: KaylaRectEntity;
588
594
  onExport: () => KaylaExports<Exports>;
589
595
  onEffect: Array<() => (() => void) | void>;
596
+ onViewportEffect: Array<(renderer: KaylaRenderer, width: number, height: number) => void>;
590
597
  onGlobalClick: Array<(pos: Vector2, type: KaylaClickType) => void | void>;
591
- onInit: () => (() => void) | void;
592
- onUnInit: () => (() => void) | void;
598
+ onInits: Array<() => (() => void) | void>;
599
+ onUnInits: Array<() => (() => void) | void>;
593
600
  onUnEffect: Array<() => void>;
594
601
  onEffectDeps?: KaylaState<any>[] | undefined;
595
602
  onPaint: Array<(ctx: CanvasRenderingContext2D, event: KaylaEvent) => void>;
@@ -601,6 +608,8 @@ declare namespace KaylaInternals {
601
608
  useDrawCallIndex: number;
602
609
  useStepCallIndex: number;
603
610
  useRefCallIndex: number;
611
+ useInitCallIndex: number;
612
+ useViewCallIndex: number;
604
613
  lastStateDeps: Array<{
605
614
  stateRef: KaylaState<any>;
606
615
  stamp: number;
@@ -618,6 +627,7 @@ declare namespace KaylaInternals {
618
627
  shouldFullRefresh(): boolean;
619
628
  captureDepStamps(): void;
620
629
  refresh(): void;
630
+ updateChildren(fcChildren: KaylaFiber<Props>["children"], isRefreshCall: boolean): void;
621
631
  lastChildren: KaylaFiber<any>[];
622
632
  isFirstUse: boolean;
623
633
  use(): void;
@@ -678,6 +688,11 @@ declare namespace KaylaInternals {
678
688
  class KaylaInternalRect {
679
689
  #private;
680
690
  constructor(fiber: KaylaFiber<any, any>);
691
+ /**
692
+ * Default behavior color
693
+ */
694
+ get color(): string;
695
+ set color(s: string);
681
696
  getRaw(): KaylaRect.RawKaylaRect;
682
697
  private get entity();
683
698
  /**
@@ -1004,6 +1019,23 @@ declare const useShouldRefresh: (deps: KaylaState<any>[]) => void;
1004
1019
  * @see {@link useInitialization} — for one-shot setup that survives refreshes
1005
1020
  */
1006
1021
  declare const useEffect: (onEffect: KaylaInternals.KaylaFiber["onEffect"][number]) => void;
1022
+ /**
1023
+ * Registers a side-effect that runs **whenever the renderer's viewport size changes**
1024
+ * (world units).
1025
+ *
1026
+ * The callback receives current viewport dimensions.
1027
+ *
1028
+ * Multiple calls stack — all callbacks run in declaration order.
1029
+ *
1030
+ * **This hook MUST be called at the top level of a component function.**
1031
+ *
1032
+ * @param callback - Receives renderer, width, and height
1033
+ * @example
1034
+ * useViewportEffect((renderer, width, height) => {
1035
+ * rect.x = renderer.centerX;
1036
+ * });
1037
+ */
1038
+ declare const useViewportEffect: (onEffect: KaylaInternals.KaylaFiber["onViewportEffect"][number]) => void;
1007
1039
  /**
1008
1040
  * Registers a callback that runs on **every click anywhere** in any attached renderer.
1009
1041
  *
@@ -1056,6 +1088,8 @@ declare const useClick: (onClick: KaylaInternals.KaylaFiber["onGlobalClick"][num
1056
1088
  *
1057
1089
  * If the callback returns a function, it is called **only on final entity destruction**.
1058
1090
  *
1091
+ * Multiple `useInitialization` calls **stack** — all run in declaration order.
1092
+ *
1059
1093
  * @param init One-time setup function — may return cleanup
1060
1094
  *
1061
1095
  * @example
@@ -1064,7 +1098,7 @@ declare const useClick: (onClick: KaylaInternals.KaylaFiber["onGlobalClick"][num
1064
1098
  * return () => physicsEngine.destroyBody(body); // cleanup only on unmount
1065
1099
  * });
1066
1100
  */
1067
- declare const useInitialization: (init: KaylaInternals.KaylaFiber["onInit"]) => void;
1101
+ declare const useInitialization: (init: KaylaInternals.KaylaFiber["onInits"][number]) => void;
1068
1102
  /**
1069
1103
  * Returns a convenient, mutable facade for the current entity's rectangle properties.
1070
1104
  *
@@ -1651,8 +1685,9 @@ declare const Kayla_useSelf: typeof useSelf;
1651
1685
  declare const Kayla_useShouldRefresh: typeof useShouldRefresh;
1652
1686
  declare const Kayla_useState: typeof useState;
1653
1687
  declare const Kayla_useTick: typeof useTick;
1688
+ declare const Kayla_useViewportEffect: typeof useViewportEffect;
1654
1689
  declare namespace Kayla {
1655
- export { type Kayla_ExportsOfFC as ExportsOfFC, type Kayla_FC as FC, type Kayla_FCExports as FCExports, type Kayla_FCProps as FCProps, Kayla_JSX as JSX, type Kayla_KaylaClickType as KaylaClickType, Kayla_KaylaContext as KaylaContext, type Kayla_KaylaCustomHookConfig as KaylaCustomHookConfig, type Kayla_KaylaElement as KaylaElement, type Kayla_KaylaElementRef as KaylaElementRef, type Kayla_KaylaExportables as KaylaExportables, type Kayla_KaylaExports as KaylaExports, type Kayla_KaylaFiberControl as KaylaFiberControl, Kayla_KaylaFragment as KaylaFragment, type Kayla_KaylaGame as KaylaGame, Kayla_KaylaInternals as KaylaInternals, Kayla_KaylaRect as KaylaRect, type Kayla_KaylaRef as KaylaRef, type Kayla_KaylaRenderer as KaylaRenderer, type Kayla_KaylaScene as KaylaScene, type Kayla_KaylaState as KaylaState, type Kayla_PropOfFC as PropOfFC, type Kayla_Reassignable as Reassignable, type Kayla_UnsafeKaylaFiber as UnsafeKaylaFiber, Kayla_createContext as createContext, Kayla_createElement as createElement, Kayla_createGame as createGame, Kayla_createReassignableObject as createReassignableObject, Kayla_createRenderer as createRenderer, Kayla_createScene as createScene, Kayla_createUseHook as createUseHook, selfSym as self, Kayla_setLogLevel as setLogLevel, Kayla_useClick as useClick, Kayla_useContext as useContext, Kayla_useCurrentGame as useCurrentGame, Kayla_useCurrentRenderer as useCurrentRenderer, Kayla_useCurrentScene as useCurrentScene, Kayla_useCurrentTicker as useCurrentTicker, Kayla_useDisposableRef as useDisposableRef, Kayla_useEffect as useEffect, Kayla_useEntity as useEntity, Kayla_useExports as useExports, Kayla_useFiber as useFiber, Kayla_useFiberControl as useFiberControl, Kayla_useGlobalClick as useGlobalClick, Kayla_useInitialization as useInitialization, Kayla_useNextStack as useNextStack, Kayla_usePaint as usePaint, Kayla_useRect as useRect, Kayla_useRef as useRef, Kayla_useSelf as useSelf, Kayla_useShouldRefresh as useShouldRefresh, Kayla_useState as useState, Kayla_useTick as useTick };
1690
+ export { type Kayla_ExportsOfFC as ExportsOfFC, type Kayla_FC as FC, type Kayla_FCExports as FCExports, type Kayla_FCProps as FCProps, Kayla_JSX as JSX, type Kayla_KaylaClickType as KaylaClickType, Kayla_KaylaContext as KaylaContext, type Kayla_KaylaCustomHookConfig as KaylaCustomHookConfig, type Kayla_KaylaElement as KaylaElement, type Kayla_KaylaElementRef as KaylaElementRef, type Kayla_KaylaExportables as KaylaExportables, type Kayla_KaylaExports as KaylaExports, type Kayla_KaylaFiberControl as KaylaFiberControl, Kayla_KaylaFragment as KaylaFragment, type Kayla_KaylaGame as KaylaGame, Kayla_KaylaInternals as KaylaInternals, Kayla_KaylaRect as KaylaRect, type Kayla_KaylaRef as KaylaRef, type Kayla_KaylaRenderer as KaylaRenderer, type Kayla_KaylaScene as KaylaScene, type Kayla_KaylaState as KaylaState, type Kayla_PropOfFC as PropOfFC, type Kayla_Reassignable as Reassignable, type Kayla_UnsafeKaylaFiber as UnsafeKaylaFiber, Kayla_createContext as createContext, Kayla_createElement as createElement, Kayla_createGame as createGame, Kayla_createReassignableObject as createReassignableObject, Kayla_createRenderer as createRenderer, Kayla_createScene as createScene, Kayla_createUseHook as createUseHook, selfSym as self, Kayla_setLogLevel as setLogLevel, Kayla_useClick as useClick, Kayla_useContext as useContext, Kayla_useCurrentGame as useCurrentGame, Kayla_useCurrentRenderer as useCurrentRenderer, Kayla_useCurrentScene as useCurrentScene, Kayla_useCurrentTicker as useCurrentTicker, Kayla_useDisposableRef as useDisposableRef, Kayla_useEffect as useEffect, Kayla_useEntity as useEntity, Kayla_useExports as useExports, Kayla_useFiber as useFiber, Kayla_useFiberControl as useFiberControl, Kayla_useGlobalClick as useGlobalClick, Kayla_useInitialization as useInitialization, Kayla_useNextStack as useNextStack, Kayla_usePaint as usePaint, Kayla_useRect as useRect, Kayla_useRef as useRef, Kayla_useSelf as useSelf, Kayla_useShouldRefresh as useShouldRefresh, Kayla_useState as useState, Kayla_useTick as useTick, Kayla_useViewportEffect as useViewportEffect };
1656
1691
  }
1657
1692
 
1658
- export { useShouldRefresh as $, setLogLevel as A, useClick as B, useContext as C, useCurrentGame as D, type ExportsOfFC as E, type FCProps as F, useCurrentRenderer as G, useCurrentScene as H, useCurrentTicker as I, JSX as J, Kayla as K, useDisposableRef as L, useEffect as M, useEntity as N, useExports as O, type PropOfFC as P, useFiber as Q, type Reassignable as R, useFiberControl as S, useGlobalClick as T, type UnsafeKaylaFiber as U, useInitialization as V, useNextStack as W, usePaint as X, useRect as Y, useRef as Z, useSelf as _, type FCExports as a, useState as a0, useTick as a1, type FC as b, type KaylaClickType as c, KaylaContext as d, type KaylaCustomHookConfig as e, type KaylaElement as f, type KaylaElementRef as g, type KaylaExportables as h, type KaylaExports as i, type KaylaFiberControl as j, KaylaFragment as k, KaylaGame as l, KaylaInternals as m, KaylaRect as n, type KaylaRef as o, KaylaRenderer as p, KaylaScene as q, type KaylaState as r, createContext as s, createElement as t, createGame as u, createReassignableObject as v, createRenderer as w, createScene as x, createUseHook as y, selfSym as z };
1693
+ export { useShouldRefresh as $, setLogLevel as A, useClick as B, useContext as C, useCurrentGame as D, type ExportsOfFC as E, type FCProps as F, useCurrentRenderer as G, useCurrentScene as H, useCurrentTicker as I, JSX as J, Kayla as K, useDisposableRef as L, useEffect as M, useEntity as N, useExports as O, type PropOfFC as P, useFiber as Q, type Reassignable as R, useFiberControl as S, useGlobalClick as T, type UnsafeKaylaFiber as U, useInitialization as V, useNextStack as W, usePaint as X, useRect as Y, useRef as Z, useSelf as _, type FCExports as a, useState as a0, useTick as a1, useViewportEffect as a2, type FC as b, type KaylaClickType as c, KaylaContext as d, type KaylaCustomHookConfig as e, type KaylaElement as f, type KaylaElementRef as g, type KaylaExportables as h, type KaylaExports as i, type KaylaFiberControl as j, KaylaFragment as k, KaylaGame as l, KaylaInternals as m, KaylaRect as n, type KaylaRef as o, KaylaRenderer as p, KaylaScene as q, type KaylaState as r, createContext as s, createElement as t, createGame as u, createReassignableObject as v, createRenderer as w, createScene as x, createUseHook as y, selfSym as z };
@@ -1,4 +1,4 @@
1
- import { a as LeaGameII, b as LeaTimeout, c as LeaRendererII, d as LeaEventEmitter, V as Vector2, e as LeaTickerII, R as RectLeaEntity, f as LeaSceneII } from './lea-k7IGP_-W.cjs';
1
+ import { a as LeaGameII, b as LeaTimeout, c as LeaRendererII, d as LeaEventEmitter, V as Vector2, e as LeaTickerII, R as RectLeaEntity, f as LeaSceneII } from './lea-B1DIEiLR.cjs';
2
2
 
3
3
  /**
4
4
  * Base props that every Kayla functional component can receive.
@@ -352,7 +352,7 @@ declare namespace KaylaInternals {
352
352
  usePaint(onPaint: KaylaFiber["onPaint"][number]): void;
353
353
  useEntity(): KaylaElementRef;
354
354
  useSelf<T>(init: () => T): T;
355
- useInitialization(init: KaylaFiber["onInit"]): void;
355
+ useInitialization(init: KaylaFiber["onInits"][number]): void;
356
356
  useRect(): KaylaRect;
357
357
  useFiber(): UnsafeKaylaFiber;
358
358
  useFiberControl(): KaylaFiberControl;
@@ -367,6 +367,7 @@ declare namespace KaylaInternals {
367
367
  useRef(initialValue: typeof selfSym): KaylaElementRef;
368
368
  useRef<T>(initialValue: T | null): KaylaRef<T>;
369
369
  useEffect(onEffect: KaylaFiber["onEffect"][number]): void;
370
+ useViewportEffect(onEffect: KaylaFiber["onViewportEffect"][number]): void;
370
371
  useExports<T extends FC<any, any>>(_fc: T, onExport: KaylaFiber<PropOfFC<T>, ExportsOfFC<T>>["onExport"]): void;
371
372
  useGlobalClick(onClick: KaylaFiber["onGlobalClick"][number]): void;
372
373
  useClick(onClick: KaylaFiber["onGlobalClick"][number]): void;
@@ -575,9 +576,14 @@ declare namespace KaylaInternals {
575
576
  };
576
577
  get childrenCount(): number;
577
578
  maxSafeChildren: number;
579
+ dynamicChildren: KaylaElement<any>[];
578
580
  constructor(globalKayla: GlobalKayla, scene: KaylaScene, element: KaylaElement<Props>);
579
581
  getChildrenEntities(): KaylaRectEntity[];
580
582
  pointerHook(pos: Vector2, type: KaylaClickType): void;
583
+ resizeHook({ width, height }: {
584
+ width: number;
585
+ height: number;
586
+ }): void;
581
587
  bindEvents(): void;
582
588
  unbindEvents(): void;
583
589
  get key(): string;
@@ -587,9 +593,10 @@ declare namespace KaylaInternals {
587
593
  entity?: KaylaRectEntity;
588
594
  onExport: () => KaylaExports<Exports>;
589
595
  onEffect: Array<() => (() => void) | void>;
596
+ onViewportEffect: Array<(renderer: KaylaRenderer, width: number, height: number) => void>;
590
597
  onGlobalClick: Array<(pos: Vector2, type: KaylaClickType) => void | void>;
591
- onInit: () => (() => void) | void;
592
- onUnInit: () => (() => void) | void;
598
+ onInits: Array<() => (() => void) | void>;
599
+ onUnInits: Array<() => (() => void) | void>;
593
600
  onUnEffect: Array<() => void>;
594
601
  onEffectDeps?: KaylaState<any>[] | undefined;
595
602
  onPaint: Array<(ctx: CanvasRenderingContext2D, event: KaylaEvent) => void>;
@@ -601,6 +608,8 @@ declare namespace KaylaInternals {
601
608
  useDrawCallIndex: number;
602
609
  useStepCallIndex: number;
603
610
  useRefCallIndex: number;
611
+ useInitCallIndex: number;
612
+ useViewCallIndex: number;
604
613
  lastStateDeps: Array<{
605
614
  stateRef: KaylaState<any>;
606
615
  stamp: number;
@@ -618,6 +627,7 @@ declare namespace KaylaInternals {
618
627
  shouldFullRefresh(): boolean;
619
628
  captureDepStamps(): void;
620
629
  refresh(): void;
630
+ updateChildren(fcChildren: KaylaFiber<Props>["children"], isRefreshCall: boolean): void;
621
631
  lastChildren: KaylaFiber<any>[];
622
632
  isFirstUse: boolean;
623
633
  use(): void;
@@ -678,6 +688,11 @@ declare namespace KaylaInternals {
678
688
  class KaylaInternalRect {
679
689
  #private;
680
690
  constructor(fiber: KaylaFiber<any, any>);
691
+ /**
692
+ * Default behavior color
693
+ */
694
+ get color(): string;
695
+ set color(s: string);
681
696
  getRaw(): KaylaRect.RawKaylaRect;
682
697
  private get entity();
683
698
  /**
@@ -1004,6 +1019,23 @@ declare const useShouldRefresh: (deps: KaylaState<any>[]) => void;
1004
1019
  * @see {@link useInitialization} — for one-shot setup that survives refreshes
1005
1020
  */
1006
1021
  declare const useEffect: (onEffect: KaylaInternals.KaylaFiber["onEffect"][number]) => void;
1022
+ /**
1023
+ * Registers a side-effect that runs **whenever the renderer's viewport size changes**
1024
+ * (world units).
1025
+ *
1026
+ * The callback receives current viewport dimensions.
1027
+ *
1028
+ * Multiple calls stack — all callbacks run in declaration order.
1029
+ *
1030
+ * **This hook MUST be called at the top level of a component function.**
1031
+ *
1032
+ * @param callback - Receives renderer, width, and height
1033
+ * @example
1034
+ * useViewportEffect((renderer, width, height) => {
1035
+ * rect.x = renderer.centerX;
1036
+ * });
1037
+ */
1038
+ declare const useViewportEffect: (onEffect: KaylaInternals.KaylaFiber["onViewportEffect"][number]) => void;
1007
1039
  /**
1008
1040
  * Registers a callback that runs on **every click anywhere** in any attached renderer.
1009
1041
  *
@@ -1056,6 +1088,8 @@ declare const useClick: (onClick: KaylaInternals.KaylaFiber["onGlobalClick"][num
1056
1088
  *
1057
1089
  * If the callback returns a function, it is called **only on final entity destruction**.
1058
1090
  *
1091
+ * Multiple `useInitialization` calls **stack** — all run in declaration order.
1092
+ *
1059
1093
  * @param init One-time setup function — may return cleanup
1060
1094
  *
1061
1095
  * @example
@@ -1064,7 +1098,7 @@ declare const useClick: (onClick: KaylaInternals.KaylaFiber["onGlobalClick"][num
1064
1098
  * return () => physicsEngine.destroyBody(body); // cleanup only on unmount
1065
1099
  * });
1066
1100
  */
1067
- declare const useInitialization: (init: KaylaInternals.KaylaFiber["onInit"]) => void;
1101
+ declare const useInitialization: (init: KaylaInternals.KaylaFiber["onInits"][number]) => void;
1068
1102
  /**
1069
1103
  * Returns a convenient, mutable facade for the current entity's rectangle properties.
1070
1104
  *
@@ -1651,8 +1685,9 @@ declare const Kayla_useSelf: typeof useSelf;
1651
1685
  declare const Kayla_useShouldRefresh: typeof useShouldRefresh;
1652
1686
  declare const Kayla_useState: typeof useState;
1653
1687
  declare const Kayla_useTick: typeof useTick;
1688
+ declare const Kayla_useViewportEffect: typeof useViewportEffect;
1654
1689
  declare namespace Kayla {
1655
- export { type Kayla_ExportsOfFC as ExportsOfFC, type Kayla_FC as FC, type Kayla_FCExports as FCExports, type Kayla_FCProps as FCProps, Kayla_JSX as JSX, type Kayla_KaylaClickType as KaylaClickType, Kayla_KaylaContext as KaylaContext, type Kayla_KaylaCustomHookConfig as KaylaCustomHookConfig, type Kayla_KaylaElement as KaylaElement, type Kayla_KaylaElementRef as KaylaElementRef, type Kayla_KaylaExportables as KaylaExportables, type Kayla_KaylaExports as KaylaExports, type Kayla_KaylaFiberControl as KaylaFiberControl, Kayla_KaylaFragment as KaylaFragment, type Kayla_KaylaGame as KaylaGame, Kayla_KaylaInternals as KaylaInternals, Kayla_KaylaRect as KaylaRect, type Kayla_KaylaRef as KaylaRef, type Kayla_KaylaRenderer as KaylaRenderer, type Kayla_KaylaScene as KaylaScene, type Kayla_KaylaState as KaylaState, type Kayla_PropOfFC as PropOfFC, type Kayla_Reassignable as Reassignable, type Kayla_UnsafeKaylaFiber as UnsafeKaylaFiber, Kayla_createContext as createContext, Kayla_createElement as createElement, Kayla_createGame as createGame, Kayla_createReassignableObject as createReassignableObject, Kayla_createRenderer as createRenderer, Kayla_createScene as createScene, Kayla_createUseHook as createUseHook, selfSym as self, Kayla_setLogLevel as setLogLevel, Kayla_useClick as useClick, Kayla_useContext as useContext, Kayla_useCurrentGame as useCurrentGame, Kayla_useCurrentRenderer as useCurrentRenderer, Kayla_useCurrentScene as useCurrentScene, Kayla_useCurrentTicker as useCurrentTicker, Kayla_useDisposableRef as useDisposableRef, Kayla_useEffect as useEffect, Kayla_useEntity as useEntity, Kayla_useExports as useExports, Kayla_useFiber as useFiber, Kayla_useFiberControl as useFiberControl, Kayla_useGlobalClick as useGlobalClick, Kayla_useInitialization as useInitialization, Kayla_useNextStack as useNextStack, Kayla_usePaint as usePaint, Kayla_useRect as useRect, Kayla_useRef as useRef, Kayla_useSelf as useSelf, Kayla_useShouldRefresh as useShouldRefresh, Kayla_useState as useState, Kayla_useTick as useTick };
1690
+ export { type Kayla_ExportsOfFC as ExportsOfFC, type Kayla_FC as FC, type Kayla_FCExports as FCExports, type Kayla_FCProps as FCProps, Kayla_JSX as JSX, type Kayla_KaylaClickType as KaylaClickType, Kayla_KaylaContext as KaylaContext, type Kayla_KaylaCustomHookConfig as KaylaCustomHookConfig, type Kayla_KaylaElement as KaylaElement, type Kayla_KaylaElementRef as KaylaElementRef, type Kayla_KaylaExportables as KaylaExportables, type Kayla_KaylaExports as KaylaExports, type Kayla_KaylaFiberControl as KaylaFiberControl, Kayla_KaylaFragment as KaylaFragment, type Kayla_KaylaGame as KaylaGame, Kayla_KaylaInternals as KaylaInternals, Kayla_KaylaRect as KaylaRect, type Kayla_KaylaRef as KaylaRef, type Kayla_KaylaRenderer as KaylaRenderer, type Kayla_KaylaScene as KaylaScene, type Kayla_KaylaState as KaylaState, type Kayla_PropOfFC as PropOfFC, type Kayla_Reassignable as Reassignable, type Kayla_UnsafeKaylaFiber as UnsafeKaylaFiber, Kayla_createContext as createContext, Kayla_createElement as createElement, Kayla_createGame as createGame, Kayla_createReassignableObject as createReassignableObject, Kayla_createRenderer as createRenderer, Kayla_createScene as createScene, Kayla_createUseHook as createUseHook, selfSym as self, Kayla_setLogLevel as setLogLevel, Kayla_useClick as useClick, Kayla_useContext as useContext, Kayla_useCurrentGame as useCurrentGame, Kayla_useCurrentRenderer as useCurrentRenderer, Kayla_useCurrentScene as useCurrentScene, Kayla_useCurrentTicker as useCurrentTicker, Kayla_useDisposableRef as useDisposableRef, Kayla_useEffect as useEffect, Kayla_useEntity as useEntity, Kayla_useExports as useExports, Kayla_useFiber as useFiber, Kayla_useFiberControl as useFiberControl, Kayla_useGlobalClick as useGlobalClick, Kayla_useInitialization as useInitialization, Kayla_useNextStack as useNextStack, Kayla_usePaint as usePaint, Kayla_useRect as useRect, Kayla_useRef as useRef, Kayla_useSelf as useSelf, Kayla_useShouldRefresh as useShouldRefresh, Kayla_useState as useState, Kayla_useTick as useTick, Kayla_useViewportEffect as useViewportEffect };
1656
1691
  }
1657
1692
 
1658
- export { useShouldRefresh as $, setLogLevel as A, useClick as B, useContext as C, useCurrentGame as D, type ExportsOfFC as E, type FCProps as F, useCurrentRenderer as G, useCurrentScene as H, useCurrentTicker as I, JSX as J, Kayla as K, useDisposableRef as L, useEffect as M, useEntity as N, useExports as O, type PropOfFC as P, useFiber as Q, type Reassignable as R, useFiberControl as S, useGlobalClick as T, type UnsafeKaylaFiber as U, useInitialization as V, useNextStack as W, usePaint as X, useRect as Y, useRef as Z, useSelf as _, type FCExports as a, useState as a0, useTick as a1, type FC as b, type KaylaClickType as c, KaylaContext as d, type KaylaCustomHookConfig as e, type KaylaElement as f, type KaylaElementRef as g, type KaylaExportables as h, type KaylaExports as i, type KaylaFiberControl as j, KaylaFragment as k, KaylaGame as l, KaylaInternals as m, KaylaRect as n, type KaylaRef as o, KaylaRenderer as p, KaylaScene as q, type KaylaState as r, createContext as s, createElement as t, createGame as u, createReassignableObject as v, createRenderer as w, createScene as x, createUseHook as y, selfSym as z };
1693
+ export { useShouldRefresh as $, setLogLevel as A, useClick as B, useContext as C, useCurrentGame as D, type ExportsOfFC as E, type FCProps as F, useCurrentRenderer as G, useCurrentScene as H, useCurrentTicker as I, JSX as J, Kayla as K, useDisposableRef as L, useEffect as M, useEntity as N, useExports as O, type PropOfFC as P, useFiber as Q, type Reassignable as R, useFiberControl as S, useGlobalClick as T, type UnsafeKaylaFiber as U, useInitialization as V, useNextStack as W, usePaint as X, useRect as Y, useRef as Z, useSelf as _, type FCExports as a, useState as a0, useTick as a1, useViewportEffect as a2, type FC as b, type KaylaClickType as c, KaylaContext as d, type KaylaCustomHookConfig as e, type KaylaElement as f, type KaylaElementRef as g, type KaylaExportables as h, type KaylaExports as i, type KaylaFiberControl as j, KaylaFragment as k, KaylaGame as l, KaylaInternals as m, KaylaRect as n, type KaylaRef as o, KaylaRenderer as p, KaylaScene as q, type KaylaState as r, createContext as s, createElement as t, createGame as u, createReassignableObject as v, createRenderer as w, createScene as x, createUseHook as y, selfSym as z };
package/dist/kayla.cjs CHANGED
@@ -1,5 +1,5 @@
1
- "use strict";var ye=Object.defineProperty;var ot=Object.getOwnPropertyDescriptor;var ut=Object.getOwnPropertyNames;var lt=Object.prototype.hasOwnProperty;var ge=(r,e)=>{for(var n in e)ye(r,n,{get:e[n],enumerable:!0})},ht=(r,e,n,i)=>{if(e&&typeof e=="object"||typeof e=="function")for(let s of ut(e))!lt.call(r,s)&&s!==n&&ye(r,s,{get:()=>e[s],enumerable:!(i=ot(e,s))||i.enumerable});return r};var ct=r=>ht(ye({},"__esModule",{value:!0}),r);var vt={};ge(vt,{Kayla:()=>de,KaylaContext:()=>B,KaylaFragment:()=>Ze,KaylaInternals:()=>L,KaylaRect:()=>F,LEA:()=>ae,UI:()=>it,createContext:()=>Ue,createElement:()=>$e,createGame:()=>Ve,createReassignableObject:()=>tt,createRenderer:()=>ze,createScene:()=>He,createUseHook:()=>rt,self:()=>ue,setLogLevel:()=>nt,useClick:()=>Xe,useContext:()=>Je,useCurrentGame:()=>We,useCurrentRenderer:()=>Ye,useCurrentScene:()=>je,useCurrentTicker:()=>Qe,useDisposableRef:()=>et,useEffect:()=>le,useEntity:()=>Be,useExports:()=>Q,useFiber:()=>Ce,useFiberControl:()=>he,useGlobalClick:()=>ve,useInitialization:()=>W,useNextStack:()=>ce,usePaint:()=>j,useRect:()=>Y,useRef:()=>oe,useSelf:()=>_,useShouldRefresh:()=>Oe,useState:()=>Ne,useTick:()=>qe});module.exports=ct(vt);var de={};ge(de,{KaylaContext:()=>B,KaylaFragment:()=>Ze,KaylaInternals:()=>L,KaylaRect:()=>F,createContext:()=>Ue,createElement:()=>$e,createGame:()=>Ve,createReassignableObject:()=>tt,createRenderer:()=>ze,createScene:()=>He,createUseHook:()=>rt,self:()=>ue,setLogLevel:()=>nt,useClick:()=>Xe,useContext:()=>Je,useCurrentGame:()=>We,useCurrentRenderer:()=>Ye,useCurrentScene:()=>je,useCurrentTicker:()=>Qe,useDisposableRef:()=>et,useEffect:()=>le,useEntity:()=>Be,useExports:()=>Q,useFiber:()=>Ce,useFiberControl:()=>he,useGlobalClick:()=>ve,useInitialization:()=>W,useNextStack:()=>ce,usePaint:()=>j,useRect:()=>Y,useRef:()=>oe,useSelf:()=>_,useShouldRefresh:()=>Oe,useState:()=>Ne,useTick:()=>qe});var ae={};ge(ae,{DeltaTweenII:()=>ie,ENVIRONMENT:()=>xe,GEmitterMemory:()=>be,LeaEntityII:()=>H,LeaEventEmitter:()=>K,LeaGameII:()=>O,LeaRendererII:()=>U,LeaSceneII:()=>N,LeaSerializers:()=>Ee,LeaTickerII:()=>re,LeaTimeout:()=>se,LeaUtilsII:()=>k,LiaAudio:()=>z,LiaAudioSrc:()=>V,LiaOscSFX:()=>A,LiaSFXMap:()=>gt,NOTE_NAMES:()=>Te,RectLeaEntity:()=>X,Vector2:()=>M,colToRGBA:()=>ft,defaultSFXConfig:()=>Ke,editRGBA:()=>pt,generateUUID:()=>Ae,getAvoidAngle:()=>De,getEnvironment:()=>ke,getNormalizedColor:()=>dt,getRayHit:()=>Le,isInitiallyMobile:()=>wt,isMobile:()=>Ge,isNode:()=>q,isNote:()=>yt,isWeb:()=>E,parseFillStyle:()=>Re,raycastAvoid:()=>xt,scaleCoord:()=>mt,setAnimInterval:()=>_e,sfxHit:()=>Me,sfxJump:()=>Fe,sfxLaser:()=>Pe,sfxUIClick:()=>Se,sfxUIHover:()=>Ie,shortUID:()=>bt,tinyUID:()=>we});var K=class{#e=new Map;constructor(){this.#e=new Map}on(e,n){let i=this.#e.get(e)||[];return i.push(n),this.#e.set(e,i),this}once(e,n){let i=(...s)=>{this.off(e,i),n(...s)};return this.on(e,i),this}off(e,n){let i=this.#e.get(e);if(!i)return this;let s=i.indexOf(n);return s>=0&&i.splice(s,1),this}emit(e,...n){let i=this.#e.get(e);if(!i||i.length===0){if(e==="error")throw n[0];return!1}return i.slice().forEach(s=>s(...n)),!0}removeAllListeners(e){return e?this.#e.delete(e):this.#e.clear(),this}listenerCount(e){return this.#e.get(e)?.length??0}},U=class extends K{canvas;ctx;running;_rafId;_fps;_frameCount;_fpsTimer;_lastFrameTime;constructor(e,{viewportWidth:n,viewportHeight:i,cameraWidth:s,cameraHeight:o}={}){if(!E)throw new Error("Web-Only");super(),this.canvas=e,this.ctx=e.getContext("2d"),this.automatic=!0,this.#e=n??e.width,this.#t=i??e.height,this.#n=s??e.width,this.#r=o??e.height,this.running=!1,this._rafId=null,this._loop=this._loop.bind(this),this.updateCanvasResolution(),this._fps=60,this._frameCount=0,this._fpsTimer=0}automatic;retransform(){this.ctx.setTransform(1,0,0,1,0,0);let e=this.#n/this.#e,n=this.#r/this.#t;this.ctx.translate(this.#n/2,this.#r/2),this.ctx.scale(e,n),this.ctx.translate(-this.#e/2,-this.#t/2)}#e=0;#t=0;#n=0;#r=0;get viewportWidth(){return this.#e}set viewportWidth(e){this.#e=e,this.retransform()}get width(){return this.#e}get height(){return this.#t}get centerX(){return this.#e/2}get centerY(){return this.#t/2}get left(){return 0}get top(){return 0}get right(){return this.#e}get bottom(){return this.#t}get viewportHeight(){return this.#t}set viewportHeight(e){this.#t=e,this.retransform()}get cameraWidth(){return this.#n}set cameraWidth(e){this.#n=e,this.updateCanvasResolution(),this.retransform()}get cameraHeight(){return this.#r}set cameraHeight(e){this.#r=e,this.updateCanvasResolution(),this.retransform()}updateCanvasResolution(){this.canvas.width=this.#n,this.canvas.height=this.#r}applyTransform(){this.retransform()}get FPS(){return this._fps}_loop(){this.automatic&&this.update(),this._rafId=requestAnimationFrame(this._loop)}update(){if(!this.running||!E)return;let e=performance.now(),n=(e-(this._lastFrameTime??e))/1e3;this._lastFrameTime=e,this._frameCount++,this._fpsTimer+=n,this._fpsTimer>=1&&(this._fps=Math.round(this._frameCount/this._fpsTimer),this._frameCount=0,this._fpsTimer=0),this.ctx.clearRect(0,0,this.#n,this.#r),this.emit("draw",this.ctx)}start(){if(!this.running){if(!E||typeof globalThis.requestAnimationFrame>"u")throw new Error("Raf is not supported");this.running=!0,this._rafId=requestAnimationFrame(this._loop)}}stop(){if(!E||typeof globalThis.requestAnimationFrame>"u")throw new Error("Raf is not supported");this.running=!1,this._rafId!==null&&(cancelAnimationFrame(this._rafId),this._rafId=null)}},re=class extends K{setNow(e){this.#e=e}#e=0;__intervalId=null;__lastTime=0;constructor(e=16){super(),this.#t=e,this.speedHackDT=1}speedHackDT;get isRaf(){return this.tickInterval===1/0}#t=15;get tickInterval(){return this.#t}set tickInterval(e){this.#t=e,this.__intervalId&&(this.stop(),this.start())}now(){return this.#e}__tick(){let e=performance.now(),n=(e-this.__lastTime)/1e3*this.speedHackDT;this.__lastTime=e,!(E&&typeof this.__intervalId=="function"&&document.hidden)&&(this.#e+=n*1e3,this.emit("tick",n))}createTimeout(e){return new se(e,this)}createTween(e,n=()=>{}){let i=new ie(e),s=(o=0)=>{if(i.finished){this.off("tick",s);return}i.update(o)};return i.on("finish",()=>{this.off("tick",s)}),i.on("delta",o=>{n(o)}),this.on("tick",s),i}start(){this.__intervalId===null&&(this.__lastTime=performance.now(),this.__intervalId=E&&!isFinite(this.tickInterval)?_e(()=>this.__tick()).clear:setInterval(()=>this.__tick(),this.tickInterval))}stop(){this.__intervalId!==null&&(typeof this.__intervalId=="function"?this.__intervalId():clearInterval(this.__intervalId)),this.__intervalId=null}getSineMod(e,n=0){return .5+.5*Math.sin((this.now()%e/e+n)*2*Math.PI)}},Ee;(t=>{function r(a){return a===!0?1:0}t.booleanExport=r;function e(a){return a===0?!1:a===1}t.booleanImport=e;function n(a){return`${a.x}|${a.y}`}t.vec2Export=n;function i(a){let[h,c]=a.split("|"),g=parseFloat(h),w=parseFloat(c);if(isNaN(g)||isNaN(w))throw new Error(`Invalid Vector2 string: ${a}`);return new M(g,w)}t.vec2Import=i,t.booleanMap={mapExport:r,mapImport:e};function o(a){return h=>Number(h.toFixed(a))}t.createRounder=o;function d(a=10){return{mapExport(h){return Math.round(h/a)},mapImport(h){return h*a}}}t.createLowPrecision=d;function f(a){return Math.round(a)}t.lightWeightRounder=f;function u(a=100){return{mapExport(h){return Math.round(h*a)},mapImport(h){return h/a}}}t.createPercent=u;function l(a){let h=new Map(Object.entries(a));return{mapExport:c=>h.get(c)??null,mapImport:c=>Array.from(h.entries()).find(([g,w])=>w===c)?.[0]??null}}t.createLookup=l;function p(a){let h=a*(180/Math.PI);return Math.round((h%360+360)%360)}t.radToDeg=p;function y(a){return a*(Math.PI/180)}t.degToRad=y,t.angleRadToDeg={mapExport:p,mapImport:y};function x(a=10){let h=d(a);return{mapExport(c){return h.mapExport(p(c))},mapImport(c){return h.mapImport(y(c))}}}t.createLowPrecisionRadToDeg=x})(Ee||={});var H=class r extends K{name="";scaleRotate=0;scale=1;constructor(e,n=0,i=0){super(),this.autoTranslate=!1,this.name=e,this.z=0,this.___pos=new M(n,i),this.nonSerializableProperties=[],this.nonSerializableProperties.push("___pos","autoTranslate","arraySerializeMap"),this.forceSerializableProperties=[],this.forceSerializableProperties.push("x","y")}arraySerializeMap;autoTranslate;z;___pos;nonSerializableProperties;forceSerializableProperties;get pos(){return this.___pos}get x(){return this.pos.x}get y(){return this.pos.y}set x(e){this.pos.x=e}set y(e){this.pos.y=e}handleUpdate(e){if(this.update)try{this.emit("update",e),this.update(e)}catch(n){this.emit("error",n)}}handleDraw(e){if(!(q||!this.draw)){e.save(),this.autoTranslate&&e.translate(this.x,this.y);try{this.emit("draw",e),this.draw(e)}catch(n){this.emit("error",n)}e.restore()}}serialize(){if(Array.isArray(this.arraySerializeMap))return this.arraySerializeMap.map(([s,{mapExport:o}])=>{let d=Reflect.get(this,s);return o?o(d):d});let e=["_events","_eventsCount","_maxListeners","nonSerializableProperties","forceSerializableProperties"],n=[...Reflect.ownKeys(this),...this.forceSerializableProperties].filter(s=>!this.nonSerializableProperties.includes(s)&&!e.includes(s.toString())),i=Object.fromEntries(n.map(s=>{let o=Reflect.get(this,s);if(q&&typeof o=="number"){let d=o.toString().split("."),u=(d[1]?d[1].length:0)>2?Number(o.toFixed(2)):o;return[s,u]}return[s,o]}));return JSON.parse(JSON.stringify(i))}toLocal(e){return e.subtract(this.pos)}toWorld(e){return e.add(this.pos)}deserializeArray(e){return r.deserializeArray(this.arraySerializeMap,e)}static deserializeArray(e,n){if(!e||!Array.isArray(n))return n;let i={};for(let s=0;s<n.length;s++){let o=e[s];if(!o)break;let[d,{mapImport:f}]=o,u=n[s];if(f&&(u=f(u)),typeof d!="string")break;try{Reflect.set(i,d,u)}catch(l){console.error(l)}}return i}},N=class extends K{name="";entities=new Map;paused=!0;constructor(e){super(),this.name=e}handleUpdate(e){if(!this.paused){this.emit("update",e);for(let n of this.entities.values())n.handleUpdate(e)}}handleDraw(e){if(!q&&!this.paused){this.emit("draw",e);for(let n of[...this.entities.values()].sort((i,s)=>i.z-s.z))n.handleDraw(e)}}addEntity(e){if(!(e instanceof H))throw new Error("invalid entity");if(!e.name)throw new Error("Entity must have a name.");this.entities.set(e.name,e)}removeEntity(e){if(!(e instanceof H))throw new Error("invalid entity");this.entities.delete(e.name)}getEntity(e){return this.entities.get(e)}},O=class{scenes;ticker;get centerX(){return this.width/2}get centerY(){return this.height/2}get left(){return 0}get top(){return 0}get right(){return this.width}get bottom(){return this.height}width;height;constructor(e,n,i=16){this.ticker=new re(i),this.scenes=new Map,this.width=e,this.height=n,this.ticker.on("tick",s=>{for(let o of this.scenes.values())o.paused||o.handleUpdate(s)})}addScene(e){if(!e.name)throw new Error("Scene must have a name.");e.paused=!1,this.scenes.set(e.name,e)}removeScene(e){e&&(e.paused=!0),this.scenes.delete(e.name)}now(){return this.ticker.now()}start(){this.ticker.start()}stop(){this.ticker.stop()}},k={lerp(r,e,n){return r+(e-r)*n},clamp(r,e,n){return Math.min(n,Math.max(e,r))},clamp01(r){return Math.min(1,Math.max(0,r))},easeLinear(r){return r},easeInQuad(r){return r*r},easeOutQuad(r){return 1-(1-r)*(1-r)},easeInOutQuad(r){return r<.5?2*r*r:1-Math.pow(-2*r+2,2)/2},easeInSine(r){return 1-Math.cos(r*Math.PI/2)},easeOutSine(r){return Math.sin(r*Math.PI/2)},easeInOutSine(r){return-(Math.cos(Math.PI*r)-1)/2},easeInExpo(r){return r===0?0:Math.pow(2,10*r-10)},easeOutExpo(r){return r===1?1:1-Math.pow(2,-10*r)},easeInOutExpo(r){return r===0?0:r===1?1:r<.5?Math.pow(2,20*r-10)/2:(2-Math.pow(2,-20*r+10))/2},smoothstep(r){return r=k.clamp(r,0,1),r*r*(3-2*r)},randomLerp(r,e){return k.lerp(r,e,Math.random())},randomInt(r,e){return Math.floor(Math.random()*(e-r+1))+r},randomArrayValue(r){return r[k.randomInt(0,r.length-1)]},createBezier(r,e,n,i){function s(f,u,l,p,y){let b=1-f;return b*b*b*u+3*b*b*f*l+3*b*f*f*p+f*f*f*y}function o(f,u,l,p,y){let b=1-f;return 3*b*b*(l-u)+6*b*f*(p-l)+3*f*f*(y-p)}function d(f){let u=f;for(let l=0;l<6;l++){let p=s(u,0,r,n,1),y=o(u,0,r,n,1);if(y===0)break;u-=(p-f)/y}return k.clamp(u,0,1)}return function(u){u=k.clamp(u,0,1);let l=d(u);return s(l,0,e,i,1)}},lengthSquared(...r){return r.reduce((e,n)=>e+n*n,0)},normalizeRad(r){let e=2*Math.PI;return r=r%e,r<0&&(r+=e),r},angleInvertY(r){return k.normalizeRad(-r)},degToRadFlipY(r){return k.angleInvertY(r*Math.PI/180)},minimalAngularDirection(r,e){r=k.normalizeRad(r),e=k.normalizeRad(e);let n=k.normalizeRad(e-r),i=k.normalizeRad(r-e);return n<=i?1:-1}},ie=class extends K{constructor({delta:e,ms:n,easing:i}){super(),this.delta=e,this.duration=n,this.elapsed=0,this.easing=i??(s=>s),this.lastValue=0,this.finished=!1}delta;duration;elapsed;lastValue;finished;easing;update(e){this.elapsed+=e*1e3;let n=k.clamp(this.elapsed/this.duration,0,1),i=this.easing(n),s=this.delta*i,o=s-this.lastValue;this.lastValue=s,this.emit("delta",o),n>=1&&(this.finished=!0,this.emit("finish",void 0))}},X=class extends H{constructor(e,n=0,i=0,s=50,o=50){super(e,n,i),this.width=s,this.height=o}width;height;get left(){return this.x-this.width/2}set left(e){this.x=e+this.width/2}get right(){return this.x+this.width/2}set right(e){this.x=e-this.width/2}get top(){return this.y-this.height/2}set top(e){this.y=e+this.height/2}get bottom(){return this.y+this.height/2}set bottom(e){this.y=e-this.height/2}get lx(){return 0}get ly(){return 0}get lleft(){return-this.width/2}get lright(){return this.width/2}get ltop(){return-this.height/2}get lbottom(){return this.height/2}isCollidingWith(e){return!(this.right<e.left||this.left>e.right||this.bottom<e.top||this.top>e.bottom)}color="rgba(0, 0, 255, 0.3)";draw(e){e.translate(this.x,this.y),e.rotate(this.scaleRotate),e.fillStyle=this.color,e.fillRect(-this.width/2,-this.height/2,this.width,this.height)}},se=class extends K{duration;ticker;elapsed;finished;_resolve;promise;_timeoutId;constructor(e,n=null){super(),this.duration=e,this.ticker=n,this.elapsed=0,this.finished=!1,this._resolve=null,this.promise=new Promise(i=>this._resolve=i),this.update=this.update.bind(this),this.ticker&&this.ticker.on("tick",this.update)}update(e=0){this.finished||(this.elapsed+=e*1e3,this.elapsed>=this.duration&&this.finish())}finish(){this.finished||(this.finished=!0,this.emit("finish",void 0),this._resolve&&this._resolve(),this.ticker&&this.ticker.off("tick",this.update))}start(){return this.ticker||(this._timeoutId=setTimeout(()=>this.finish(),this.duration)),this}cancel(){this.finished||(this.finished=!0,!this.ticker&&this._timeoutId!=null&&clearTimeout(this._timeoutId),this.ticker&&this.ticker.off("tick",this.update))}then(e,n){return this.promise.then(e,n)}after(e,n){return this.promise.then(e,n)}},M=class r{constructor(e=0,n=0){this.x=e,this.y=n}x;y;toJSON(){return{x:this.x,y:this.y,vec2:!0}}static isVec2(e){return e&&typeof e=="object"&&"x"in e&&"y"in e&&e.vec2===!0}static fromSerialized(e){return this.isVec2(e)?new this(e.x,e.y):null}rotate(e){let n=Math.cos(e),i=Math.sin(e);return new r(this.x*n-this.y*i,this.x*i+this.y*n)}static from(e){return new r(Math.cos(e),Math.sin(e))}isEmpty(){return Math.abs(this.x)<.01&&Math.abs(this.y)<.01}get angle(){return Math.atan2(this.y,this.x)}angleTo(e){return Math.atan2(e.y-this.y,e.x-this.x)}get length(){return Math.hypot(this.x,this.y)}get lengthSquared(){return this.x*this.x+this.y*this.y}normalized(){let e=this.length;return e===0?new r(0,0):new r(this.x/e,this.y/e)}consume(e){let n=this.length;n<=e?(this.x=0,this.y=0):this.overwite(this.scale((n-e)/n))}project(e){return e.scale(this.dotNormalized(e))}reflect(e){let n=this.dot(e);return this.subtract(e.scale(2*n))}dotNormalized(e){let n=this.normalized(),i=e.normalized();return n.x*i.x+n.y*i.y}lengthSquaredTo(e){let n=this.x-e.x,i=this.y-e.y;return n*n+i*i}dot(e){return this.x*e.x+this.y*e.y}distanceTo(e){return Math.hypot(this.x-e.x,this.y-e.y)}distanceToCheap(e){let n=this.x-e.x,i=this.y-e.y;return n*n+i*i}directionTo(e){return new r(e.x-this.x,e.y-this.y).normalized()}add(e){return new r(this.x+e.x,this.y+e.y)}addRaw(e){return new r(this.x+e,this.y+e)}overwite(e){this.x=e.x,this.y=e.y}subtract(e){return new r(this.x-e.x,this.y-e.y)}scale(e){return new r(this.x*e,this.y*e)}toString(){return`Vector2(${this.x}, ${this.y})`}clone(){return new r(this.x,this.y)}};function dt(r){let e=/^rgba?\(([^)]+)\)$/,n=r.match(e);if(n){let[i,s,o,d=1]=n[1].split(",").map(f=>parseFloat(f));return{r:Math.max(0,Math.min(255,Math.floor(i))),g:Math.max(0,Math.min(255,Math.floor(s))),b:Math.max(0,Math.min(255,Math.floor(o))),a:Math.max(0,Math.min(1,Math.floor(d*255)/255))}}return Re(r)}function ft(r){return`rgba(${r.r}, ${r.g}, ${r.b}, ${r.a})`}function Re(r){if(r=r.trim().toLowerCase(),r[0]==="#"){let n,i,s;if(r.length===7)n=parseInt(r.slice(1,3),16),i=parseInt(r.slice(3,5),16),s=parseInt(r.slice(5,7),16);else if(r.length===4)n=parseInt(r[1]+r[1],16),i=parseInt(r[2]+r[2],16),s=parseInt(r[3]+r[3],16);else throw new Error("Invalid hex color");return{r:n,g:i,b:s,a:1}}let e=r.match(/^rgba?\s*\(\s*(\d+)[, ]\s*(\d+)[, ]\s*(\d+)(?:[, ]\s*([\d.]+))?\s*\)$/);if(e)return{r:parseInt(e[1]),g:parseInt(e[2]),b:parseInt(e[3]),a:e[4]!==void 0?parseFloat(e[4]):1};throw new Error("Unsupported fillStyle format")}function pt(r,{r:e,g:n,b:i,a:s}={}){let[o,d,f,u,l]=r.match(/rgba?\((\d+),\s*(\d+),\s*(\d+),?\s*([\d.]*)\)?/)||[];return`rgba(${e??d}, ${n??f}, ${i??u}, ${s??(l||1)})`}function mt(r,e,n){return n+(r-n)*e}function ke(){return typeof process<"u"&&process.release?.name==="node"?"node":typeof window<"u"||typeof self<"u"?"web":"unknown"}var xe=ke(),q=xe==="node",E=xe==="web",z=class r{static unlock(){E&&this.audioCtx.state!=="running"&&this.audioCtx.resume()}static audioCtx=E?new AudioContext:null;static masterGain=E?this.audioCtx.createGain():null;static musicGain=E?this.audioCtx.createGain():null;static sfxGain=E?this.audioCtx.createGain():null;static{E&&(this.masterGain.gain.value=1,this.musicGain.gain.value=1,this.sfxGain.gain.value=1,this.sfxGain.connect(this.masterGain),this.musicGain.connect(this.masterGain),this.masterGain.connect(this.audioCtx.destination))}static get SFX_VOLUME(){return this.sfxGain.gain.value}static get MUSIC_VOLUME(){return this.musicGain.gain.value}static get VOLUME(){return this.masterGain.gain.value}static set SFX_VOLUME(e){this.sfxGain.gain.value=e}static set MUSIC_VOLUME(e){this.musicGain.gain.value=e}static set VOLUME(e){this.masterGain.gain.value=e}static noteToHz(e){return this.tuningFreq*Math.pow(2,(e-9)/12)}static tuningFreq=440;static audioBufferCache=new Map;static loops=new Map;static sfsx=new Map;static loopIdCounter=0;static CACHE_NAME="lia-audio-cache-v1";static async preLoad(e){if(this.audioBufferCache.has(e))return this.audioBufferCache.get(e);let n=r.CACHE_NAME,i,s;if(typeof caches<"u"&&(s=await caches.open(n),i=await s.match(e)),!i){if(i=await fetch(e),!i.ok)throw new Error(`Failed to fetch ${e}`);s&&await s.put(e,i.clone())}let o=await i.arrayBuffer(),d=await this.audioCtx.decodeAudioData(o);return this.audioBufferCache.set(e,d),d}static async getOnlyDownloadedCache(e){let n=r.CACHE_NAME;return await(await caches.open(n)).match(e)}static getCached(e){return this.audioBufferCache.get(e)||null}static async playSound(e,n=.2,i=1,s=!0){try{this.sfsx.has(e)&&this.sfsx.get(e).source.stop(),this.audioBufferCache.has(e)||await this.preLoad(e);let o=this.getCached(e);if(!o)return;let d=new V(o);d.buffer=o;let f=1-.12,u=1+.12;d.playbackRate=i??f+Math.random()*(u-f);let l=this.audioCtx.createGain();l.gain.value=n,d.tempGain=l,d.connect(l),l.connect(this.sfxGain),d.onended=()=>{d.disconnect(),l.disconnect()},d.start(),s&&this.sfsx.set(e,{source:d,gain:l})}catch(o){console.error(o)}}static async playLoop(e,n=1,{loopStart:i=0,loopEnd:s=null,exclusive:o=!0,skipMS:d=0}={}){if(o)for(let y of this.loops.keys())this.stopLoop(y);this.audioBufferCache.has(e)||await this.preLoad(e);let f=this.getCached(e);if(!f)return;let u=new V(f);u.buffer=f,u.loop=!0,typeof i=="number"&&(u.loopStart=i),typeof s=="number"&&(u.loopEnd=s);let l=this.audioCtx.createGain();l.gain.value=n,u.tempGain=l,u.playbackRate=1,u.onended=()=>{u.disconnect(),l.disconnect()},u.connect(l),l.connect(this.musicGain),u.start(0,d/1e3);let p=++this.loopIdCounter;return this.loops.set(p,{source:u,gain:l}),p}static stopLoop(e){let n=this.loops.get(e);n&&(n.source.stop(),n.source.notIndependent||(n.source.disconnect(),n.gain.disconnect()),this.loops.delete(e))}static async createLiaSource(e,{volume:n=1,speed:i=1,loop:s=!1,loopStart:o=0,loopEnd:d=null,isMusic:f=!1,gain:u=null}={}){try{this.audioBufferCache.has(e)||await this.preLoad(e);let l=this.getCached(e);if(!l)return null;let p=new V(l);p.loop=s,p.loopStart=o,p.loopEnd=typeof d=="number"?d:l.duration,p.playbackRate=i;let y=this.audioCtx.createGain();return y.gain.value=n,p.connect(y),p.tempGain=y,y.connect(u||(f?this.musicGain:this.sfxGain)),p.onended=()=>{p.disconnect(),y.disconnect()},p}catch(l){return console.error("Failed to create LiaAudioSrc:",l),null}}},Te=["C","C#","D","D#","E","F","F#","G","G#","A","A#","B"];function yt(r){return Te.includes(r)}var V=class{numberOfInputs;numberOfOutputs;constructor(e,n=z.audioCtx){this.context=n,this.buffer=e,this.source=null,this.startTime=0,this.pauseTime=0,this.playbackRate=1,this.isPlaying=!1,this.loop=!1,this.output=E?n.createGain():null,this.output.gain.value=1,this.channelCount=2,this.channelCountMode="max",this.channelInterpretation="speakers",this.numberOfInputs=0,this.numberOfOutputs=1,this.onended=null}channelCount;channelCountMode;channelInterpretation;onended;source;buffer;context;_createSource(){this.source&&(this.source.onended=null);let e=this.context.createBufferSource();return e.buffer=this.buffer,e.playbackRate.value=this.playbackRate,e.loop=this.loop,e.loopStart=this.loopStart,e.loopEnd=this.loopEnd>0?this.loopEnd:this.buffer.duration,e.connect(this.output),this.source=e,e.onended=()=>{this.source===e&&(this.isPlaying&&!this.loop&&(this.isPlaying=!1,this.pauseTime=0),typeof this.onended=="function"&&this.onended())},e}play({fadeIn:e=0,offset:n=null}={}){let i=n!==null?n:this.pauseTime;if(this.source){this.source.onended=null;try{this.source.stop()}catch{}}this.source=this._createSource(),this.startTime=this.context.currentTime-i/this.playbackRate,this.source.start(0,i),e>0?(this.output.gain.setValueAtTime(0,this.context.currentTime),this.output.gain.linearRampToValueAtTime(1,this.context.currentTime+e)):this.output.gain.setValueAtTime(1,this.context.currentTime),this.isPlaying=!0}start(e=0,n=0,i){this.isPlaying||(this.source=this._createSource(),this.startTime=this.context.currentTime+e-n/this.playbackRate,i!==void 0?this.source.start(this.context.currentTime+e,n,i):this.source.start(this.context.currentTime+e,n),this.pauseTime=n,this.isPlaying=!0)}pause({fadeOut:e=0}={}){if(!this.isPlaying)return;let n=this.getElapsed()/1e3;if(this.loop&&this.loopEnd>this.loopStart){let i=this.loopEnd-this.loopStart;n=this.loopStart+(n-this.loopStart)%i}if(this.isPlaying=!1,e>0){let i=this.context.currentTime;this.output.gain.setValueAtTime(this.output.gain.value,i),this.output.gain.linearRampToValueAtTime(0,i+e),setTimeout(()=>{if(this.source){this.source.onended=null;try{this.source.stop()}catch{}}this.pauseTime=n,this.output.gain.setValueAtTime(1,this.context.currentTime)},e*1e3)}else{if(this.source){this.source.onended=null;try{this.source.stop()}catch{}}this.pauseTime=n}}getElapsed(){return this.isPlaying?(this.context.currentTime-this.startTime)*this.playbackRate*1e3:this.pauseTime*1e3}setSpeed(e){if(e<=0)throw new Error("Playback rate must be positive");let n=this.getElapsed()/1e3;this.playbackRate=e,this.isPlaying&&(this.pause(),this.pauseTime=n,this.play())}setLoop(e=!0){this.loop=e,this.source&&(this.source.loop=e)}loop;playbackRate;startTime;tempGain=null;connect(e,n=0,i=0){if("value"in e)this.output.connect(e,n);else return this.output.connect(e,n,i),e}disconnect(e,n,i){e===void 0?this.output.disconnect():this.output.disconnect(e,n,i)}output;stop(e=0){if(this.notIndependent)return this.pause();if(!this.source)return;let n=this.context.currentTime+e;this.source.stop(n),this.isPlaying=!1,this.notIndependent||(this.pauseTime=0)}pauseTime;isPlaying;notIndependent=!1;loopStart=0;loopEnd=0},Ke={osc:{enabled:!0,type:"sine",freq:440,detune:0},noise:{enabled:!1,level:.5},ampEnv:{attack:.005,decay:.1,sustain:0,release:.1,volume:.3},pitchEnv:{amount:0,decay:.2},filter:{enabled:!1,type:"lowpass",freq:1200,Q:1,envAmount:0,decay:.2},lfo:{enabled:!1,target:"freq",rate:8,depth:20},duration:.4},A=class r{constructor(e={}){this.ctx=z.audioCtx,this.cfg=structuredClone(Ke),Object.assign(this.cfg,e)}ctx;cfg;play(e=z.sfxGain){let n=this.ctx,i=n.currentTime,s=this.cfg,o=n.createGain();o.gain.setValueAtTime(1e-4,i);let d=s.ampEnv;o.gain.exponentialRampToValueAtTime(d.volume,i+d.attack),o.gain.exponentialRampToValueAtTime(Math.max(1e-4,d.sustain*d.volume),i+d.attack+d.decay),o.gain.exponentialRampToValueAtTime(1e-4,i+s.duration+d.release);let f=o,u;s.filter.enabled&&(u=n.createBiquadFilter(),u.type=s.filter.type,u.frequency.value=s.filter.freq,u.Q.value=s.filter.Q,u.connect(o),f=u);let l;if(s.osc.enabled){if(l=n.createOscillator(),l.type=s.osc.type,l.frequency.value=s.osc.freq,l.detune.value=s.osc.detune,s.pitchEnv.amount!==0){let a=Math.pow(2,s.pitchEnv.amount/12);l.frequency.exponentialRampToValueAtTime(s.osc.freq*a,i+s.pitchEnv.decay)}l.connect(f),l.start(i),l.stop(i+s.duration+d.release)}let p;if(s.noise.enabled){let a=n.sampleRate*s.duration,h=n.createBuffer(1,a,n.sampleRate),c=h.getChannelData(0);for(let g=0;g<a;g++)c[g]=(Math.random()*2-1)*s.noise.level;p=n.createBufferSource(),p.buffer=h,p.connect(f),p.start(i),p.stop(i+s.duration+d.release)}let y,b;s.lfo.enabled&&l&&(y=n.createOscillator(),y.frequency.value=s.lfo.rate,b=n.createGain(),b.gain.value=s.lfo.depth,y.connect(b),s.lfo.target==="freq"?b.connect(l.frequency):s.lfo.target==="gain"?b.connect(o.gain):s.lfo.target==="filter"&&u&&b.connect(u.frequency),y.start(i),y.stop(i+s.duration)),o.connect(e);let x=[l,p,y,b,u,o],t=i+s.duration+d.release;setTimeout(()=>{x.forEach(a=>a?.disconnect())},(t-n.currentTime)*1e3)}getConfig(){return structuredClone(this.cfg)}setConfig(e){return Object.assign(this.cfg,e),this}getKey(e){return this.cfg[e]}setKey(e,n){return Object.assign(this.cfg[e],n),this}setFreq(e){return this.cfg.osc.freq=e,this}setWave(e){return this.cfg.osc.type=e,this}setVolume(e){return this.cfg.ampEnv.volume=e,this}setAmpEnv(e,n,i,s){return Object.assign(this.cfg.ampEnv,{attack:e,decay:n,sustain:i,release:s}),this}setPitchEnv(e,n){return Object.assign(this.cfg.pitchEnv,{amount:e,decay:n}),this}setNoiseEnabled(e){return this.cfg.noise.enabled=e,this}setNoiseLevel(e){return this.cfg.noise.level=e,this}setFilterEnabled(e){return this.cfg.filter.enabled=e,this}setFilter(e,n,i){return Object.assign(this.cfg.filter,{type:e,freq:n,Q:i,enabled:!0}),this}setLFOEnabled(e){return this.cfg.lfo.enabled=e,this}setLFO(e,n,i){return Object.assign(this.cfg.lfo,{target:e,rate:n,depth:i,enabled:!0}),this}setDuration(e){return this.cfg.duration=e,this}clone(){return new r(structuredClone(this.cfg))}},Se=new A({osc:{enabled:!0,type:"square",freq:900,detune:0},ampEnv:{attack:.002,decay:.04,sustain:0,release:.02,volume:.15},duration:.05}),Ie=new A({osc:{enabled:!0,type:"sine",freq:600,detune:0},ampEnv:{attack:.01,decay:.08,sustain:0,release:.04,volume:.12},duration:.1}),Fe=new A({osc:{enabled:!0,type:"triangle",freq:500,detune:0},pitchEnv:{amount:12,decay:.15},ampEnv:{attack:.01,decay:.12,sustain:0,release:.05,volume:.25},duration:.18}),Pe=new A({osc:{enabled:!0,type:"sawtooth",freq:1200,detune:0},pitchEnv:{amount:-24,decay:.3},ampEnv:{attack:.005,decay:.25,sustain:0,release:.05,volume:.3},duration:.35}),Me=new A({osc:{enabled:!0,type:"square",freq:180,detune:0},noise:{enabled:!0,level:.4},ampEnv:{attack:.002,decay:.15,sustain:0,release:.05,volume:.35},duration:.2}),gt=new Map([["ui_click",Se],["ui_hover",Ie],["jump",Fe],["laser",Pe],["hit",Me]]);function bt(r=12){let e=Date.now().toString(36),n=crypto.getRandomValues(new Uint8Array(r)),i=Array.from(n).map(s=>s.toString(36).padStart(2,"0")).join("");return(e+i).slice(0,r)}function we(r=12){let e=Date.now().toString(36),n=crypto.getRandomValues(new Uint8Array(4)),i=Array.from(n).map(s=>s.toString(36).padStart(2,"0")).join("");return(e+i).slice(0,r)}var be=class{peer=null;key;events={};mbAcc=0;connected=!1;constructor(){this.key=`${Ae()}_${Date.now()}`}connect(e){e&&(this.peer=e,e.peer=this,this.connected=!0,e.connected=!0),this._emit("open")}isConnected(){return this.connected&&!!this.peer}on(e,n){this.events[e]||(this.events[e]=[]),this.events[e].push(n)}off(e,n){this.events[e]&&(this.events[e]=this.events[e].filter(i=>i!==n))}_emit(e,n){this.events[e]?.forEach(i=>i(n))}send(e,n){if(!this.peer)throw new Error("No peer connected");this.peer._receive(e,n)}_receive(e,n){e?this._emit(e,n):this._emit("message",n)}close(){if(this.connected=!1,this.peer){let e=this.peer;this.peer=null,e.peer=null,e.connected=!1,e._emit("close")}this._emit("close")}getKey(){return this.key}};function Ae(){if(typeof crypto<"u"&&typeof crypto.randomUUID=="function")return crypto.randomUUID();if(typeof crypto<"u"&&typeof crypto.getRandomValues=="function"){let r=new Uint8Array(16);return crypto.getRandomValues(r),r[6]=r[6]&15|64,r[8]=r[8]&63|128,[...r].map(e=>e.toString(16).padStart(2,"0")).join("").replace(/^(.{8})(.{4})(.{4})(.{4})(.{12})$/,"$1-$2-$3-$4-$5")}return"xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx".replace(/[xy]/g,r=>{let e=Math.random()*16|0;return(r==="x"?e:e&3|8).toString(16)})}function _e(r){let e=!0;function n(){e&&(r(),requestAnimationFrame(n))}return requestAnimationFrame(n),{clear:()=>e=!1}}function Le(r,e,n,i,s){let o=Math.cos(s),d=Math.sin(s),f=[];if(o!==0){let u=(0-r)/o,l=e+u*d;u>0&&l>=0&&l<=i&&f.push({side:"left",t:u})}if(o!==0){let u=(n-r)/o,l=e+u*d;u>0&&l>=0&&l<=i&&f.push({side:"right",t:u})}if(d!==0){let u=(0-e)/d,l=r+u*o;u>0&&l>=0&&l<=n&&f.push({side:"top",t:u})}if(d!==0){let u=(i-e)/d,l=r+u*o;u>0&&l>=0&&l<=n&&f.push({side:"bottom",t:u})}return f.length===0?null:(f.sort((u,l)=>u.t-l.t),f[0])}function De(r,e){let n;switch(e){case"left":case"right":n=Math.PI-r;break;case"top":case"bottom":n=2*Math.PI-r;break}return(n%(2*Math.PI)+2*Math.PI)%(2*Math.PI)}function xt(r,e,n,i,s){let o=Le(r,e,n,i,s);return o?{...o,avoidAngle:De(s,o.side)}:null}function Ge(){return q?!1:/Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(navigator.userAgent)}var wt=Ge();function Ve({width:r,height:e,updateHz:n="frames"}){return new L.KaylaGame(r,e,n==="frames"?1/0:n)}function He(r){let e=new N(r);return new L.KaylaScene(e)}function ze(r){return new L.KaylaRenderer(r)}function $e(r,e){return{type:r,props:e}}var F;(i=>{function r(s,o){return!(s.right<o.left||s.left>o.right||s.bottom<o.top||s.top>o.bottom)}i.rawCollision=r;function e(s,o,d){let f=o*Math.PI/180,u=Math.cos(f),l=Math.sin(f),p=1/0;return u>0&&(p=Math.min(p,(d.right-s.x)/u)),u<0&&(p=Math.min(p,(d.left-s.x)/u)),l>0&&(p=Math.min(p,(d.bottom-s.y)/l)),l<0&&(p=Math.min(p,(d.top-s.y)/l)),M.from(o).scale(p)}i.getCurrToBound=e;function n(s){let{left:o,right:d,top:f,bottom:u,width:l,height:p,x:y=0,y:b=0}=s;if(l===null||p===null)throw new Error("width and height are required");let x,t;if(o!=null&&d!=null){if(Math.abs(d-o-l)>1e-6)throw new Error("left, right, and width mismatch");x=o}else y!=null?x=y-l/2:o!=null?x=o:d!=null?x=d-l:x=0;if(f!=null&&u!=null){if(Math.abs(u-f-p)>1e-6)throw new Error("top, bottom, and height mismatch");t=f}else b!=null?t=b-p/2:f!=null?t=f:u!=null?t=u-p:t=0;return{left:x,right:x+l,top:t,bottom:t+p,width:l,height:p,x:x+l/2,y:t+p/2}}i.createRawRect=n})(F||={});var L;(b=>{class r extends O{#e;#t;constructor(t,a,h){super(t,a,h),this.#e=new Set,this.#t=!1}delay(t){return this.ticker.createTimeout(t)}get started(){return this.#t}start(){if(!this.#t){for(let t of this.#e)t.start();this.#t=!0,super.start()}}stop(){if(this.#t){for(let t of this.#e)t.stop();this.#t=!1,super.stop()}}addRenderer(t){this.#e.has(t)||(this.#e.add(t),this.#t&&t.start(),t.game=this)}get mainRenderer(){return[...this.#e].at(0)}getRenderers(){return[...this.#e]}deleteRenderer(t){this.#e.has(t)&&(this.#e.delete(t),this.#t&&t.stop(),delete t.game)}}b.KaylaGame=r;class e extends U{game;pointerX;pointerY;pointerEvents;constructor(t){super(t),this.useDraw=this.useDraw.bind(this),this.on("draw",a=>{if(this.game)for(let h of this.game.scenes.values())h.handleDraw(a)}),this.pointerX=0,this.pointerY=0,this.pointerEvents=new K,this.pointerPosUpdater=this.pointerPosUpdater.bind(this),this.onPointerDown=this.onPointerDown.bind(this)}pointerPosUpdater(t){this.pointerX=t.clientX,this.pointerY=t.clientY}onPointerDown(t){this.pointerPosUpdater(t);let a=e.getClickType(t);if(a!=="invalid"){t.preventDefault();let h=this.getMousePos();this.pointerEvents.emit("down",h,a)}}static getClickType(t){switch(t.button){case 0:return"left";case 1:return"middle";case 2:return"right";default:return"invalid"}}listenPointerUpdates(){this.canvas.addEventListener("pointermove",this.pointerPosUpdater),this.canvas.addEventListener("pointerdown",this.onPointerDown)}unlistenPointerUpdates(){this.canvas.removeEventListener("pointermove",this.pointerPosUpdater),this.canvas.removeEventListener("pointerdown",this.onPointerDown)}pointerPosToWorldPos(t,a){let h=this.canvas.getBoundingClientRect(),c=(t-h.left)/h.width,g=(a-h.top)/h.height,w=c*this.viewportWidth*this.cameraWidth/h.width,C=g*this.viewportHeight*this.cameraHeight/h.height;return new M(w,C)}getMousePos(){return this.pointerPosToWorldPos(this.pointerX,this.pointerY)}useDraw(t){let a=h=>{t(h,new i)};return this.on("draw",a),()=>{this.off("draw",a)}}attachTo(t){t.addRenderer(this),this.game=t}detach(){this.game&&this.game.deleteRenderer(this)}}b.KaylaRenderer=e;class n{current;saves;constructor(){this.saves=[]}useTick(t){if(!this.current)throw new Error("Hook 'useTick' must be executed in the top level scope of a component.");this.current.onTick[this.current.useStepCallIndex]=t,this.current.useStepCallIndex++}usePaint(t){if(!this.current)throw new Error("Hook 'usePaint' must be executed in the top level scope of a component.");this.current.onPaint[this.current.useDrawCallIndex]=t,this.current.useDrawCallIndex++}useEntity(){if(!this.current)throw new Error("Hook 'useEntity' must be executed in the top level scope of a component.");return oe(ue)}useSelf(t){if(!this.current)throw new Error("Hook 'useSelf' must be executed in the top level scope of a component.");let a=oe(null);return(a.current===null||a.current===void 0)&&(a.current=t()),a.current}useInitialization(t){if(!this.current)throw new Error("Hook 'useInitialization' must be executed in the top level scope of a component.");let a=this.current;a.onInit=t}useRect(){if(!this.current)throw new Error("Hook 'useRect' must be executed in the top level scope of a component.");return _(()=>new b.KaylaInternalRect(this.current))}useFiber(){if(!this.current)throw new Error("Hook 'useFiber' must be executed in the top level scope of a component.");return _(()=>this.current)}useFiberControl(){if(!this.current)throw new Error("Hook 'useFiberControl' must be executed in the top level scope of a component.");let t=this.current;return _(()=>({refresh:()=>t.refresh(),get childrenCount(){return t.lastChildren.length},setMaxChildren:a=>{t.setMaxChildren(a)},getMaxChildren:()=>t.getMaxChildren(),get maxSafeChildren(){return t.maxSafeChildren},get key(){return t.key},get getChildrenEntities(){return t.getChildrenEntities.bind(t)},get getEntityChain(){return t.getEntityChain.bind(t)},get getFiberChain(){return t.getFiberChain.bind(t)}}))}useCurrentTicker(){if(!this.current)throw new Error("Hook 'useCurrentTicker' must be executed in the top level scope of a component.");return this.current.getAttachedGame().ticker}useCurrentRenderer(){if(!this.current)throw new Error("Hook 'useCurrentRenderer' must be executed in the top level scope of a component.");return this.current.getAttachedGame().mainRenderer}useCurrentGame(){if(!this.current)throw new Error("Hook 'useCurrentGame' must be executed in the top level scope of a component.");return this.current.getAttachedGame()}useCurrentScene(){if(!this.current)throw new Error("Hook 'useCurrentScene' must be executed in the top level scope of a component.");return this.current.scene}useState(t,{alwaysRecall:a=!1}={}){if(!this.current)throw new Error("Hook 'useState' must be executed in the top level scope of a component.");let c=this.current.state[this.current.useStateCallIndex]??new s(this.current,t,{alwaysRecall:a});return this.current.state[this.current.useStateCallIndex]=c,this.current.useStateCallIndex++,c}useShouldRefresh(t){let a=this.current;if(!a)throw new Error("useShouldRefresh must be called inside a component");a.watchedDeps&&console.warn("useShouldRefresh called multiple times \u2014 using the last call"),a.watchedDeps=t}useRef(t){if(!this.current)throw new Error("Hook 'useRef' must be executed in the top level scope of a component.");let h=this.current.refs[this.current.useRefCallIndex]??d(t??null);return this.current.refs[this.current.useRefCallIndex]=h,this.current.useRefCallIndex++,h}useEffect(t){if(!this.current)throw new Error("Hook 'useEffect' must be executed in the top level scope of a component.");this.current.onEffect[this.current.useEffectCallIndex]=t,this.current.useEffectCallIndex++}useExports(t,a){if(!this.current)throw new Error("Hook 'useExports' must be executed in the top level scope of a component.");this.current.onExport=a}useGlobalClick(t){if(!this.current)throw new Error("Hook 'useGlobalClick' must be executed in the top level scope of a component.");this.current.onGlobalClick[this.current.useGlobalClickCallIndex]=t,this.current.useGlobalClickCallIndex++}useClick(t){if(!this.current)throw new Error("Hook 'useClick' must be executed in the top level scope of a component.");let a=this.current;ve((h,c)=>{let g=a.entity;if(!g)return;let w=g.getRawRect(),C=F.createRawRect({x:h.x,y:h.y,width:3,height:3});F.rawCollision(w,C)&&t(h,c)})}useContext(t){if(!this.current)throw new Error("Hook 'useContext' must be executed in the top level scope of a component.");return this.current.findContextValueFromInst(t)}save(){this.saves.push({current:this.current})}restore(){let t=this.saves.pop();if(!t)throw new Error("Cannot restore without saving.");this.current=t.current}logLevel="warn";logger={debug:(...t)=>{this.logLevel==="debug"&&console.debug(...t)},info:(...t)=>{["info","warn","debug"].includes(this.logLevel)&&console.info(...t)},warn:(...t)=>{["warn","debug"].includes(this.logLevel)&&console.warn(...t)},error:(...t)=>console.error(...t),withFiber:(t,a,h,...c)=>{let g=t?.fc?.name||"anonymous",w=t?.key?` key=${t.key}`:"";this.logger[a](`${h} <${g}${w}>`,...c)}}}b.GlobalKayla=n;class i{preventDefault(){this.#e=!0}#e=!1;isPrevented(){return this.#e}}b.KaylaEvent=i;class s{#e;#t;#n;alwaysRecall;constructor(t,a,{alwaysRecall:h=!1}={}){this.#t=t,this.#e=a??void 0,this.#n=Date.now(),this.alwaysRecall=h}get(){return this.#e}*[Symbol.iterator](){throw new Error(`Hey! KaylaState is NOT an array / iterable like useState in React.
1
+ "use strict";var ge=Object.defineProperty;var lt=Object.getOwnPropertyDescriptor;var ht=Object.getOwnPropertyNames;var ct=Object.prototype.hasOwnProperty;var xe=(r,e)=>{for(var n in e)ge(r,n,{get:e[n],enumerable:!0})},dt=(r,e,n,i)=>{if(e&&typeof e=="object"||typeof e=="function")for(let s of ht(e))!ct.call(r,s)&&s!==n&&ge(r,s,{get:()=>e[s],enumerable:!(i=lt(e,s))||i.enumerable});return r};var ft=r=>dt(ge({},"__esModule",{value:!0}),r);var Et={};xe(Et,{Kayla:()=>pe,KaylaContext:()=>W,KaylaFragment:()=>nt,KaylaInternals:()=>V,KaylaRect:()=>F,LEA:()=>ue,UI:()=>ot,createContext:()=>Oe,createElement:()=>Ne,createGame:()=>ze,createReassignableObject:()=>it,createRenderer:()=>$e,createScene:()=>Ue,createUseHook:()=>at,self:()=>he,setLogLevel:()=>st,useClick:()=>We,useContext:()=>tt,useCurrentGame:()=>Qe,useCurrentRenderer:()=>Je,useCurrentScene:()=>Ze,useCurrentTicker:()=>et,useDisposableRef:()=>rt,useEffect:()=>ce,useEntity:()=>je,useExports:()=>J,useFiber:()=>Ee,useFiberControl:()=>de,useGlobalClick:()=>Ce,useInitialization:()=>Y,useNextStack:()=>fe,usePaint:()=>Q,useRect:()=>j,useRef:()=>le,useSelf:()=>L,useShouldRefresh:()=>qe,useState:()=>Xe,useTick:()=>Ye,useViewportEffect:()=>Be});module.exports=ft(Et);var pe={};xe(pe,{KaylaContext:()=>W,KaylaFragment:()=>nt,KaylaInternals:()=>V,KaylaRect:()=>F,createContext:()=>Oe,createElement:()=>Ne,createGame:()=>ze,createReassignableObject:()=>it,createRenderer:()=>$e,createScene:()=>Ue,createUseHook:()=>at,self:()=>he,setLogLevel:()=>st,useClick:()=>We,useContext:()=>tt,useCurrentGame:()=>Qe,useCurrentRenderer:()=>Je,useCurrentScene:()=>Ze,useCurrentTicker:()=>et,useDisposableRef:()=>rt,useEffect:()=>ce,useEntity:()=>je,useExports:()=>J,useFiber:()=>Ee,useFiberControl:()=>de,useGlobalClick:()=>Ce,useInitialization:()=>Y,useNextStack:()=>fe,usePaint:()=>Q,useRect:()=>j,useRef:()=>le,useSelf:()=>L,useShouldRefresh:()=>qe,useState:()=>Xe,useTick:()=>Ye,useViewportEffect:()=>Be});var ue={};xe(ue,{DeltaTweenII:()=>se,ENVIRONMENT:()=>ve,GEmitterMemory:()=>we,LeaEntityII:()=>z,LeaEventEmitter:()=>T,LeaGameII:()=>X,LeaRendererII:()=>N,LeaSceneII:()=>O,LeaSerializers:()=>ke,LeaTickerII:()=>ie,LeaTimeout:()=>ae,LeaUtilsII:()=>R,LiaAudio:()=>U,LiaAudioSrc:()=>H,LiaOscSFX:()=>_,LiaSFXMap:()=>xt,NOTE_NAMES:()=>Se,RectLeaEntity:()=>q,Vector2:()=>A,colToRGBA:()=>mt,defaultSFXConfig:()=>Ie,editRGBA:()=>yt,generateUUID:()=>Le,getAvoidAngle:()=>Ge,getEnvironment:()=>Te,getNormalizedColor:()=>pt,getRayHit:()=>De,isInitiallyMobile:()=>Ct,isMobile:()=>He,isNode:()=>B,isNote:()=>gt,isWeb:()=>C,parseFillStyle:()=>Ke,raycastAvoid:()=>vt,scaleCoord:()=>bt,setAnimInterval:()=>Ve,sfxHit:()=>_e,sfxJump:()=>Me,sfxLaser:()=>Ae,sfxUIClick:()=>Fe,sfxUIHover:()=>Pe,shortUID:()=>wt,tinyUID:()=>oe});var T=class{#e=new Map;constructor(){this.#e=new Map}on(e,n){let i=this.#e.get(e)||[];return i.push(n),this.#e.set(e,i),this}once(e,n){let i=(...s)=>{this.off(e,i),n(...s)};return this.on(e,i),this}off(e,n){let i=this.#e.get(e);if(!i)return this;let s=i.indexOf(n);return s>=0&&i.splice(s,1),this}emit(e,...n){let i=this.#e.get(e);if(!i||i.length===0){if(e==="error")throw n[0];return!1}return i.slice().forEach(s=>s(...n)),!0}removeAllListeners(e){return e?this.#e.delete(e):this.#e.clear(),this}listenerCount(e){return this.#e.get(e)?.length??0}},N=class extends T{canvas;ctx;running;_rafId;_fps;_frameCount;_fpsTimer;_lastFrameTime;constructor(e,{viewportWidth:n,viewportHeight:i,cameraWidth:s,cameraHeight:o}={}){if(!C)throw new Error("Web-Only");super(),this.canvas=e,this.ctx=e.getContext("2d"),this.automatic=!0,this.#e=n??e.width,this.#t=i??e.height,this.#n=s??e.width,this.#r=o??e.height,this.running=!1,this._rafId=null,this._loop=this._loop.bind(this),this.updateCanvasResolution(),this._fps=60,this._frameCount=0,this._fpsTimer=0}automatic;retransform(){this.ctx.setTransform(1,0,0,1,0,0);let e=this.#n/this.#e,n=this.#r/this.#t;this.ctx.translate(this.#n/2,this.#r/2),this.ctx.scale(e,n),this.ctx.translate(-this.#e/2,-this.#t/2)}#e=0;#t=0;#n=0;#r=0;get viewportWidth(){return this.#e}set viewportWidth(e){this.#e=e,this.retransform(),this.emitViewportUpdate()}get width(){return this.#e}get height(){return this.#t}get centerX(){return this.#e/2}get centerY(){return this.#t/2}get left(){return 0}get top(){return 0}get right(){return this.#e}get bottom(){return this.#t}get viewportHeight(){return this.#t}set viewportHeight(e){this.#t=e,this.retransform(),this.emitViewportUpdate()}get cameraWidth(){return this.#n}set cameraWidth(e){this.#n=e,this.updateCanvasResolution(),this.retransform()}get cameraHeight(){return this.#r}set cameraHeight(e){this.#r=e,this.updateCanvasResolution(),this.retransform()}updateCanvasResolution(){this.canvas.width=this.#n,this.canvas.height=this.#r}emitViewportUpdate(){this.emit("viewport_update",{width:this.viewportWidth,height:this.viewportHeight})}applyTransform(){this.retransform()}get FPS(){return this._fps}_loop(){this.automatic&&this.update(),this._rafId=requestAnimationFrame(this._loop)}update(){if(!this.running||!C)return;let e=performance.now(),n=(e-(this._lastFrameTime??e))/1e3;this._lastFrameTime=e,this._frameCount++,this._fpsTimer+=n,this._fpsTimer>=1&&(this._fps=Math.round(this._frameCount/this._fpsTimer),this._frameCount=0,this._fpsTimer=0),this.ctx.clearRect(0,0,this.#n,this.#r),this.emit("draw",this.ctx)}start(){if(!this.running){if(!C||typeof globalThis.requestAnimationFrame>"u")throw new Error("Raf is not supported");this.running=!0,this._rafId=requestAnimationFrame(this._loop)}}stop(){if(!C||typeof globalThis.requestAnimationFrame>"u")throw new Error("Raf is not supported");this.running=!1,this._rafId!==null&&(cancelAnimationFrame(this._rafId),this._rafId=null)}},ie=class extends T{setNow(e){this.#e=e}#e=0;__intervalId=null;__lastTime=0;constructor(e=16){super(),this.#t=e,this.speedHackDT=1}speedHackDT;get isRaf(){return this.tickInterval===1/0}#t=15;get tickInterval(){return this.#t}set tickInterval(e){this.#t=e,this.__intervalId&&(this.stop(),this.start())}now(){return this.#e}__tick(){let e=performance.now(),n=(e-this.__lastTime)/1e3*this.speedHackDT;this.__lastTime=e,!(C&&typeof this.__intervalId=="function"&&document.hidden)&&(this.#e+=n*1e3,this.emit("tick",n))}createTimeout(e){return new ae(e,this)}createTween(e,n=()=>{}){let i=new se(e),s=(o=0)=>{if(i.finished){this.off("tick",s);return}i.update(o)};return i.on("finish",()=>{this.off("tick",s)}),i.on("delta",o=>{n(o)}),this.on("tick",s),i}start(){this.__intervalId===null&&(this.__lastTime=performance.now(),this.__intervalId=C&&!isFinite(this.tickInterval)?Ve(()=>this.__tick()).clear:setInterval(()=>this.__tick(),this.tickInterval))}stop(){this.__intervalId!==null&&(typeof this.__intervalId=="function"?this.__intervalId():clearInterval(this.__intervalId)),this.__intervalId=null}getSineMod(e,n=0){return .5+.5*Math.sin((this.now()%e/e+n)*2*Math.PI)}},ke;(t=>{function r(a){return a===!0?1:0}t.booleanExport=r;function e(a){return a===0?!1:a===1}t.booleanImport=e;function n(a){return`${a.x}|${a.y}`}t.vec2Export=n;function i(a){let[l,f]=a.split("|"),y=parseFloat(l),w=parseFloat(f);if(isNaN(y)||isNaN(w))throw new Error(`Invalid Vector2 string: ${a}`);return new A(y,w)}t.vec2Import=i,t.booleanMap={mapExport:r,mapImport:e};function o(a){return l=>Number(l.toFixed(a))}t.createRounder=o;function c(a=10){return{mapExport(l){return Math.round(l/a)},mapImport(l){return l*a}}}t.createLowPrecision=c;function d(a){return Math.round(a)}t.lightWeightRounder=d;function u(a=100){return{mapExport(l){return Math.round(l*a)},mapImport(l){return l/a}}}t.createPercent=u;function h(a){let l=new Map(Object.entries(a));return{mapExport:f=>l.get(f)??null,mapImport:f=>Array.from(l.entries()).find(([y,w])=>w===f)?.[0]??null}}t.createLookup=h;function p(a){let l=a*(180/Math.PI);return Math.round((l%360+360)%360)}t.radToDeg=p;function b(a){return a*(Math.PI/180)}t.degToRad=b,t.angleRadToDeg={mapExport:p,mapImport:b};function x(a=10){let l=c(a);return{mapExport(f){return l.mapExport(p(f))},mapImport(f){return l.mapImport(b(f))}}}t.createLowPrecisionRadToDeg=x})(ke||={});var z=class r extends T{name="";scaleRotate=0;scale=1;constructor(e,n=0,i=0){super(),this.autoTranslate=!1,this.name=e,this.z=0,this.___pos=new A(n,i),this.nonSerializableProperties=[],this.nonSerializableProperties.push("___pos","autoTranslate","arraySerializeMap"),this.forceSerializableProperties=[],this.forceSerializableProperties.push("x","y")}arraySerializeMap;autoTranslate;z;___pos;nonSerializableProperties;forceSerializableProperties;get pos(){return this.___pos}get x(){return this.pos.x}get y(){return this.pos.y}set x(e){this.pos.x=e}set y(e){this.pos.y=e}handleUpdate(e){if(this.update)try{this.emit("update",e),this.update(e)}catch(n){this.emit("error",n)}}handleDraw(e){if(!(B||!this.draw)){e.save(),this.autoTranslate&&e.translate(this.x,this.y);try{this.emit("draw",e),this.draw(e)}catch(n){this.emit("error",n)}e.restore()}}serialize(){if(Array.isArray(this.arraySerializeMap))return this.arraySerializeMap.map(([s,{mapExport:o}])=>{let c=Reflect.get(this,s);return o?o(c):c});let e=["_events","_eventsCount","_maxListeners","nonSerializableProperties","forceSerializableProperties"],n=[...Reflect.ownKeys(this),...this.forceSerializableProperties].filter(s=>!this.nonSerializableProperties.includes(s)&&!e.includes(s.toString())),i=Object.fromEntries(n.map(s=>{let o=Reflect.get(this,s);if(B&&typeof o=="number"){let c=o.toString().split("."),u=(c[1]?c[1].length:0)>2?Number(o.toFixed(2)):o;return[s,u]}return[s,o]}));return JSON.parse(JSON.stringify(i))}toLocal(e){return e.subtract(this.pos)}toWorld(e){return e.add(this.pos)}deserializeArray(e){return r.deserializeArray(this.arraySerializeMap,e)}static deserializeArray(e,n){if(!e||!Array.isArray(n))return n;let i={};for(let s=0;s<n.length;s++){let o=e[s];if(!o)break;let[c,{mapImport:d}]=o,u=n[s];if(d&&(u=d(u)),typeof c!="string")break;try{Reflect.set(i,c,u)}catch(h){console.error(h)}}return i}},O=class extends T{name="";entities=new Map;paused=!0;constructor(e){super(),this.name=e}handleUpdate(e){if(!this.paused){this.emit("update",e);for(let n of this.entities.values())n.handleUpdate(e)}}handleDraw(e){if(!B&&!this.paused){this.emit("draw",e);for(let n of[...this.entities.values()].sort((i,s)=>i.z-s.z))n.handleDraw(e)}}addEntity(e){if(!(e instanceof z))throw new Error("invalid entity");if(!e.name)throw new Error("Entity must have a name.");this.entities.set(e.name,e)}removeEntity(e){if(!(e instanceof z))throw new Error("invalid entity");this.entities.delete(e.name)}getEntity(e){return this.entities.get(e)}},X=class{scenes;ticker;get centerX(){return this.width/2}get centerY(){return this.height/2}get left(){return 0}get top(){return 0}get right(){return this.width}get bottom(){return this.height}width;height;constructor(e,n,i=16){this.ticker=new ie(i),this.scenes=new Map,this.width=e,this.height=n,this.ticker.on("tick",s=>{for(let o of this.scenes.values())o.paused||o.handleUpdate(s)})}addScene(e){if(!e.name)throw new Error("Scene must have a name.");e.paused=!1,this.scenes.set(e.name,e)}removeScene(e){e&&(e.paused=!0),this.scenes.delete(e.name)}now(){return this.ticker.now()}start(){this.ticker.start()}stop(){this.ticker.stop()}},R={lerp(r,e,n){return r+(e-r)*n},clamp(r,e,n){return Math.min(n,Math.max(e,r))},clamp01(r){return Math.min(1,Math.max(0,r))},easeLinear(r){return r},easeInQuad(r){return r*r},easeOutQuad(r){return 1-(1-r)*(1-r)},easeInOutQuad(r){return r<.5?2*r*r:1-Math.pow(-2*r+2,2)/2},easeInSine(r){return 1-Math.cos(r*Math.PI/2)},easeOutSine(r){return Math.sin(r*Math.PI/2)},easeInOutSine(r){return-(Math.cos(Math.PI*r)-1)/2},easeInExpo(r){return r===0?0:Math.pow(2,10*r-10)},easeOutExpo(r){return r===1?1:1-Math.pow(2,-10*r)},easeInOutExpo(r){return r===0?0:r===1?1:r<.5?Math.pow(2,20*r-10)/2:(2-Math.pow(2,-20*r+10))/2},smoothstep(r){return r=R.clamp(r,0,1),r*r*(3-2*r)},randomLerp(r,e){return R.lerp(r,e,Math.random())},randomInt(r,e){return Math.floor(Math.random()*(e-r+1))+r},randomArrayValue(r){return r[R.randomInt(0,r.length-1)]},createBezier(r,e,n,i){function s(d,u,h,p,b){let g=1-d;return g*g*g*u+3*g*g*d*h+3*g*d*d*p+d*d*d*b}function o(d,u,h,p,b){let g=1-d;return 3*g*g*(h-u)+6*g*d*(p-h)+3*d*d*(b-p)}function c(d){let u=d;for(let h=0;h<6;h++){let p=s(u,0,r,n,1),b=o(u,0,r,n,1);if(b===0)break;u-=(p-d)/b}return R.clamp(u,0,1)}return function(u){u=R.clamp(u,0,1);let h=c(u);return s(h,0,e,i,1)}},lengthSquared(...r){return r.reduce((e,n)=>e+n*n,0)},normalizeRad(r){let e=2*Math.PI;return r=r%e,r<0&&(r+=e),r},angleInvertY(r){return R.normalizeRad(-r)},degToRadFlipY(r){return R.angleInvertY(r*Math.PI/180)},minimalAngularDirection(r,e){r=R.normalizeRad(r),e=R.normalizeRad(e);let n=R.normalizeRad(e-r),i=R.normalizeRad(r-e);return n<=i?1:-1}},se=class extends T{constructor({delta:e,ms:n,easing:i}){super(),this.delta=e,this.duration=n,this.elapsed=0,this.easing=i??(s=>s),this.lastValue=0,this.finished=!1}delta;duration;elapsed;lastValue;finished;easing;update(e){this.elapsed+=e*1e3;let n=R.clamp(this.elapsed/this.duration,0,1),i=this.easing(n),s=this.delta*i,o=s-this.lastValue;this.lastValue=s,this.emit("delta",o),n>=1&&(this.finished=!0,this.emit("finish",void 0))}},q=class extends z{constructor(e,n=0,i=0,s=50,o=50){super(e,n,i),this.width=s,this.height=o}width;height;get left(){return this.x-this.width/2}set left(e){this.x=e+this.width/2}get right(){return this.x+this.width/2}set right(e){this.x=e-this.width/2}get top(){return this.y-this.height/2}set top(e){this.y=e+this.height/2}get bottom(){return this.y+this.height/2}set bottom(e){this.y=e-this.height/2}get lx(){return 0}get ly(){return 0}get lleft(){return-this.width/2}get lright(){return this.width/2}get ltop(){return-this.height/2}get lbottom(){return this.height/2}isCollidingWith(e){return!(this.right<e.left||this.left>e.right||this.bottom<e.top||this.top>e.bottom)}color="rgba(0, 0, 255, 0.3)";draw(e){e.translate(this.x,this.y),e.rotate(this.scaleRotate),e.fillStyle=this.color,e.fillRect(-this.width/2,-this.height/2,this.width,this.height)}},ae=class extends T{duration;ticker;elapsed;finished;_resolve;promise;_timeoutId;constructor(e,n=null){super(),this.duration=e,this.ticker=n,this.elapsed=0,this.finished=!1,this._resolve=null,this.promise=new Promise(i=>this._resolve=i),this.update=this.update.bind(this),this.ticker&&this.ticker.on("tick",this.update)}update(e=0){this.finished||(this.elapsed+=e*1e3,this.elapsed>=this.duration&&this.finish())}finish(){this.finished||(this.finished=!0,this.emit("finish",void 0),this._resolve&&this._resolve(),this.ticker&&this.ticker.off("tick",this.update))}start(){return this.ticker||(this._timeoutId=setTimeout(()=>this.finish(),this.duration)),this}cancel(){this.finished||(this.finished=!0,!this.ticker&&this._timeoutId!=null&&clearTimeout(this._timeoutId),this.ticker&&this.ticker.off("tick",this.update))}then(e,n){return this.promise.then(e,n)}after(e,n){return this.promise.then(e,n)}},A=class r{constructor(e=0,n=0){this.x=e,this.y=n}x;y;toJSON(){return{x:this.x,y:this.y,vec2:!0}}static isVec2(e){return e&&typeof e=="object"&&"x"in e&&"y"in e&&e.vec2===!0}static fromSerialized(e){return this.isVec2(e)?new this(e.x,e.y):null}rotate(e){let n=Math.cos(e),i=Math.sin(e);return new r(this.x*n-this.y*i,this.x*i+this.y*n)}static from(e){return new r(Math.cos(e),Math.sin(e))}isEmpty(){return Math.abs(this.x)<.01&&Math.abs(this.y)<.01}get angle(){return Math.atan2(this.y,this.x)}angleTo(e){return Math.atan2(e.y-this.y,e.x-this.x)}get length(){return Math.hypot(this.x,this.y)}get lengthSquared(){return this.x*this.x+this.y*this.y}normalized(){let e=this.length;return e===0?new r(0,0):new r(this.x/e,this.y/e)}consume(e){let n=this.length;n<=e?(this.x=0,this.y=0):this.overwite(this.scale((n-e)/n))}project(e){return e.scale(this.dotNormalized(e))}reflect(e){let n=this.dot(e);return this.subtract(e.scale(2*n))}dotNormalized(e){let n=this.normalized(),i=e.normalized();return n.x*i.x+n.y*i.y}lengthSquaredTo(e){let n=this.x-e.x,i=this.y-e.y;return n*n+i*i}dot(e){return this.x*e.x+this.y*e.y}distanceTo(e){return Math.hypot(this.x-e.x,this.y-e.y)}distanceToCheap(e){let n=this.x-e.x,i=this.y-e.y;return n*n+i*i}directionTo(e){return new r(e.x-this.x,e.y-this.y).normalized()}add(e){return new r(this.x+e.x,this.y+e.y)}addRaw(e){return new r(this.x+e,this.y+e)}overwite(e){this.x=e.x,this.y=e.y}subtract(e){return new r(this.x-e.x,this.y-e.y)}scale(e){return new r(this.x*e,this.y*e)}toString(){return`Vector2(${this.x}, ${this.y})`}clone(){return new r(this.x,this.y)}};function pt(r){let e=/^rgba?\(([^)]+)\)$/,n=r.match(e);if(n){let[i,s,o,c=1]=n[1].split(",").map(d=>parseFloat(d));return{r:Math.max(0,Math.min(255,Math.floor(i))),g:Math.max(0,Math.min(255,Math.floor(s))),b:Math.max(0,Math.min(255,Math.floor(o))),a:Math.max(0,Math.min(1,Math.floor(c*255)/255))}}return Ke(r)}function mt(r){return`rgba(${r.r}, ${r.g}, ${r.b}, ${r.a})`}function Ke(r){if(r=r.trim().toLowerCase(),r[0]==="#"){let n,i,s;if(r.length===7)n=parseInt(r.slice(1,3),16),i=parseInt(r.slice(3,5),16),s=parseInt(r.slice(5,7),16);else if(r.length===4)n=parseInt(r[1]+r[1],16),i=parseInt(r[2]+r[2],16),s=parseInt(r[3]+r[3],16);else throw new Error("Invalid hex color");return{r:n,g:i,b:s,a:1}}let e=r.match(/^rgba?\s*\(\s*(\d+)[, ]\s*(\d+)[, ]\s*(\d+)(?:[, ]\s*([\d.]+))?\s*\)$/);if(e)return{r:parseInt(e[1]),g:parseInt(e[2]),b:parseInt(e[3]),a:e[4]!==void 0?parseFloat(e[4]):1};throw new Error("Unsupported fillStyle format")}function yt(r,{r:e,g:n,b:i,a:s}={}){let[o,c,d,u,h]=r.match(/rgba?\((\d+),\s*(\d+),\s*(\d+),?\s*([\d.]*)\)?/)||[];return`rgba(${e??c}, ${n??d}, ${i??u}, ${s??(h||1)})`}function bt(r,e,n){return n+(r-n)*e}function Te(){return typeof process<"u"&&process.release?.name==="node"?"node":typeof window<"u"||typeof self<"u"?"web":"unknown"}var ve=Te(),B=ve==="node",C=ve==="web",U=class r{static unlock(){C&&this.audioCtx.state!=="running"&&this.audioCtx.resume()}static audioCtx=C?new AudioContext:null;static masterGain=C?this.audioCtx.createGain():null;static musicGain=C?this.audioCtx.createGain():null;static sfxGain=C?this.audioCtx.createGain():null;static{C&&(this.masterGain.gain.value=1,this.musicGain.gain.value=1,this.sfxGain.gain.value=1,this.sfxGain.connect(this.masterGain),this.musicGain.connect(this.masterGain),this.masterGain.connect(this.audioCtx.destination))}static get SFX_VOLUME(){return this.sfxGain.gain.value}static get MUSIC_VOLUME(){return this.musicGain.gain.value}static get VOLUME(){return this.masterGain.gain.value}static set SFX_VOLUME(e){this.sfxGain.gain.value=e}static set MUSIC_VOLUME(e){this.musicGain.gain.value=e}static set VOLUME(e){this.masterGain.gain.value=e}static noteToHz(e){return this.tuningFreq*Math.pow(2,(e-9)/12)}static tuningFreq=440;static audioBufferCache=new Map;static loops=new Map;static sfsx=new Map;static loopIdCounter=0;static CACHE_NAME="lia-audio-cache-v1";static async preLoad(e){if(this.audioBufferCache.has(e))return this.audioBufferCache.get(e);let n=r.CACHE_NAME,i,s;if(typeof caches<"u"&&(s=await caches.open(n),i=await s.match(e)),!i){if(i=await fetch(e),!i.ok)throw new Error(`Failed to fetch ${e}`);s&&await s.put(e,i.clone())}let o=await i.arrayBuffer(),c=await this.audioCtx.decodeAudioData(o);return this.audioBufferCache.set(e,c),c}static async getOnlyDownloadedCache(e){let n=r.CACHE_NAME;return await(await caches.open(n)).match(e)}static getCached(e){return this.audioBufferCache.get(e)||null}static async playSound(e,n=.2,i=1,s=!0){try{this.sfsx.has(e)&&this.sfsx.get(e).source.stop(),this.audioBufferCache.has(e)||await this.preLoad(e);let o=this.getCached(e);if(!o)return;let c=new H(o);c.buffer=o;let d=1-.12,u=1+.12;c.playbackRate=i??d+Math.random()*(u-d);let h=this.audioCtx.createGain();h.gain.value=n,c.tempGain=h,c.connect(h),h.connect(this.sfxGain),c.onended=()=>{c.disconnect(),h.disconnect()},c.start(),s&&this.sfsx.set(e,{source:c,gain:h})}catch(o){console.error(o)}}static async playLoop(e,n=1,{loopStart:i=0,loopEnd:s=null,exclusive:o=!0,skipMS:c=0}={}){if(o)for(let b of this.loops.keys())this.stopLoop(b);this.audioBufferCache.has(e)||await this.preLoad(e);let d=this.getCached(e);if(!d)return;let u=new H(d);u.buffer=d,u.loop=!0,typeof i=="number"&&(u.loopStart=i),typeof s=="number"&&(u.loopEnd=s);let h=this.audioCtx.createGain();h.gain.value=n,u.tempGain=h,u.playbackRate=1,u.onended=()=>{u.disconnect(),h.disconnect()},u.connect(h),h.connect(this.musicGain),u.start(0,c/1e3);let p=++this.loopIdCounter;return this.loops.set(p,{source:u,gain:h}),p}static stopLoop(e){let n=this.loops.get(e);n&&(n.source.stop(),n.source.notIndependent||(n.source.disconnect(),n.gain.disconnect()),this.loops.delete(e))}static async createLiaSource(e,{volume:n=1,speed:i=1,loop:s=!1,loopStart:o=0,loopEnd:c=null,isMusic:d=!1,gain:u=null}={}){try{this.audioBufferCache.has(e)||await this.preLoad(e);let h=this.getCached(e);if(!h)return null;let p=new H(h);p.loop=s,p.loopStart=o,p.loopEnd=typeof c=="number"?c:h.duration,p.playbackRate=i;let b=this.audioCtx.createGain();return b.gain.value=n,p.connect(b),p.tempGain=b,b.connect(u||(d?this.musicGain:this.sfxGain)),p.onended=()=>{p.disconnect(),b.disconnect()},p}catch(h){return console.error("Failed to create LiaAudioSrc:",h),null}}},Se=["C","C#","D","D#","E","F","F#","G","G#","A","A#","B"];function gt(r){return Se.includes(r)}var H=class{numberOfInputs;numberOfOutputs;constructor(e,n=U.audioCtx){this.context=n,this.buffer=e,this.source=null,this.startTime=0,this.pauseTime=0,this.playbackRate=1,this.isPlaying=!1,this.loop=!1,this.output=C?n.createGain():null,this.output.gain.value=1,this.channelCount=2,this.channelCountMode="max",this.channelInterpretation="speakers",this.numberOfInputs=0,this.numberOfOutputs=1,this.onended=null}channelCount;channelCountMode;channelInterpretation;onended;source;buffer;context;_createSource(){this.source&&(this.source.onended=null);let e=this.context.createBufferSource();return e.buffer=this.buffer,e.playbackRate.value=this.playbackRate,e.loop=this.loop,e.loopStart=this.loopStart,e.loopEnd=this.loopEnd>0?this.loopEnd:this.buffer.duration,e.connect(this.output),this.source=e,e.onended=()=>{this.source===e&&(this.isPlaying&&!this.loop&&(this.isPlaying=!1,this.pauseTime=0),typeof this.onended=="function"&&this.onended())},e}play({fadeIn:e=0,offset:n=null}={}){let i=n!==null?n:this.pauseTime;if(this.source){this.source.onended=null;try{this.source.stop()}catch{}}this.source=this._createSource(),this.startTime=this.context.currentTime-i/this.playbackRate,this.source.start(0,i),e>0?(this.output.gain.setValueAtTime(0,this.context.currentTime),this.output.gain.linearRampToValueAtTime(1,this.context.currentTime+e)):this.output.gain.setValueAtTime(1,this.context.currentTime),this.isPlaying=!0}start(e=0,n=0,i){this.isPlaying||(this.source=this._createSource(),this.startTime=this.context.currentTime+e-n/this.playbackRate,i!==void 0?this.source.start(this.context.currentTime+e,n,i):this.source.start(this.context.currentTime+e,n),this.pauseTime=n,this.isPlaying=!0)}pause({fadeOut:e=0}={}){if(!this.isPlaying)return;let n=this.getElapsed()/1e3;if(this.loop&&this.loopEnd>this.loopStart){let i=this.loopEnd-this.loopStart;n=this.loopStart+(n-this.loopStart)%i}if(this.isPlaying=!1,e>0){let i=this.context.currentTime;this.output.gain.setValueAtTime(this.output.gain.value,i),this.output.gain.linearRampToValueAtTime(0,i+e),setTimeout(()=>{if(this.source){this.source.onended=null;try{this.source.stop()}catch{}}this.pauseTime=n,this.output.gain.setValueAtTime(1,this.context.currentTime)},e*1e3)}else{if(this.source){this.source.onended=null;try{this.source.stop()}catch{}}this.pauseTime=n}}getElapsed(){return this.isPlaying?(this.context.currentTime-this.startTime)*this.playbackRate*1e3:this.pauseTime*1e3}setSpeed(e){if(e<=0)throw new Error("Playback rate must be positive");let n=this.getElapsed()/1e3;this.playbackRate=e,this.isPlaying&&(this.pause(),this.pauseTime=n,this.play())}setLoop(e=!0){this.loop=e,this.source&&(this.source.loop=e)}loop;playbackRate;startTime;tempGain=null;connect(e,n=0,i=0){if("value"in e)this.output.connect(e,n);else return this.output.connect(e,n,i),e}disconnect(e,n,i){e===void 0?this.output.disconnect():this.output.disconnect(e,n,i)}output;stop(e=0){if(this.notIndependent)return this.pause();if(!this.source)return;let n=this.context.currentTime+e;this.source.stop(n),this.isPlaying=!1,this.notIndependent||(this.pauseTime=0)}pauseTime;isPlaying;notIndependent=!1;loopStart=0;loopEnd=0},Ie={osc:{enabled:!0,type:"sine",freq:440,detune:0},noise:{enabled:!1,level:.5},ampEnv:{attack:.005,decay:.1,sustain:0,release:.1,volume:.3},pitchEnv:{amount:0,decay:.2},filter:{enabled:!1,type:"lowpass",freq:1200,Q:1,envAmount:0,decay:.2},lfo:{enabled:!1,target:"freq",rate:8,depth:20},duration:.4},_=class r{constructor(e={}){this.ctx=U.audioCtx,this.cfg=structuredClone(Ie),Object.assign(this.cfg,e)}ctx;cfg;play(e=U.sfxGain){let n=this.ctx,i=n.currentTime,s=this.cfg,o=n.createGain();o.gain.setValueAtTime(1e-4,i);let c=s.ampEnv;o.gain.exponentialRampToValueAtTime(c.volume,i+c.attack),o.gain.exponentialRampToValueAtTime(Math.max(1e-4,c.sustain*c.volume),i+c.attack+c.decay),o.gain.exponentialRampToValueAtTime(1e-4,i+s.duration+c.release);let d=o,u;s.filter.enabled&&(u=n.createBiquadFilter(),u.type=s.filter.type,u.frequency.value=s.filter.freq,u.Q.value=s.filter.Q,u.connect(o),d=u);let h;if(s.osc.enabled){if(h=n.createOscillator(),h.type=s.osc.type,h.frequency.value=s.osc.freq,h.detune.value=s.osc.detune,s.pitchEnv.amount!==0){let a=Math.pow(2,s.pitchEnv.amount/12);h.frequency.exponentialRampToValueAtTime(s.osc.freq*a,i+s.pitchEnv.decay)}h.connect(d),h.start(i),h.stop(i+s.duration+c.release)}let p;if(s.noise.enabled){let a=n.sampleRate*s.duration,l=n.createBuffer(1,a,n.sampleRate),f=l.getChannelData(0);for(let y=0;y<a;y++)f[y]=(Math.random()*2-1)*s.noise.level;p=n.createBufferSource(),p.buffer=l,p.connect(d),p.start(i),p.stop(i+s.duration+c.release)}let b,g;s.lfo.enabled&&h&&(b=n.createOscillator(),b.frequency.value=s.lfo.rate,g=n.createGain(),g.gain.value=s.lfo.depth,b.connect(g),s.lfo.target==="freq"?g.connect(h.frequency):s.lfo.target==="gain"?g.connect(o.gain):s.lfo.target==="filter"&&u&&g.connect(u.frequency),b.start(i),b.stop(i+s.duration)),o.connect(e);let x=[h,p,b,g,u,o],t=i+s.duration+c.release;setTimeout(()=>{x.forEach(a=>a?.disconnect())},(t-n.currentTime)*1e3)}getConfig(){return structuredClone(this.cfg)}setConfig(e){return Object.assign(this.cfg,e),this}getKey(e){return this.cfg[e]}setKey(e,n){return Object.assign(this.cfg[e],n),this}setFreq(e){return this.cfg.osc.freq=e,this}setWave(e){return this.cfg.osc.type=e,this}setVolume(e){return this.cfg.ampEnv.volume=e,this}setAmpEnv(e,n,i,s){return Object.assign(this.cfg.ampEnv,{attack:e,decay:n,sustain:i,release:s}),this}setPitchEnv(e,n){return Object.assign(this.cfg.pitchEnv,{amount:e,decay:n}),this}setNoiseEnabled(e){return this.cfg.noise.enabled=e,this}setNoiseLevel(e){return this.cfg.noise.level=e,this}setFilterEnabled(e){return this.cfg.filter.enabled=e,this}setFilter(e,n,i){return Object.assign(this.cfg.filter,{type:e,freq:n,Q:i,enabled:!0}),this}setLFOEnabled(e){return this.cfg.lfo.enabled=e,this}setLFO(e,n,i){return Object.assign(this.cfg.lfo,{target:e,rate:n,depth:i,enabled:!0}),this}setDuration(e){return this.cfg.duration=e,this}clone(){return new r(structuredClone(this.cfg))}},Fe=new _({osc:{enabled:!0,type:"square",freq:900,detune:0},ampEnv:{attack:.002,decay:.04,sustain:0,release:.02,volume:.15},duration:.05}),Pe=new _({osc:{enabled:!0,type:"sine",freq:600,detune:0},ampEnv:{attack:.01,decay:.08,sustain:0,release:.04,volume:.12},duration:.1}),Me=new _({osc:{enabled:!0,type:"triangle",freq:500,detune:0},pitchEnv:{amount:12,decay:.15},ampEnv:{attack:.01,decay:.12,sustain:0,release:.05,volume:.25},duration:.18}),Ae=new _({osc:{enabled:!0,type:"sawtooth",freq:1200,detune:0},pitchEnv:{amount:-24,decay:.3},ampEnv:{attack:.005,decay:.25,sustain:0,release:.05,volume:.3},duration:.35}),_e=new _({osc:{enabled:!0,type:"square",freq:180,detune:0},noise:{enabled:!0,level:.4},ampEnv:{attack:.002,decay:.15,sustain:0,release:.05,volume:.35},duration:.2}),xt=new Map([["ui_click",Fe],["ui_hover",Pe],["jump",Me],["laser",Ae],["hit",_e]]);function wt(r=12){let e=Date.now().toString(36),n=crypto.getRandomValues(new Uint8Array(r)),i=Array.from(n).map(s=>s.toString(36).padStart(2,"0")).join("");return(e+i).slice(0,r)}function oe(r=12){let e=Date.now().toString(36),n=crypto.getRandomValues(new Uint8Array(4)),i=Array.from(n).map(s=>s.toString(36).padStart(2,"0")).join("");return(e+i).slice(0,r)}var we=class{peer=null;key;events={};mbAcc=0;connected=!1;constructor(){this.key=`${Le()}_${Date.now()}`}connect(e){e&&(this.peer=e,e.peer=this,this.connected=!0,e.connected=!0),this._emit("open")}isConnected(){return this.connected&&!!this.peer}on(e,n){this.events[e]||(this.events[e]=[]),this.events[e].push(n)}off(e,n){this.events[e]&&(this.events[e]=this.events[e].filter(i=>i!==n))}_emit(e,n){this.events[e]?.forEach(i=>i(n))}send(e,n){if(!this.peer)throw new Error("No peer connected");this.peer._receive(e,n)}_receive(e,n){e?this._emit(e,n):this._emit("message",n)}close(){if(this.connected=!1,this.peer){let e=this.peer;this.peer=null,e.peer=null,e.connected=!1,e._emit("close")}this._emit("close")}getKey(){return this.key}};function Le(){if(typeof crypto<"u"&&typeof crypto.randomUUID=="function")return crypto.randomUUID();if(typeof crypto<"u"&&typeof crypto.getRandomValues=="function"){let r=new Uint8Array(16);return crypto.getRandomValues(r),r[6]=r[6]&15|64,r[8]=r[8]&63|128,[...r].map(e=>e.toString(16).padStart(2,"0")).join("").replace(/^(.{8})(.{4})(.{4})(.{4})(.{12})$/,"$1-$2-$3-$4-$5")}return"xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx".replace(/[xy]/g,r=>{let e=Math.random()*16|0;return(r==="x"?e:e&3|8).toString(16)})}function Ve(r){let e=!0;function n(){e&&(r(),requestAnimationFrame(n))}return requestAnimationFrame(n),{clear:()=>e=!1}}function De(r,e,n,i,s){let o=Math.cos(s),c=Math.sin(s),d=[];if(o!==0){let u=(0-r)/o,h=e+u*c;u>0&&h>=0&&h<=i&&d.push({side:"left",t:u})}if(o!==0){let u=(n-r)/o,h=e+u*c;u>0&&h>=0&&h<=i&&d.push({side:"right",t:u})}if(c!==0){let u=(0-e)/c,h=r+u*o;u>0&&h>=0&&h<=n&&d.push({side:"top",t:u})}if(c!==0){let u=(i-e)/c,h=r+u*o;u>0&&h>=0&&h<=n&&d.push({side:"bottom",t:u})}return d.length===0?null:(d.sort((u,h)=>u.t-h.t),d[0])}function Ge(r,e){let n;switch(e){case"left":case"right":n=Math.PI-r;break;case"top":case"bottom":n=2*Math.PI-r;break}return(n%(2*Math.PI)+2*Math.PI)%(2*Math.PI)}function vt(r,e,n,i,s){let o=De(r,e,n,i,s);return o?{...o,avoidAngle:Ge(s,o.side)}:null}function He(){return B?!1:/Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(navigator.userAgent)}var Ct=He();function ze({width:r,height:e,updateHz:n="frames"}){return new V.KaylaGame(r,e,n==="frames"?1/0:n)}function Ue(r){let e=new O(r);return new V.KaylaScene(e)}function $e(r){return new V.KaylaRenderer(r)}function Ne(r,e){if(typeof r!="function")throw new Error("Invalid Element Type.");let n=e??{};return n.key??=r.name+"_"+oe(),{type:r,props:n}}var F;(i=>{function r(s,o){return!(s.right<o.left||s.left>o.right||s.bottom<o.top||s.top>o.bottom)}i.rawCollision=r;function e(s,o,c){let d=o*Math.PI/180,u=Math.cos(d),h=Math.sin(d),p=1/0;return u>0&&(p=Math.min(p,(c.right-s.x)/u)),u<0&&(p=Math.min(p,(c.left-s.x)/u)),h>0&&(p=Math.min(p,(c.bottom-s.y)/h)),h<0&&(p=Math.min(p,(c.top-s.y)/h)),A.from(o).scale(p)}i.getCurrToBound=e;function n(s){let{left:o,right:c,top:d,bottom:u,width:h,height:p,x:b=0,y:g=0}=s;if(h===null||p===null)throw new Error("width and height are required");let x,t;if(o!=null&&c!=null){if(Math.abs(c-o-h)>1e-6)throw new Error("left, right, and width mismatch");x=o}else b!=null?x=b-h/2:o!=null?x=o:c!=null?x=c-h:x=0;if(d!=null&&u!=null){if(Math.abs(u-d-p)>1e-6)throw new Error("top, bottom, and height mismatch");t=d}else g!=null?t=g-p/2:d!=null?t=d:u!=null?t=u-p:t=0;return{left:x,right:x+h,top:t,bottom:t+p,width:h,height:p,x:x+h/2,y:t+p/2}}i.createRawRect=n})(F||={});var V;(g=>{class r extends X{#e;#t;constructor(t,a,l){super(t,a,l),this.#e=new Set,this.#t=!1}delay(t){return this.ticker.createTimeout(t)}get started(){return this.#t}start(){if(!this.#t){for(let t of this.#e)t.start();this.#t=!0,super.start()}}stop(){if(this.#t){for(let t of this.#e)t.stop();this.#t=!1,super.stop()}}addRenderer(t){this.#e.has(t)||(this.#e.add(t),this.#t&&t.start(),t.game=this)}get mainRenderer(){return[...this.#e].at(0)}getRenderers(){return[...this.#e]}deleteRenderer(t){this.#e.has(t)&&(this.#e.delete(t),this.#t&&t.stop(),delete t.game)}}g.KaylaGame=r;class e extends N{game;pointerX;pointerY;pointerEvents;constructor(t){super(t),this.useDraw=this.useDraw.bind(this),this.on("draw",a=>{if(this.game)for(let l of this.game.scenes.values())l.handleDraw(a)}),this.pointerX=0,this.pointerY=0,this.pointerEvents=new T,this.pointerPosUpdater=this.pointerPosUpdater.bind(this),this.onPointerDown=this.onPointerDown.bind(this)}pointerPosUpdater(t){this.pointerX=t.clientX,this.pointerY=t.clientY}onPointerDown(t){this.pointerPosUpdater(t);let a=e.getClickType(t);if(a!=="invalid"){t.preventDefault();let l=this.getMousePos();this.pointerEvents.emit("down",l,a)}}static getClickType(t){switch(t.button){case 0:return"left";case 1:return"middle";case 2:return"right";default:return"invalid"}}listenPointerUpdates(){this.canvas.addEventListener("pointermove",this.pointerPosUpdater),this.canvas.addEventListener("pointerdown",this.onPointerDown)}unlistenPointerUpdates(){this.canvas.removeEventListener("pointermove",this.pointerPosUpdater),this.canvas.removeEventListener("pointerdown",this.onPointerDown)}pointerPosToWorldPos(t,a){let l=this.canvas.getBoundingClientRect(),f=(t-l.left)/l.width,y=(a-l.top)/l.height,w=f*this.viewportWidth*this.cameraWidth/l.width,k=y*this.viewportHeight*this.cameraHeight/l.height;return new A(w,k)}getMousePos(){return this.pointerPosToWorldPos(this.pointerX,this.pointerY)}useDraw(t){let a=l=>{t(l,new i)};return this.on("draw",a),()=>{this.off("draw",a)}}attachTo(t){t.addRenderer(this),this.game=t}detach(){this.game&&this.game.deleteRenderer(this)}}g.KaylaRenderer=e;class n{current;saves;constructor(){this.saves=[]}useTick(t){if(!this.current)throw new Error("Hook 'useTick' must be executed in the top level scope of a component.");this.current.onTick[this.current.useStepCallIndex]=t,this.current.useStepCallIndex++}usePaint(t){if(!this.current)throw new Error("Hook 'usePaint' must be executed in the top level scope of a component.");this.current.onPaint[this.current.useDrawCallIndex]=t,this.current.useDrawCallIndex++}useEntity(){if(!this.current)throw new Error("Hook 'useEntity' must be executed in the top level scope of a component.");return le(he)}useSelf(t){if(!this.current)throw new Error("Hook 'useSelf' must be executed in the top level scope of a component.");let a=le(null);return(a.current===null||a.current===void 0)&&(a.current=t()),a.current}useInitialization(t){if(!this.current)throw new Error("Hook 'useInitialization' must be executed in the top level scope of a component.");let a=this.current;a.onInits[this.current.useInitCallIndex]=t,a.useInitCallIndex++}useRect(){if(!this.current)throw new Error("Hook 'useRect' must be executed in the top level scope of a component.");return L(()=>new g.KaylaInternalRect(this.current))}useFiber(){if(!this.current)throw new Error("Hook 'useFiber' must be executed in the top level scope of a component.");return L(()=>this.current)}useFiberControl(){if(!this.current)throw new Error("Hook 'useFiberControl' must be executed in the top level scope of a component.");let t=this.current;return L(()=>({refresh:()=>t.refresh(),get childrenCount(){return t.lastChildren.length},setMaxChildren:a=>{t.setMaxChildren(a)},getMaxChildren:()=>t.getMaxChildren(),get maxSafeChildren(){return t.maxSafeChildren},get key(){return t.key},get getChildrenEntities(){return t.getChildrenEntities.bind(t)},get getEntityChain(){return t.getEntityChain.bind(t)},get getFiberChain(){return t.getFiberChain.bind(t)}}))}useCurrentTicker(){if(!this.current)throw new Error("Hook 'useCurrentTicker' must be executed in the top level scope of a component.");return this.current.getAttachedGame().ticker}useCurrentRenderer(){if(!this.current)throw new Error("Hook 'useCurrentRenderer' must be executed in the top level scope of a component.");return this.current.getAttachedGame().mainRenderer}useCurrentGame(){if(!this.current)throw new Error("Hook 'useCurrentGame' must be executed in the top level scope of a component.");return this.current.getAttachedGame()}useCurrentScene(){if(!this.current)throw new Error("Hook 'useCurrentScene' must be executed in the top level scope of a component.");return this.current.scene}useState(t,{alwaysRecall:a=!1}={}){if(!this.current)throw new Error("Hook 'useState' must be executed in the top level scope of a component.");let f=this.current.state[this.current.useStateCallIndex]??new s(this.current,t,{alwaysRecall:a});return this.current.state[this.current.useStateCallIndex]=f,this.current.useStateCallIndex++,f}useShouldRefresh(t){let a=this.current;if(!a)throw new Error("useShouldRefresh must be called inside a component");a.watchedDeps&&console.warn("useShouldRefresh called multiple times \u2014 using the last call"),a.watchedDeps=t}useRef(t){if(!this.current)throw new Error("Hook 'useRef' must be executed in the top level scope of a component.");let l=this.current.refs[this.current.useRefCallIndex]??c(t??null);return this.current.refs[this.current.useRefCallIndex]=l,this.current.useRefCallIndex++,l}useEffect(t){if(!this.current)throw new Error("Hook 'useEffect' must be executed in the top level scope of a component.");this.current.onEffect[this.current.useEffectCallIndex]=t,this.current.useEffectCallIndex++}useViewportEffect(t){if(!this.current)throw new Error("Hook 'useViewport' must be executed in the top level scope of a component.");this.current.onViewportEffect[this.current.useViewCallIndex]=t,this.current.useViewCallIndex++}useExports(t,a){if(!this.current)throw new Error("Hook 'useExports' must be executed in the top level scope of a component.");this.current.onExport=a}useGlobalClick(t){if(!this.current)throw new Error("Hook 'useGlobalClick' must be executed in the top level scope of a component.");this.current.onGlobalClick[this.current.useGlobalClickCallIndex]=t,this.current.useGlobalClickCallIndex++}useClick(t){if(!this.current)throw new Error("Hook 'useClick' must be executed in the top level scope of a component.");let a=this.current;Ce((l,f)=>{let y=a.entity;if(!y)return;let w=y.getRawRect(),k=F.createRawRect({x:l.x,y:l.y,width:3,height:3});F.rawCollision(w,k)&&t(l,f)})}useContext(t){if(!this.current)throw new Error("Hook 'useContext' must be executed in the top level scope of a component.");return this.current.findContextValueFromInst(t)}save(){this.saves.push({current:this.current})}restore(){let t=this.saves.pop();if(!t)throw new Error("Cannot restore without saving.");this.current=t.current}logLevel="warn";logger={debug:(...t)=>{this.logLevel==="debug"&&console.debug(...t)},info:(...t)=>{["info","warn","debug"].includes(this.logLevel)&&console.info(...t)},warn:(...t)=>{["warn","debug"].includes(this.logLevel)&&console.warn(...t)},error:(...t)=>console.error(...t),withFiber:(t,a,l,...f)=>{let y=t?.fc?.name||"anonymous",w=t?.key?` key=${t.key}`:"";this.logger[a](`${l} <${y}${w}>`,...f)}}}g.GlobalKayla=n;class i{preventDefault(){this.#e=!0}#e=!1;isPrevented(){return this.#e}}g.KaylaEvent=i;class s{#e;#t;#n;alwaysRecall;constructor(t,a,{alwaysRecall:l=!1}={}){this.#t=t,this.#e=a??void 0,this.#n=Date.now(),this.alwaysRecall=l}get(){return this.#e}*[Symbol.iterator](){throw new Error(`Hey! KaylaState is NOT an array / iterable like useState in React.
2
2
  You probably wrote: const [value, setValue] = useState(...)
3
3
 
4
4
  \u2192 In Kayla write: const value = useState(...);
5
- \u2192 Then: value.get() / value.set(v) / value.add(n)`)}refreshBased(){return[this.set.bind(this),this.get()]}add(t,{recall:a}={}){this.set(this.get()+t,{recall:a})}multiply(t,{recall:a}={}){this.set(this.get()*t,{recall:a})}set(t,{recall:a=!1}={}){let h=this.#e;if(t===h)return;this.#e=t;let g=Date.now()-this.#n;a&&g<67&&this.#t.global.logger.warn(`Hot structural state change <${this.#t.fc?.name||"anonymous"}> delta=${g}ms`),(a||this.alwaysRecall)&&this.#t.refresh(),this.#n=Date.now()}get value(){return this.#e}get lastChanged(){return this.#n}}b.KaylaInternalState=s;class o{#e;constructor(t){this.#e=t??void 0}#t;setSetter(t){this.#t=t}get current(){return this.#e}set current(t){this.#e=t,this.#t&&this.#t(this.#e)}}b.KaylaInternalRef=o;function d(x){return new o(x)}b.createReassignableRef=d;class f{state;refs;global;callProps;scene;exports;detectedParent;contextInfo;get childrenCount(){return this.lastChildren.length}maxSafeChildren;constructor(t,a,h){if(!h)throw new Error("Empty element");this.maxSafeChildren=40,this.scene=a,this.state=[],this.refs=[],this.fc=h.type,this.callProps=h.props??{},this.global=t,this.lastStateDeps=[],this.entity=null,this.lastChildren=[],this.onEffect=[],this.onUnEffect=[],this.onPaint=[],this.onTick=[],this.onGlobalClick=[],this.pointerHook=this.pointerHook.bind(this),this.contextInfo=null,this.detectedParent=null}getChildrenEntities(){return this.lastChildren.map(t=>t.entity)}pointerHook(t,a){try{for(let h of this.onGlobalClick)h(t,a)}catch(h){this.global.logger.error(h)}}bindEvents(){for(let t of[this.getAttachedRenderer()])t&&t.pointerEvents.on("down",this.pointerHook)}unbindEvents(){for(let t of[this.getAttachedRenderer()])t&&t.pointerEvents.off("down",this.pointerHook)}get key(){return this.callProps.key}set key(t){this.callProps.key=t}get children(){return this.callProps.children}set children(t){this.callProps.children=t}entity;onExport=()=>({});onEffect;onGlobalClick;onInit;onUnInit;onUnEffect;onEffectDeps;onPaint;onTick;fc;useStateCallIndex=0;useEffectCallIndex=0;useGlobalClickCallIndex=0;useDrawCallIndex=0;useStepCallIndex=0;useRefCallIndex=0;lastStateDeps;watchedDeps;lastDepStamps=[];getAttachedRenderer(){return this.getAttachedGame().mainRenderer}getAttachedGame(){return this.scene.getGame()}setMaxChildren(t){if(this.maxSafeChildren=Math.max(0,t),this.global.logger.debug(`Max children limit updated to ${t} for <${this.fc?.name||"anonymous"} key=${this.key}>`),this.lastChildren.length>this.maxSafeChildren){let a=this.lastChildren.length-this.maxSafeChildren;this.global.logger.warn(`Child limit exceeded (${this.lastChildren.length} > ${this.maxSafeChildren}) \u2014 removing ${a} oldest children <${this.fc?.name||"anonymous"} key=${this.key}>`);let h=this.lastChildren.slice(0,this.maxSafeChildren),c=this.lastChildren.slice(this.maxSafeChildren);this.lastChildren=h;for(let g of c)g.unuse()}}getMaxChildren(){return this.maxSafeChildren??1/0}getFiberChain(){let t=[],a=this.detectedParent;for(;a;)t.push(a),a=a?.detectedParent;return t}getContextChain(){return this.getFiberChain().map(t=>t.contextInfo).filter(Boolean)}findContextValueFromInst(t){return this.getContextChain().find(a=>a.instance===t)?.value}getEntityChain(){return this.getFiberChain().map(t=>t.entity)}shouldFullRefresh(){if(this.isFirstUse||!this.watchedDeps||this.watchedDeps.length===0)return!0;for(let t=0;t<this.watchedDeps.length;t++){let a=this.watchedDeps[t],h=this.lastDepStamps[t]??0;if(a.lastChanged>h)return!0}return!1}captureDepStamps(){this.watchedDeps&&(this.lastDepStamps=this.watchedDeps.map(t=>t.lastChanged))}refresh(){if(!this.shouldFullRefresh())return;let t=this.fc?.name||"anonymous";if(!this.shouldFullRefresh()){this.global.logger.debug(`Refresh skipped <${t} key=${this.key}>`);return}this.global.logger.debug(`Refresh executed <${t} key=${this.key}> reason=${this.isFirstUse?"first":"deps-changed"}`),this.lastChildren.length>this.maxSafeChildren&&this.global.logger.warn(`High child count <${t} key=${this.key}> children=${this.lastChildren.length}`);let a;this.global.save(),this.global.current=this,this.useStateCallIndex=0,this.useRefCallIndex=0;let h=[];try{let c=this.fc(this.callProps)??[];if(c&&!Array.isArray(c)&&(c=[c]),!Array.isArray(c))throw new Error("Non array or non undefined children received.");for(let g of c)if(g.type===this.fc)throw new Error("Circular Component.");h=c}catch(c){a=c}this.useStateCallIndex=0,this.useRefCallIndex=0,this.useDrawCallIndex=0,this.useStepCallIndex=0,this.useEffectCallIndex=0,this.useGlobalClickCallIndex=0,this.global.restore();try{let c=0,g=[];for(let w of h){let C=this.lastChildren.at(c)??new f(this.global,this.scene,w);this.lastChildren[c]=C,C.detectedParent=this,g.push(C),c++}this.captureDepStamps(),this.use();for(let w of this.lastChildren.filter(C=>!g.includes(C))){let C=this.lastChildren.indexOf(w);C!==1&&this.lastChildren.splice(C,1),w.unuse()}for(let w of this.lastChildren)try{w.refresh()}catch(C){console.error(C)}}catch(c){console.error(c)}if(a)throw a}lastChildren;isFirstUse=!0;use(){try{let t=!0;if(this.lastStateDeps??=[],Array.isArray(this.onEffectDeps)&&(t=this.onEffectDeps.some((a,h)=>{let c=this.lastStateDeps.at(h);if(c){let g=a.lastChanged,w=c.stamp;return g>w}})),t||this.isFirstUse){this.key??=this.fc.name+"_"+we(),this.global.logger.debug(`Using <${this.fc?.name||"anonymous"} key=${this.key}> count=${this.onEffect.length}`);let a=this.isFirstUse;this.isFirstUse=!1,Array.isArray(this.onEffectDeps)&&(this.lastStateDeps=this.onEffectDeps.map(c=>({stamp:c.lastChanged,stateRef:c}))),this.entity&&this.scene.getScene().removeEntity(this.entity),this.entity&&this.entity.name!==this.key&&(this.entity=null),this.entity=this.entity??new u(this,this.key);for(let c of this.refs)c.current===ue&&(c.current=this.entity);if(this.callProps.ref instanceof o&&(this.callProps.ref.current=this.entity),this.exports=this.onExport(),this.callProps.exportsRef instanceof o&&(this.callProps.exportsRef.current=this.exports),this.entity&&this.entity!==this.entity&&this.global.logger.warn(`Entity name mismatch during refresh <${this.fc?.name} key=${this.key}>`),this.scene.getScene().addEntity(this.entity),a&&this.onInit){this.bindEvents();try{let c=this.onInit();typeof c=="function"&&(this.onUnInit=c)}catch(c){throw this.global.logger.error("Initialization failed",this.fc?.name||"anonymous",c),c}}try{for(let c of this.onUnEffect??[])c()}catch(c){console.error(c)}let h=this.onEffect.map(c=>c()).filter(c=>c!==void 0);this.onUnEffect=h}}catch(t){throw this.global.logger.error(`use() failed <${this.fc?.name||"anonymous"} key=${this.key}>`,t),t}}unuse(){this.global.logger.debug(`unuse called <${this.fc?.name||"anonymous"} key=${this.key}> children=${this.lastChildren.length}`),this.watchedDeps=void 0,this.lastDepStamps=[],this.unbindEvents();try{this.onUnInit&&this.onUnInit();for(let t of this.onUnEffect)t()}catch(t){this.global.logger.error(`Cleanup failed in unuse <${this.fc?.name||"anonymous"} key=${this.key}>`,t)}this.scene.getScene().removeEntity(this.entity);for(let t of this.lastChildren)t.unuse();this.lastChildren.length=0}}b.KaylaFiber=f;class u extends X{#e;flags;getRawRect(){return F.createRawRect({x:this.x,y:this.y,width:this.width,height:this.height})}getFiber(){return this.#e}constructor(t,a){super(a,0,0,0,0),this.#e=t,this.flags=new Map}setFlag(t,a){return this.flags.set(t,a)}getFlag(t){return this.flags.get(t)}removeFlag(t){return this.flags.delete(t)}update(t){let a=new i;if(this.#e&&this.#e.onTick)for(let h of this.#e.onTick)h(t,a);a.isPrevented()}draw(t){let a=new i;if(this.#e&&this.#e.onPaint)for(let h of this.#e.onPaint)h(t,a);a.isPrevented()||super.draw(t)}getRect(){return new l(this.getFiber())}}b.KaylaRectEntity=u;class l{#e;constructor(t){this.#e=t}getRaw(){return F.createRawRect({x:this.x,y:this.y,width:this.width,height:this.height})}get entity(){return this.#e.entity??null}#t(){if(!this.#e)throw new Error("No fibers found.");if(!this.entity)throw new Error("The entity does NOT exist yet.")}isCollidingWith(t){return this.#t(),this.entity.isCollidingWith(t.entity)}get setFlag(){return this.#t(),this.entity.setFlag.bind(this.entity)}get getFlag(){return this.#t(),this.entity.getFlag.bind(this.entity)}get removeFlag(){return this.#t(),this.entity.removeFlag.bind(this.entity)}isHovered(){let t=this.getRaw(),a=this.#e.getAttachedRenderer().getMousePos(),h=F.createRawRect({x:a.x,y:a.y,width:3,height:3});return F.rawCollision(t,h)}get pos(){return this.#t(),this.entity.pos}get x(){return this.#t(),this.pos.x}set x(t){this.#t(),this.pos.x=t}get y(){return this.#t(),this.pos.y}set y(t){this.#t(),this.pos.y=t}get width(){return this.#t(),this.entity.width}set width(t){this.#t(),this.entity.width=t}get height(){return this.#t(),this.entity.height}set height(t){this.#t(),this.entity.height=t}get z(){return this.#t(),this.entity.z}set z(t){this.#t(),this.entity.z=t}get left(){return this.#t(),this.entity.left}set left(t){this.#t(),this.entity.left=t}get right(){return this.#t(),this.entity.right}set right(t){this.#t(),this.entity.right=t}get top(){return this.#t(),this.entity.top}set top(t){this.#t(),this.entity.top=t}get bottom(){return this.#t(),this.entity.bottom}set bottom(t){this.#t(),this.entity.bottom=t}get toLocal(){return this.entity.toLocal.bind(this.entity)}get toWorld(){return this.entity.toWorld.bind(this.entity)}}b.KaylaInternalRect=l;class p{constructor(t){this.#t=t,this.#e=null,t.on("update",this.tickHandler.bind(this)),this.drawHandler=this.drawHandler.bind(this)}#e;#t;getFibers(){return this.getEntities().map(t=>t.getFiber())}getEntities(){return Array.from(this.getScene().entities.values())}getScene(){return this.#t}getGame(){return this.#e}drawHandler(t){return this.#t.handleDraw(t)}attachTo(t){t.addScene(this.#t),this.#e=t}async spawn(t){let a=this.createFiber(t);await this.#e.delay(0),a.refresh()}createFiber(t){return new f(b.singleGlobalInstance,this,t)}detach(){this.#e&&this.#e.removeScene(this.#t)}tickHandler(){}}b.KaylaScene=p,b.singleGlobalInstance=new b.GlobalKayla})(L||={});var B=class{#e;constructor(e){this.Provider=this.#t.bind(this),this.#e=e}get defaultValue(){return this.#e}#t({value:e=this.defaultValue,children:n}){let i=Ce();return W(()=>{i.contextInfo={instance:this,value:e}}),Q(this.Provider,()=>({value:e})),n}Provider;Consumer};function Ue(r){return new B(r)}var m=L.singleGlobalInstance,Ne=m.useState.bind(m),oe=m.useRef.bind(m),Oe=m.useShouldRefresh.bind(m),le=m.useEffect.bind(m),ve=m.useGlobalClick.bind(m),Xe=m.useClick.bind(m),W=m.useInitialization.bind(m),Y=m.useRect.bind(m),qe=m.useTick.bind(m),j=m.usePaint.bind(m),Q=m.useExports.bind(m),_=m.useSelf.bind(m),he=m.useFiberControl.bind(m),Ce=m.useFiber.bind(m),Be=m.useEntity.bind(m),We=m.useCurrentGame.bind(m),Ye=m.useCurrentRenderer.bind(m),je=m.useCurrentScene.bind(m),Qe=m.useCurrentTicker.bind(m),Je=m.useContext.bind(m),ue=Symbol("self_ref");var ce=r=>{Promise.resolve(1).then(()=>{try{r()}catch(e){console.error(e)}})},Ze=({children:r})=>Array.isArray(r)?[...r]:r;function et(r){return L.createReassignableRef(r)}function tt(r){if(typeof r!="object"||typeof r=="function"||r===null)return r;let e={current:r};return new Proxy({},{get(i,s,o){return s==="reassignSelf"?d=>{e.current=d}:Reflect.get(e.current,s,o)},set(i,s,o,d){return Reflect.set(e.current,s,o,d)},has(i,s){return Reflect.has(e.current,s)},ownKeys(i){return Reflect.ownKeys(e.current)},getOwnPropertyDescriptor(i,s){return Reflect.getOwnPropertyDescriptor(e.current,s)},deleteProperty(i,s){return Reflect.deleteProperty(e.current,s)}})}function nt(r){m.logLevel=r}function rt(r){let e=r.name||"anonymous-custom-hook";return function(i){let s=m.current;if(!s)throw new Error(`Custom hook '${e}' must be called inside a Kayla component`);let o=i??{};return r.memoize!==!1?_(()=>(s.global.logLevel==="debug"&&s.global.logger.debug(`Custom hook '${e}' initialized (memoized) <${s.fc?.name||"anonymous"} key=${s.key||"no-key"}>`),r.onUse(s,m,o))):(s.global.logLevel==="debug"&&s.global.logger.debug(`Custom hook '${e}' running (non-memoized) <${s.fc?.name||"anonymous"} key=${s.key||"no-key"}>`),r.onUse(s,m,o))}}Reflect.set(globalThis,"Kayla",de);var it;(n=>(n.Flex=({align:i="stretch",children:s,direction:o="row",gap:d=0,justify:f="start",wrap:u="nowrap",getHeight:l,getWidth:p,getCenterX:y,getCenterY:b,color:x})=>{let t=he(),a=Y(),h=_(()=>({recalc(){let c=Number(d)||0,g=y(),w=b(),C=p(),st=l();a.x=g,a.y=w,a.width=C,a.height=st;let at=t.getChildrenEntities().filter(Boolean).map(v=>v.getRect()).filter(v=>v.getFlag("flex-ignored")!==!0),S=o==="row",P=S?a.width:a.height,Et=S?a.height:a.width,fe=0,$=0,pe=[],J=[];at.forEach(v=>{let Z=S?v.width:v.height;fe+Z>P&&u==="wrap"?(pe.push({height:$,items:J}),J=[v],fe=Z,$=S?v.height:v.width):(J.push(v),fe+=Z+c,$=Math.max($,S?v.height:v.width))}),pe.push({height:$,items:J});let me=0;pe.forEach((v,Z)=>{let I=v.items,D=I.reduce((R,ee)=>R+(S?ee.width:ee.height),0)+c*(I.length-1),T=0;f==="center"&&(T=(P-D)/2),f==="end"&&(T=P-D),f==="space-between"&&(T=0),f==="space-around"&&(T=(P-D)/(I.length*2)),f==="space-evenly"&&(T=(P-D)/(I.length+1)),I.forEach((R,ee)=>{R.z=a.z+1;let G=S?R.width:R.height,te=S?R.height:R.width,ne=0;i==="center"&&(ne=(v.height-te)/2),i==="end"&&(ne=v.height-te),i==="stretch"&&(S?R.height=v.height:R.width=v.height),S?(R.x=T+G/2,R.y=me+ne+te/2):(R.x=me+ne+te/2,R.y=T+G/2),f==="space-between"&&ee<I.length-1?T+=G+c+(P-D)/(I.length-1):f==="space-around"?T+=G+c+(P-D)/I.length:f==="space-evenly"?T+=G+c+(P-D)/(I.length+1):T+=G+c}),me+=v.height+c})}}));return j((c,g)=>{g.preventDefault(),c.fillStyle=x,c.fillRect(a.left,a.top,a.width,a.height)}),le(()=>{ce(()=>{h.recalc()})}),Q(n.Flex,()=>({controls:h})),s},n.GenericBox=({color:i,width:s=20,height:o=20,x:d=0,y:f=0})=>{let u=Y();W(()=>{u.width=s,u.height=o,u.x=d,u.y=f}),j((l,p)=>{p.preventDefault(),l.fillStyle=i,l.fillRect(u.left,u.top,u.width,u.height)})}))(it||={});0&&(module.exports={Kayla,KaylaContext,KaylaFragment,KaylaInternals,KaylaRect,LEA,UI,createContext,createElement,createGame,createReassignableObject,createRenderer,createScene,createUseHook,self,setLogLevel,useClick,useContext,useCurrentGame,useCurrentRenderer,useCurrentScene,useCurrentTicker,useDisposableRef,useEffect,useEntity,useExports,useFiber,useFiberControl,useGlobalClick,useInitialization,useNextStack,usePaint,useRect,useRef,useSelf,useShouldRefresh,useState,useTick});
5
+ \u2192 Then: value.get() / value.set(v) / value.add(n)`)}refreshBased(){return[this.set.bind(this),this.get()]}add(t,{recall:a}={}){this.set(this.get()+t,{recall:a})}multiply(t,{recall:a}={}){this.set(this.get()*t,{recall:a})}set(t,{recall:a=!1}={}){let l=this.#e;if(t===l)return;this.#e=t;let y=Date.now()-this.#n;a&&y<67&&this.#t.global.logger.warn(`Hot structural state change <${this.#t.fc?.name||"anonymous"}> delta=${y}ms`),(a||this.alwaysRecall)&&this.#t.refresh(),this.#n=Date.now()}get value(){return this.#e}get lastChanged(){return this.#n}}g.KaylaInternalState=s;class o{#e;constructor(t){this.#e=t??void 0}#t;setSetter(t){this.#t=t}get current(){return this.#e}set current(t){this.#e=t,this.#t&&this.#t(this.#e)}}g.KaylaInternalRef=o;function c(x){return new o(x)}g.createReassignableRef=c;class d{state;refs;global;callProps;scene;exports;detectedParent;contextInfo;get childrenCount(){return this.lastChildren.length}maxSafeChildren;dynamicChildren;constructor(t,a,l){if(!l)throw new Error("Empty element");this.maxSafeChildren=40,this.scene=a,this.state=[],this.refs=[],this.onInits=[],this.onUnInits=[],this.fc=l.type,this.callProps=l.props??{},this.global=t,this.lastStateDeps=[],this.entity=null,this.lastChildren=[],this.onEffect=[],this.onUnEffect=[],this.onPaint=[],this.onTick=[],this.onGlobalClick=[],this.pointerHook=this.pointerHook.bind(this),this.resizeHook=this.resizeHook.bind(this),this.contextInfo=null,this.detectedParent=null,this.dynamicChildren=[],this.key??=this.fc.name+"_"+oe(),this.onViewportEffect=[]}getChildrenEntities(){return this.lastChildren.map(t=>t.entity)}pointerHook(t,a){try{for(let l of this.onGlobalClick)l(t,a)}catch(l){this.global.logger.error(l)}}resizeHook({width:t,height:a}){try{for(let l of this.onViewportEffect)l(this.getAttachedRenderer(),t,a)}catch(l){this.global.logger.error(l)}}bindEvents(){for(let t of[this.getAttachedRenderer()])t&&(t.pointerEvents.on("down",this.pointerHook),t.on("viewport_update",this.resizeHook))}unbindEvents(){for(let t of[this.getAttachedRenderer()])t&&(t.pointerEvents.off("down",this.pointerHook),t.off("viewport_update",this.resizeHook))}get key(){return this.callProps.key}set key(t){this.callProps.key=t}get children(){return this.callProps.children}set children(t){this.callProps.children=t}entity;onExport=()=>({});onEffect;onViewportEffect;onGlobalClick;onInits;onUnInits;onUnEffect;onEffectDeps;onPaint;onTick;fc;useStateCallIndex=0;useEffectCallIndex=0;useGlobalClickCallIndex=0;useDrawCallIndex=0;useStepCallIndex=0;useRefCallIndex=0;useInitCallIndex=0;useViewCallIndex=0;lastStateDeps;watchedDeps;lastDepStamps=[];getAttachedRenderer(){return this.getAttachedGame().mainRenderer}getAttachedGame(){return this.scene.getGame()}setMaxChildren(t){if(this.maxSafeChildren=Math.max(0,t),this.global.logger.debug(`Max children limit updated to ${t} for <${this.fc?.name||"anonymous"} key=${this.key}>`),this.lastChildren.length>this.maxSafeChildren){let a=this.lastChildren.length-this.maxSafeChildren;this.global.logger.warn(`Child limit exceeded (${this.lastChildren.length} > ${this.maxSafeChildren}) \u2014 removing ${a} oldest children <${this.fc?.name||"anonymous"} key=${this.key}>`);let l=this.lastChildren.slice(0,this.maxSafeChildren),f=this.lastChildren.slice(this.maxSafeChildren);this.lastChildren=l;for(let y of f)y.unuse()}}getMaxChildren(){return this.maxSafeChildren??1/0}getFiberChain(){let t=[],a=this.detectedParent;for(;a;)t.push(a),a=a?.detectedParent;return t}getContextChain(){return this.getFiberChain().map(t=>t.contextInfo).filter(Boolean)}findContextValueFromInst(t){return this.getContextChain().find(a=>a.instance===t)?.value}getEntityChain(){return this.getFiberChain().map(t=>t.entity)}shouldFullRefresh(){if(this.isFirstUse||!this.watchedDeps||this.watchedDeps.length===0)return!0;for(let t=0;t<this.watchedDeps.length;t++){let a=this.watchedDeps[t],l=this.lastDepStamps[t]??0;if(a.lastChanged>l)return!0}return!1}captureDepStamps(){this.watchedDeps&&(this.lastDepStamps=this.watchedDeps.map(t=>t.lastChanged))}refresh(){if(!this.shouldFullRefresh())return;let t=this.fc?.name||"anonymous";if(!this.shouldFullRefresh()){this.global.logger.debug(`Refresh skipped <${t} key=${this.key}>`);return}this.global.logger.debug(`Refresh executed <${t} key=${this.key}> reason=${this.isFirstUse?"first":"deps-changed"}`),this.lastChildren.length>this.maxSafeChildren&&this.global.logger.warn(`High child count <${t} key=${this.key}> children=${this.lastChildren.length}`);let a;this.global.save(),this.global.current=this,this.useStateCallIndex=0,this.useRefCallIndex=0,this.useInitCallIndex=0,this.useViewCallIndex=0,this.useStateCallIndex=0,this.useDrawCallIndex=0,this.useStepCallIndex=0,this.useEffectCallIndex=0,this.useGlobalClickCallIndex=0;let l=[];try{let f=this.fc(this.callProps)??[];if(f&&!Array.isArray(f)&&(f=[f]),!Array.isArray(f))throw new Error("Non array or non undefined children received.");for(let y of f)if(y.type===this.fc)throw new Error("Circular Component.");l=f}catch(f){a=f}if(this.global.restore(),this.updateChildren(l,!0),a)throw a}updateChildren(t,a){try{let l=[...t,...this.dynamicChildren],f=[],y=[];for(let w of l){let k=w.props?.key,P;k!=null&&(P=this.lastChildren.find(Re=>Re.key===k)),P||(P=new d(this.global,this.scene,w)),P.detectedParent=this,y.push(P),f.push(P)}for(let w of this.lastChildren)f.includes(w)||w.unuse();this.lastChildren=y,this.captureDepStamps(),this.use();for(let w of this.lastChildren)try{w.refresh()}catch(k){console.error(k)}}catch(l){console.error(l)}}lastChildren;isFirstUse=!0;use(){try{let t=!0;if(this.lastStateDeps??=[],Array.isArray(this.onEffectDeps)&&(t=this.onEffectDeps.some((a,l)=>{let f=this.lastStateDeps.at(l);if(f){let y=a.lastChanged,w=f.stamp;return y>w}})),t||this.isFirstUse){this.global.logger.debug(`Using <${this.fc?.name||"anonymous"} key=${this.key}> count=${this.onEffect.length}`);let a=this.isFirstUse;this.isFirstUse=!1,Array.isArray(this.onEffectDeps)&&(this.lastStateDeps=this.onEffectDeps.map(f=>({stamp:f.lastChanged,stateRef:f}))),this.entity&&this.scene.getScene().removeEntity(this.entity),this.entity&&this.entity.name!==this.key&&(this.entity=null),this.entity=this.entity??new u(this,this.key);for(let f of this.refs)f.current===he&&(f.current=this.entity);if(this.callProps.ref instanceof o&&(this.callProps.ref.current=this.entity),this.exports=this.onExport(),this.callProps.exportsRef instanceof o&&(this.callProps.exportsRef.current=this.exports),this.entity&&this.entity!==this.entity&&this.global.logger.warn(`Entity name mismatch during refresh <${this.fc?.name} key=${this.key}>`),this.scene.getScene().addEntity(this.entity),a){this.onUnInits=[];for(let f of this.onInits){this.bindEvents();try{let y=f();typeof y=="function"&&this.onUnInits.push(y)}catch(y){throw this.global.logger.error("Initialization failed",this.fc?.name||"anonymous",y),y}}}try{for(let f of this.onUnEffect??[])f()}catch(f){console.error(f)}let l=this.onEffect.map(f=>f()).filter(f=>f!==void 0);this.onUnEffect=l}}catch(t){throw this.global.logger.error(`use() failed <${this.fc?.name||"anonymous"} key=${this.key}>`,t),t}}unuse(){this.global.logger.debug(`unuse called <${this.fc?.name||"anonymous"} key=${this.key}> children=${this.lastChildren.length}`),this.detectedParent=null,this.watchedDeps=void 0,this.lastDepStamps=[],this.unbindEvents();try{for(let t of this.onUnInits)t();for(let t of this.onUnEffect)t()}catch(t){this.global.logger.error(`Cleanup failed in unuse <${this.fc?.name||"anonymous"} key=${this.key}>`,t)}this.scene.getScene().removeEntity(this.entity);for(let t of this.lastChildren)t.unuse();this.lastChildren.length=0}}g.KaylaFiber=d;class u extends q{#e;flags;getRawRect(){return F.createRawRect({x:this.x,y:this.y,width:this.width,height:this.height})}getFiber(){return this.#e}constructor(t,a){super(a,0,0,0,0),this.#e=t,this.flags=new Map,this.color="transparent"}setFlag(t,a){return this.flags.set(t,a)}getFlag(t){return this.flags.get(t)}removeFlag(t){return this.flags.delete(t)}update(t){let a=new i;if(this.#e&&this.#e.onTick)for(let l of this.#e.onTick)l(t,a);a.isPrevented()}draw(t){let a=new i;if(this.#e&&this.#e.onPaint)for(let l of this.#e.onPaint)l(t,a);a.isPrevented()||super.draw(t)}getRect(){return new h(this.getFiber())}}g.KaylaRectEntity=u;class h{#e;constructor(t){this.#e=t}get color(){return this.#t(),this.entity.color}set color(t){this.#t(),this.entity.color=t}getRaw(){return F.createRawRect({x:this.x,y:this.y,width:this.width,height:this.height})}get entity(){return this.#e.entity??null}#t(){if(!this.#e)throw new Error("No fibers found.");if(!this.entity)throw new Error("The entity does NOT exist yet.")}isCollidingWith(t){return this.#t(),this.entity.isCollidingWith(t.entity)}get setFlag(){return this.#t(),this.entity.setFlag.bind(this.entity)}get getFlag(){return this.#t(),this.entity.getFlag.bind(this.entity)}get removeFlag(){return this.#t(),this.entity.removeFlag.bind(this.entity)}isHovered(){let t=this.getRaw(),a=this.#e.getAttachedRenderer().getMousePos(),l=F.createRawRect({x:a.x,y:a.y,width:3,height:3});return F.rawCollision(t,l)}get pos(){return this.#t(),this.entity.pos}get x(){return this.#t(),this.pos.x}set x(t){this.#t(),this.pos.x=t}get y(){return this.#t(),this.pos.y}set y(t){this.#t(),this.pos.y=t}get width(){return this.#t(),this.entity.width}set width(t){this.#t(),this.entity.width=t}get height(){return this.#t(),this.entity.height}set height(t){this.#t(),this.entity.height=t}get z(){return this.#t(),this.entity.z}set z(t){this.#t(),this.entity.z=t}get left(){return this.#t(),this.entity.left}set left(t){this.#t(),this.entity.left=t}get right(){return this.#t(),this.entity.right}set right(t){this.#t(),this.entity.right=t}get top(){return this.#t(),this.entity.top}set top(t){this.#t(),this.entity.top=t}get bottom(){return this.#t(),this.entity.bottom}set bottom(t){this.#t(),this.entity.bottom=t}get toLocal(){return this.entity.toLocal.bind(this.entity)}get toWorld(){return this.entity.toWorld.bind(this.entity)}}g.KaylaInternalRect=h;class p{constructor(t){this.#t=t,this.#e=null,t.on("update",this.tickHandler.bind(this)),this.drawHandler=this.drawHandler.bind(this)}#e;#t;getFibers(){return this.getEntities().map(t=>t.getFiber())}getEntities(){return Array.from(this.getScene().entities.values())}getScene(){return this.#t}getGame(){return this.#e}drawHandler(t){return this.#t.handleDraw(t)}attachTo(t){t.addScene(this.#t),this.#e=t}async spawn(t){let a=this.createFiber(t);await this.#e.delay(0),a.refresh()}createFiber(t){return new d(g.singleGlobalInstance,this,t)}detach(){this.#e&&this.#e.removeScene(this.#t)}tickHandler(){}}g.KaylaScene=p,g.singleGlobalInstance=new g.GlobalKayla})(V||={});var W=class{#e;constructor(e){this.Provider=this.#t.bind(this),this.#e=e}get defaultValue(){return this.#e}#t({value:e=this.defaultValue,children:n}){let i=Ee();return Y(()=>{i.contextInfo={instance:this,value:e}}),J(this.Provider,()=>({value:e})),n}Provider;Consumer};function Oe(r){return new W(r)}var m=V.singleGlobalInstance,Xe=m.useState.bind(m),le=m.useRef.bind(m),qe=m.useShouldRefresh.bind(m),ce=m.useEffect.bind(m),Be=m.useViewportEffect.bind(m),Ce=m.useGlobalClick.bind(m),We=m.useClick.bind(m),Y=m.useInitialization.bind(m),j=m.useRect.bind(m),Ye=m.useTick.bind(m),Q=m.usePaint.bind(m),J=m.useExports.bind(m),L=m.useSelf.bind(m),de=m.useFiberControl.bind(m),Ee=m.useFiber.bind(m),je=m.useEntity.bind(m),Qe=m.useCurrentGame.bind(m),Je=m.useCurrentRenderer.bind(m),Ze=m.useCurrentScene.bind(m),et=m.useCurrentTicker.bind(m),tt=m.useContext.bind(m),he=Symbol("self_ref");var fe=r=>{Promise.resolve(1).then(()=>{try{r()}catch(e){console.error(e)}})},nt=({children:r})=>Array.isArray(r)?[...r]:r;function rt(r){return V.createReassignableRef(r)}function it(r){if(typeof r!="object"||typeof r=="function"||r===null)return r;let e={current:r};return new Proxy({},{get(i,s,o){return s==="reassignSelf"?c=>{e.current=c}:Reflect.get(e.current,s,o)},set(i,s,o,c){return Reflect.set(e.current,s,o,c)},has(i,s){return Reflect.has(e.current,s)},ownKeys(i){return Reflect.ownKeys(e.current)},getOwnPropertyDescriptor(i,s){return Reflect.getOwnPropertyDescriptor(e.current,s)},deleteProperty(i,s){return Reflect.deleteProperty(e.current,s)}})}function st(r){m.logLevel=r}function at(r){let e=r.name||"anonymous-custom-hook";return function(i){let s=m.current;if(!s)throw new Error(`Custom hook '${e}' must be called inside a Kayla component`);let o=i??{};return r.memoize!==!1?L(()=>(s.global.logLevel==="debug"&&s.global.logger.debug(`Custom hook '${e}' initialized (memoized) <${s.fc?.name||"anonymous"} key=${s.key||"no-key"}>`),r.onUse(s,m,o))):(s.global.logLevel==="debug"&&s.global.logger.debug(`Custom hook '${e}' running (non-memoized) <${s.fc?.name||"anonymous"} key=${s.key||"no-key"}>`),r.onUse(s,m,o))}}Reflect.set(globalThis,"Kayla",pe);var ot;(n=>(n.Flex=({align:i="stretch",children:s,direction:o="row",gap:c=0,justify:d="start",wrap:u="nowrap",getHeight:h,getWidth:p,getCenterX:b,getCenterY:g,color:x})=>{let t=de(),a=j(),l=L(()=>({recalc(){let f=Number(c)||0,y=b(),w=g(),k=p(),P=h();a.x=y,a.y=w,a.width=k,a.height=P;let ut=t.getChildrenEntities().filter(Boolean).map(v=>v.getRect()).filter(v=>v.getFlag("flex-ignored")!==!0),S=o==="row",M=S?a.width:a.height,Rt=S?a.height:a.width,me=0,$=0,ye=[],Z=[];ut.forEach(v=>{let ee=S?v.width:v.height;me+ee>M&&u==="wrap"?(ye.push({height:$,items:Z}),Z=[v],me=ee,$=S?v.height:v.width):(Z.push(v),me+=ee+f,$=Math.max($,S?v.height:v.width))}),ye.push({height:$,items:Z});let be=0;ye.forEach((v,ee)=>{let I=v.items,D=I.reduce((E,te)=>E+(S?te.width:te.height),0)+f*(I.length-1),K=0;d==="center"&&(K=(M-D)/2),d==="end"&&(K=M-D),d==="space-between"&&(K=0),d==="space-around"&&(K=(M-D)/(I.length*2)),d==="space-evenly"&&(K=(M-D)/(I.length+1)),I.forEach((E,te)=>{E.z=a.z+1;let G=S?E.width:E.height,ne=S?E.height:E.width,re=0;i==="center"&&(re=(v.height-ne)/2),i==="end"&&(re=v.height-ne),i==="stretch"&&(S?E.height=v.height:E.width=v.height),S?(E.x=K+G/2,E.y=be+re+ne/2):(E.x=be+re+ne/2,E.y=K+G/2),d==="space-between"&&te<I.length-1?K+=G+f+(M-D)/(I.length-1):d==="space-around"?K+=G+f+(M-D)/I.length:d==="space-evenly"?K+=G+f+(M-D)/(I.length+1):K+=G+f}),be+=v.height+f})}}));return Q((f,y)=>{y.preventDefault(),f.fillStyle=x,f.fillRect(a.left,a.top,a.width,a.height)}),ce(()=>{fe(()=>{l.recalc()})}),J(n.Flex,()=>({controls:l})),s},n.GenericBox=({color:i,width:s=20,height:o=20,x:c=0,y:d=0})=>{let u=j();Y(()=>{u.width=s,u.height=o,u.x=c,u.y=d}),Q((h,p)=>{p.preventDefault(),h.fillStyle=i,h.fillRect(u.left,u.top,u.width,u.height)})}))(ot||={});0&&(module.exports={Kayla,KaylaContext,KaylaFragment,KaylaInternals,KaylaRect,LEA,UI,createContext,createElement,createGame,createReassignableObject,createRenderer,createScene,createUseHook,self,setLogLevel,useClick,useContext,useCurrentGame,useCurrentRenderer,useCurrentScene,useCurrentTicker,useDisposableRef,useEffect,useEntity,useExports,useFiber,useFiberControl,useGlobalClick,useInitialization,useNextStack,usePaint,useRect,useRef,useSelf,useShouldRefresh,useState,useTick,useViewportEffect});
package/dist/kayla.d.cts CHANGED
@@ -1,6 +1,6 @@
1
- import { F as FCProps, a as FCExports, b as FC } from './kayla-internals-CudoMM3W.cjs';
2
- export { E as ExportsOfFC, J as JSX, K as Kayla, c as KaylaClickType, d as KaylaContext, e as KaylaCustomHookConfig, f as KaylaElement, g as KaylaElementRef, h as KaylaExportables, i as KaylaExports, j as KaylaFiberControl, k as KaylaFragment, l as KaylaGame, m as KaylaInternals, n as KaylaRect, o as KaylaRef, p as KaylaRenderer, q as KaylaScene, r as KaylaState, P as PropOfFC, R as Reassignable, U as UnsafeKaylaFiber, s as createContext, t as createElement, u as createGame, v as createReassignableObject, w as createRenderer, x as createScene, y as createUseHook, z as self, A as setLogLevel, B as useClick, C as useContext, D as useCurrentGame, G as useCurrentRenderer, H as useCurrentScene, I as useCurrentTicker, L as useDisposableRef, M as useEffect, N as useEntity, O as useExports, Q as useFiber, S as useFiberControl, T as useGlobalClick, V as useInitialization, W as useNextStack, X as usePaint, Y as useRect, Z as useRef, _ as useSelf, $ as useShouldRefresh, a0 as useState, a1 as useTick } from './kayla-internals-CudoMM3W.cjs';
3
- export { L as LEA } from './lea-k7IGP_-W.cjs';
1
+ import { F as FCProps, a as FCExports, b as FC } from './kayla-internals-vuPhjkRg.cjs';
2
+ export { E as ExportsOfFC, J as JSX, K as Kayla, c as KaylaClickType, d as KaylaContext, e as KaylaCustomHookConfig, f as KaylaElement, g as KaylaElementRef, h as KaylaExportables, i as KaylaExports, j as KaylaFiberControl, k as KaylaFragment, l as KaylaGame, m as KaylaInternals, n as KaylaRect, o as KaylaRef, p as KaylaRenderer, q as KaylaScene, r as KaylaState, P as PropOfFC, R as Reassignable, U as UnsafeKaylaFiber, s as createContext, t as createElement, u as createGame, v as createReassignableObject, w as createRenderer, x as createScene, y as createUseHook, z as self, A as setLogLevel, B as useClick, C as useContext, D as useCurrentGame, G as useCurrentRenderer, H as useCurrentScene, I as useCurrentTicker, L as useDisposableRef, M as useEffect, N as useEntity, O as useExports, Q as useFiber, S as useFiberControl, T as useGlobalClick, V as useInitialization, W as useNextStack, X as usePaint, Y as useRect, Z as useRef, _ as useSelf, $ as useShouldRefresh, a0 as useState, a1 as useTick, a2 as useViewportEffect } from './kayla-internals-vuPhjkRg.cjs';
3
+ export { L as LEA } from './lea-B1DIEiLR.cjs';
4
4
 
5
5
  declare namespace UI {
6
6
  interface FlexProps extends FCProps {
package/dist/kayla.d.ts CHANGED
@@ -1,6 +1,6 @@
1
- import { F as FCProps, a as FCExports, b as FC } from './kayla-internals-8Xl7b2Jc.js';
2
- export { E as ExportsOfFC, J as JSX, K as Kayla, c as KaylaClickType, d as KaylaContext, e as KaylaCustomHookConfig, f as KaylaElement, g as KaylaElementRef, h as KaylaExportables, i as KaylaExports, j as KaylaFiberControl, k as KaylaFragment, l as KaylaGame, m as KaylaInternals, n as KaylaRect, o as KaylaRef, p as KaylaRenderer, q as KaylaScene, r as KaylaState, P as PropOfFC, R as Reassignable, U as UnsafeKaylaFiber, s as createContext, t as createElement, u as createGame, v as createReassignableObject, w as createRenderer, x as createScene, y as createUseHook, z as self, A as setLogLevel, B as useClick, C as useContext, D as useCurrentGame, G as useCurrentRenderer, H as useCurrentScene, I as useCurrentTicker, L as useDisposableRef, M as useEffect, N as useEntity, O as useExports, Q as useFiber, S as useFiberControl, T as useGlobalClick, V as useInitialization, W as useNextStack, X as usePaint, Y as useRect, Z as useRef, _ as useSelf, $ as useShouldRefresh, a0 as useState, a1 as useTick } from './kayla-internals-8Xl7b2Jc.js';
3
- export { L as LEA } from './lea-k7IGP_-W.js';
1
+ import { F as FCProps, a as FCExports, b as FC } from './kayla-internals-C8v5s-0r.js';
2
+ export { E as ExportsOfFC, J as JSX, K as Kayla, c as KaylaClickType, d as KaylaContext, e as KaylaCustomHookConfig, f as KaylaElement, g as KaylaElementRef, h as KaylaExportables, i as KaylaExports, j as KaylaFiberControl, k as KaylaFragment, l as KaylaGame, m as KaylaInternals, n as KaylaRect, o as KaylaRef, p as KaylaRenderer, q as KaylaScene, r as KaylaState, P as PropOfFC, R as Reassignable, U as UnsafeKaylaFiber, s as createContext, t as createElement, u as createGame, v as createReassignableObject, w as createRenderer, x as createScene, y as createUseHook, z as self, A as setLogLevel, B as useClick, C as useContext, D as useCurrentGame, G as useCurrentRenderer, H as useCurrentScene, I as useCurrentTicker, L as useDisposableRef, M as useEffect, N as useEntity, O as useExports, Q as useFiber, S as useFiberControl, T as useGlobalClick, V as useInitialization, W as useNextStack, X as usePaint, Y as useRect, Z as useRef, _ as useSelf, $ as useShouldRefresh, a0 as useState, a1 as useTick, a2 as useViewportEffect } from './kayla-internals-C8v5s-0r.js';
3
+ export { L as LEA } from './lea-B1DIEiLR.js';
4
4
 
5
5
  declare namespace UI {
6
6
  interface FlexProps extends FCProps {