{"version":3,"file":"create-effect.mjs","sources":["../../../../src/effects/utils/create-effect.ts"],"sourcesContent":["import {\n AnyResolvedKeyframe,\n UnresolvedValueKeyframe,\n} from \"../../animation/types\"\nimport { Schedule } from \"../../frameloop/types\"\nimport { MotionValue } from \"../../value\"\nimport { MotionValueState } from \"../MotionValueState\"\n\n/**\n * Returns true if the effect knows how to write to `subject`.\n */\nexport type EffectTest = (\n subject: unknown\n) => subject is Subject\n\n/**\n * Reads the current value of `key` from `subject`, used as the initial\n * keyframe when `animate()` creates a motion value for the subject.\n * Returns `undefined` when the value can't be read.\n *\n * `keyframes` is the target being animated to, so effects can match\n * the format of the initial value (for instance color vs numeric).\n */\nexport type EffectRead = (\n subject: Subject,\n key: string,\n keyframes?: UnresolvedValueKeyframe | UnresolvedValueKeyframe[]\n) => AnyResolvedKeyframe | undefined\n\nexport interface EffectOptions {\n test?: EffectTest\n read?: EffectRead\n\n /**\n * Frameloop step writes are scheduled in. Defaults to `frame.render`.\n */\n step?: Schedule\n}\n\nexport interface Effect\n extends EffectOptions {\n (subject: Subject, values: Record): VoidFunction\n\n /**\n * Returns the motion value currently bound to `key` on `subject`, if any.\n */\n get(subject: Subject, key: string): MotionValue | undefined\n\n /**\n * Write `subject`'s pending values now rather than in the next frame,\n * e.g. so it can be measured with a target applied.\n */\n flush(subject: Subject): void\n\n /**\n * The state holding the motion values bound to `subject`, if any have\n * been, so they can be handed to another renderer.\n */\n state(subject: Subject): MotionValueState | undefined\n}\n\n/**\n * An effect that can be registered with `animate.addEffect()`.\n */\nexport interface AnimateEffect\n extends Effect {\n test: EffectTest\n read: EffectRead\n}\n\nexport type AddEffectValue = (\n subject: Subject,\n state: MotionValueState,\n key: string,\n value: MotionValue\n) => VoidFunction\n\nexport function createEffect(\n addValue: AddEffectValue,\n options: EffectOptions & {\n test: EffectTest\n read: EffectRead\n }\n): AnimateEffect\nexport function createEffect(\n addValue: AddEffectValue,\n options?: EffectOptions\n): Effect\nexport function createEffect(\n addValue: AddEffectValue,\n { step, ...options }: EffectOptions = {}\n): Effect {\n const stateCache = new WeakMap()\n\n const effect = (\n subject: Subject,\n values: Record\n ): VoidFunction => {\n const state = stateCache.get(subject) ?? new MotionValueState(step)\n\n stateCache.set(subject, state)\n\n const subscriptions: VoidFunction[] = []\n\n for (const key in values) {\n const value = values[key]\n const remove = addValue(subject, state, key, value)\n subscriptions.push(remove)\n }\n\n return () => {\n for (const cancel of subscriptions) cancel()\n }\n }\n\n return Object.assign(effect, options, {\n get: (subject: Subject, key: string) =>\n stateCache.get(subject)?.get(key),\n flush: (subject: Subject) => stateCache.get(subject)?.flush(),\n state: (subject: Subject) => stateCache.get(subject),\n })\n}\n"],"names":[],"mappings":";;AAwFM,SAAU,YAAY,CACxB,QAAiC,EACjC,EAAE,IAAI,EAAE,GAAG,OAAO,EAAA,GAA6B,EAAE,EAAA;AAEjD,IAAA,MAAM,UAAU,GAAG,IAAI,OAAO,EAA6B;AAE3D,IAAA,MAAM,MAAM,GAAG,CACX,OAAgB,EAChB,MAAmC,KACrB;AACd,QAAA,MAAM,KAAK,GAAG,UAAU,CAAC,GAAG,CAAC,OAAO,CAAC,IAAI,IAAI,gBAAgB,CAAC,IAAI,CAAC;AAEnE,QAAA,UAAU,CAAC,GAAG,CAAC,OAAO,EAAE,KAAK,CAAC;QAE9B,MAAM,aAAa,GAAmB,EAAE;AAExC,QAAA,KAAK,MAAM,GAAG,IAAI,MAAM,EAAE;AACtB,YAAA,MAAM,KAAK,GAAG,MAAM,CAAC,GAAG,CAAC;AACzB,YAAA,MAAM,MAAM,GAAG,QAAQ,CAAC,OAAO,EAAE,KAAK,EAAE,GAAG,EAAE,KAAK,CAAC;AACnD,YAAA,aAAa,CAAC,IAAI,CAAC,MAAM,CAAC;QAC9B;AAEA,QAAA,OAAO,MAAK;YACR,KAAK,MAAM,MAAM,IAAI,aAAa;AAAE,gBAAA,MAAM,EAAE;AAChD,QAAA,CAAC;AACL,IAAA,CAAC;AAED,IAAA,OAAO,MAAM,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,EAAE;AAClC,QAAA,GAAG,EAAE,CAAC,OAAgB,EAAE,GAAW,KAC/B,UAAU,CAAC,GAAG,CAAC,OAAO,CAAC,EAAE,GAAG,CAAC,GAAG,CAAC;AACrC,QAAA,KAAK,EAAE,CAAC,OAAgB,KAAK,UAAU,CAAC,GAAG,CAAC,OAAO,CAAC,EAAE,KAAK,EAAE;QAC7D,KAAK,EAAE,CAAC,OAAgB,KAAK,UAAU,CAAC,GAAG,CAAC,OAAO,CAAC;AACvD,KAAA,CAAC;AACN;;;;"}