@videojs/spf 10.0.0-beta.22 → 10.0.0-beta.24
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/{dev/core → default/core/actors}/create-machine-actor.js +3 -3
- package/dist/default/core/actors/create-machine-actor.js.map +1 -0
- package/dist/default/core/{create-transition-actor.js → actors/create-transition-actor.js} +3 -3
- package/dist/default/core/actors/create-transition-actor.js.map +1 -0
- package/dist/default/core/composition/create-composition.js +85 -0
- package/dist/default/core/composition/create-composition.js.map +1 -0
- package/dist/default/core/composition/share-signals.js +37 -0
- package/dist/default/core/composition/share-signals.js.map +1 -0
- package/dist/{dev/core → default/core/reactors}/create-machine-reactor.js +4 -4
- package/dist/default/core/reactors/create-machine-reactor.js.map +1 -0
- package/dist/default/core/signals/primitives.js +33 -11
- package/dist/default/core/signals/primitives.js.map +1 -1
- package/dist/default/core/{task.js → tasks/task.js} +2 -2
- package/dist/default/core/tasks/task.js.map +1 -0
- package/dist/default/dom.js +9 -10
- package/dist/default/hls.js +3 -0
- package/dist/default/index.js +12 -3
- package/dist/default/index.js.map +1 -1
- package/dist/default/media/abr/quality-selection.js +83 -0
- package/dist/default/media/abr/quality-selection.js.map +1 -0
- package/dist/default/{core → media}/buffer/back-buffer.js +2 -2
- package/dist/default/media/buffer/back-buffer.js.map +1 -0
- package/dist/{dev/core → default/media}/buffer/forward-buffer.js +14 -2
- package/dist/default/media/buffer/forward-buffer.js.map +1 -0
- package/dist/{dev/dom/media → default/media/dom/mse}/append-segment.js +1 -1
- package/dist/default/media/dom/mse/append-segment.js.map +1 -0
- package/dist/default/{dom/media → media/dom/mse}/buffer-flusher.js +1 -1
- package/dist/default/media/dom/mse/buffer-flusher.js.map +1 -0
- package/dist/default/media/dom/mse/duration.js +78 -0
- package/dist/default/media/dom/mse/duration.js.map +1 -0
- package/dist/default/media/dom/mse/end-of-stream.js +20 -0
- package/dist/default/media/dom/mse/end-of-stream.js.map +1 -0
- package/dist/default/{dom/media → media/dom/mse}/mediasource-setup.js +63 -18
- package/dist/default/media/dom/mse/mediasource-setup.js.map +1 -0
- package/dist/default/{dom/text/parse-vtt-segment.js → media/dom/text/resolve-vtt-segment.js} +5 -5
- package/dist/default/media/dom/text/resolve-vtt-segment.js.map +1 -0
- package/dist/default/media/dom/text/text-track-slots.js +69 -0
- package/dist/default/media/dom/text/text-track-slots.js.map +1 -0
- package/dist/{dev/core → default/media}/hls/parse-attributes.js +1 -1
- package/dist/default/media/hls/parse-attributes.js.map +1 -0
- package/dist/{dev/core → default/media}/hls/parse-media-playlist.js +1 -1
- package/dist/default/media/hls/parse-media-playlist.js.map +1 -0
- package/dist/{dev/core → default/media}/hls/parse-multivariant.js +2 -2
- package/dist/default/media/hls/parse-multivariant.js.map +1 -0
- package/dist/default/{core → media}/hls/resolve-url.js +1 -1
- package/dist/default/media/hls/resolve-url.js.map +1 -0
- package/dist/default/media/primitives/select-tracks.js +45 -0
- package/dist/default/media/primitives/select-tracks.js.map +1 -0
- package/dist/default/media/types/index.js +36 -0
- package/dist/default/media/types/index.js.map +1 -0
- package/dist/default/media/utils/preload.js +22 -0
- package/dist/default/media/utils/preload.js.map +1 -0
- package/dist/default/media/utils/track-selection.js +47 -0
- package/dist/default/media/utils/track-selection.js.map +1 -0
- package/dist/default/media/utils/tracks.js +103 -0
- package/dist/default/media/utils/tracks.js.map +1 -0
- package/dist/default/{core/abr → network}/bandwidth-estimator.js +6 -5
- package/dist/default/network/bandwidth-estimator.js.map +1 -0
- package/dist/{dev/dom → default}/network/chunked-stream-iterable.js +1 -1
- package/dist/default/network/chunked-stream-iterable.js.map +1 -0
- package/dist/{dev/core/abr → default/network}/ewma.js +1 -1
- package/dist/default/network/ewma.js.map +1 -0
- package/dist/default/network/fetch.js +109 -0
- package/dist/default/network/fetch.js.map +1 -0
- package/dist/{dev/dom/features/segment-loader-actor.js → default/playback/actors/dom/segment-loader.js} +24 -15
- package/dist/default/playback/actors/dom/segment-loader.js.map +1 -0
- package/dist/{dev/dom/media/source-buffer-actor.js → default/playback/actors/dom/source-buffer.js} +8 -8
- package/dist/default/playback/actors/dom/source-buffer.js.map +1 -0
- package/dist/{dev/dom/features/text-tracks-actor.js → default/playback/actors/dom/text-tracks.js} +7 -3
- package/dist/default/playback/actors/dom/text-tracks.js.map +1 -0
- package/dist/default/playback/actors/text-track-segment-loader.js +135 -0
- package/dist/default/playback/actors/text-track-segment-loader.js.map +1 -0
- package/dist/default/playback/behaviors/calculate-presentation-duration.js +58 -0
- package/dist/default/playback/behaviors/calculate-presentation-duration.js.map +1 -0
- package/dist/default/playback/behaviors/dom/end-of-stream.js +178 -0
- package/dist/default/playback/behaviors/dom/end-of-stream.js.map +1 -0
- package/dist/default/playback/behaviors/dom/load-segments.js +177 -0
- package/dist/default/playback/behaviors/dom/load-segments.js.map +1 -0
- package/dist/default/playback/behaviors/dom/setup-buffer-actors.js +173 -0
- package/dist/default/playback/behaviors/dom/setup-buffer-actors.js.map +1 -0
- package/dist/default/playback/behaviors/dom/setup-mediasource.js +89 -0
- package/dist/default/playback/behaviors/dom/setup-mediasource.js.map +1 -0
- package/dist/default/playback/behaviors/dom/setup-text-track-actors.js +54 -0
- package/dist/default/playback/behaviors/dom/setup-text-track-actors.js.map +1 -0
- package/dist/default/playback/behaviors/dom/sync-text-tracks.js +99 -0
- package/dist/default/playback/behaviors/dom/sync-text-tracks.js.map +1 -0
- package/dist/default/playback/behaviors/dom/track-current-time.js +46 -0
- package/dist/default/playback/behaviors/dom/track-current-time.js.map +1 -0
- package/dist/default/playback/behaviors/dom/track-load-triggers.js +94 -0
- package/dist/default/playback/behaviors/dom/track-load-triggers.js.map +1 -0
- package/dist/default/playback/behaviors/dom/track-playback-rate.js +37 -0
- package/dist/default/playback/behaviors/dom/track-playback-rate.js.map +1 -0
- package/dist/default/playback/behaviors/dom/update-mediasource-duration.js +90 -0
- package/dist/default/playback/behaviors/dom/update-mediasource-duration.js.map +1 -0
- package/dist/default/playback/behaviors/quality-switching.js +96 -0
- package/dist/default/playback/behaviors/quality-switching.js.map +1 -0
- package/dist/default/playback/behaviors/resolve-presentation.js +85 -0
- package/dist/default/playback/behaviors/resolve-presentation.js.map +1 -0
- package/dist/default/playback/behaviors/resolve-track.js +97 -0
- package/dist/default/playback/behaviors/resolve-track.js.map +1 -0
- package/dist/default/playback/behaviors/select-tracks.js +132 -0
- package/dist/default/playback/behaviors/select-tracks.js.map +1 -0
- package/dist/default/playback/behaviors/sync-preload.js +59 -0
- package/dist/default/playback/behaviors/sync-preload.js.map +1 -0
- package/dist/default/playback/behaviors/track-types.js +61 -0
- package/dist/default/playback/behaviors/track-types.js.map +1 -0
- package/dist/default/{dom/playback-engine → playback/engines/hls}/adapter.js +36 -25
- package/dist/default/playback/engines/hls/adapter.js.map +1 -0
- package/dist/default/playback/engines/hls/engine.js +102 -0
- package/dist/default/playback/engines/hls/engine.js.map +1 -0
- package/dist/dev/core/{actor.d.ts → actors/actor.d.ts} +2 -2
- package/dist/dev/core/actors/actor.d.ts.map +1 -0
- package/dist/dev/core/actors/create-machine-actor.d.ts +125 -0
- package/dist/dev/core/actors/create-machine-actor.d.ts.map +1 -0
- package/dist/{default/core → dev/core/actors}/create-machine-actor.js +3 -3
- package/dist/dev/core/actors/create-machine-actor.js.map +1 -0
- package/dist/dev/core/actors/create-transition-actor.d.ts +42 -0
- package/dist/dev/core/actors/create-transition-actor.d.ts.map +1 -0
- package/dist/dev/core/{create-transition-actor.js → actors/create-transition-actor.js} +3 -3
- package/dist/dev/core/actors/create-transition-actor.js.map +1 -0
- package/dist/dev/core/composition/create-composition.d.ts +274 -0
- package/dist/dev/core/composition/create-composition.d.ts.map +1 -0
- package/dist/dev/core/composition/create-composition.js +85 -0
- package/dist/dev/core/composition/create-composition.js.map +1 -0
- package/dist/dev/core/composition/share-signals.d.ts +45 -0
- package/dist/dev/core/composition/share-signals.d.ts.map +1 -0
- package/dist/dev/core/composition/share-signals.js +37 -0
- package/dist/dev/core/composition/share-signals.js.map +1 -0
- package/dist/dev/core/machine.d.ts +0 -1
- package/dist/dev/core/machine.d.ts.map +1 -1
- package/dist/dev/core/reactors/create-machine-reactor.d.ts +93 -0
- package/dist/dev/core/reactors/create-machine-reactor.d.ts.map +1 -0
- package/dist/{default/core → dev/core/reactors}/create-machine-reactor.js +4 -4
- package/dist/dev/core/reactors/create-machine-reactor.js.map +1 -0
- package/dist/dev/core/signals/primitives.d.ts +38 -1
- package/dist/dev/core/signals/primitives.d.ts.map +1 -1
- package/dist/dev/core/signals/primitives.js +33 -11
- package/dist/dev/core/signals/primitives.js.map +1 -1
- package/dist/dev/core/tasks/task.d.ts +115 -0
- package/dist/dev/core/tasks/task.d.ts.map +1 -0
- package/dist/dev/core/{task.js → tasks/task.js} +2 -2
- package/dist/dev/core/tasks/task.js.map +1 -0
- package/dist/dev/dom.d.ts +9 -10
- package/dist/dev/dom.js +9 -10
- package/dist/dev/hls.d.ts +3 -0
- package/dist/dev/hls.js +3 -0
- package/dist/dev/index.d.ts +15 -3
- package/dist/dev/index.d.ts.map +1 -1
- package/dist/dev/index.js +12 -3
- package/dist/dev/index.js.map +1 -1
- package/dist/dev/media/abr/quality-selection.d.ts +22 -0
- package/dist/dev/media/abr/quality-selection.d.ts.map +1 -0
- package/dist/dev/media/abr/quality-selection.js +83 -0
- package/dist/dev/media/abr/quality-selection.js.map +1 -0
- package/dist/dev/media/buffer/back-buffer.d.ts +14 -0
- package/dist/dev/media/buffer/back-buffer.d.ts.map +1 -0
- package/dist/dev/{core → media}/buffer/back-buffer.js +2 -2
- package/dist/dev/media/buffer/back-buffer.js.map +1 -0
- package/dist/dev/media/buffer/forward-buffer.d.ts +14 -0
- package/dist/dev/media/buffer/forward-buffer.d.ts.map +1 -0
- package/dist/{default/core → dev/media}/buffer/forward-buffer.js +14 -2
- package/dist/dev/media/buffer/forward-buffer.js.map +1 -0
- package/dist/dev/{dom/media → media/dom/mse}/append-segment.d.ts +1 -1
- package/dist/dev/media/dom/mse/append-segment.d.ts.map +1 -0
- package/dist/{default/dom/media → dev/media/dom/mse}/append-segment.js +1 -1
- package/dist/dev/media/dom/mse/append-segment.js.map +1 -0
- package/dist/dev/{dom/media → media/dom/mse}/buffer-flusher.d.ts +1 -1
- package/dist/dev/media/dom/mse/buffer-flusher.d.ts.map +1 -0
- package/dist/dev/{dom/media → media/dom/mse}/buffer-flusher.js +1 -1
- package/dist/dev/media/dom/mse/buffer-flusher.js.map +1 -0
- package/dist/dev/media/dom/mse/duration.js +78 -0
- package/dist/dev/media/dom/mse/duration.js.map +1 -0
- package/dist/dev/media/dom/mse/end-of-stream.js +20 -0
- package/dist/dev/media/dom/mse/end-of-stream.js.map +1 -0
- package/dist/dev/{dom/media → media/dom/mse}/mediasource-setup.js +63 -18
- package/dist/dev/media/dom/mse/mediasource-setup.js.map +1 -0
- package/dist/dev/media/dom/text/resolve-vtt-segment.d.ts +12 -0
- package/dist/dev/media/dom/text/resolve-vtt-segment.d.ts.map +1 -0
- package/dist/dev/{dom/text/parse-vtt-segment.js → media/dom/text/resolve-vtt-segment.js} +5 -5
- package/dist/dev/media/dom/text/resolve-vtt-segment.js.map +1 -0
- package/dist/dev/media/dom/text/text-track-slots.d.ts +31 -0
- package/dist/dev/media/dom/text/text-track-slots.d.ts.map +1 -0
- package/dist/dev/media/dom/text/text-track-slots.js +69 -0
- package/dist/dev/media/dom/text/text-track-slots.js.map +1 -0
- package/dist/{default/core → dev/media}/hls/parse-attributes.js +1 -1
- package/dist/dev/media/hls/parse-attributes.js.map +1 -0
- package/dist/{default/core → dev/media}/hls/parse-media-playlist.js +1 -1
- package/dist/dev/media/hls/parse-media-playlist.js.map +1 -0
- package/dist/{default/core → dev/media}/hls/parse-multivariant.js +2 -2
- package/dist/dev/media/hls/parse-multivariant.js.map +1 -0
- package/dist/dev/{core → media}/hls/resolve-url.js +1 -1
- package/dist/dev/media/hls/resolve-url.js.map +1 -0
- package/dist/dev/media/primitives/select-tracks.js +45 -0
- package/dist/dev/media/primitives/select-tracks.js.map +1 -0
- package/dist/dev/{core → media}/types/index.d.ts +30 -2
- package/dist/dev/media/types/index.d.ts.map +1 -0
- package/dist/dev/media/types/index.js +36 -0
- package/dist/dev/media/types/index.js.map +1 -0
- package/dist/dev/media/utils/preload.js +22 -0
- package/dist/dev/media/utils/preload.js.map +1 -0
- package/dist/dev/media/utils/track-selection.js +47 -0
- package/dist/dev/media/utils/track-selection.js.map +1 -0
- package/dist/dev/media/utils/tracks.js +103 -0
- package/dist/dev/media/utils/tracks.js.map +1 -0
- package/dist/dev/{core/abr → network}/bandwidth-estimator.d.ts +17 -2
- package/dist/dev/network/bandwidth-estimator.d.ts.map +1 -0
- package/dist/dev/{core/abr → network}/bandwidth-estimator.js +6 -5
- package/dist/dev/network/bandwidth-estimator.js.map +1 -0
- package/dist/{default/dom → dev}/network/chunked-stream-iterable.js +1 -1
- package/dist/dev/network/chunked-stream-iterable.js.map +1 -0
- package/dist/{default/core/abr → dev/network}/ewma.js +1 -1
- package/dist/dev/network/ewma.js.map +1 -0
- package/dist/dev/network/fetch.js +109 -0
- package/dist/dev/network/fetch.js.map +1 -0
- package/dist/dev/playback/actors/dom/segment-loader.d.ts +36 -0
- package/dist/dev/playback/actors/dom/segment-loader.d.ts.map +1 -0
- package/dist/{default/dom/features/segment-loader-actor.js → dev/playback/actors/dom/segment-loader.js} +24 -15
- package/dist/dev/playback/actors/dom/segment-loader.js.map +1 -0
- package/dist/dev/{dom/media/source-buffer-actor.d.ts → playback/actors/dom/source-buffer.d.ts} +5 -5
- package/dist/dev/playback/actors/dom/source-buffer.d.ts.map +1 -0
- package/dist/{default/dom/media/source-buffer-actor.js → dev/playback/actors/dom/source-buffer.js} +8 -8
- package/dist/dev/playback/actors/dom/source-buffer.js.map +1 -0
- package/dist/dev/playback/actors/dom/text-tracks.d.ts +1 -0
- package/dist/{default/dom/features/text-tracks-actor.js → dev/playback/actors/dom/text-tracks.js} +7 -3
- package/dist/dev/playback/actors/dom/text-tracks.js.map +1 -0
- package/dist/dev/playback/actors/text-track-segment-loader.d.ts +59 -0
- package/dist/dev/playback/actors/text-track-segment-loader.d.ts.map +1 -0
- package/dist/dev/playback/actors/text-track-segment-loader.js +135 -0
- package/dist/dev/playback/actors/text-track-segment-loader.js.map +1 -0
- package/dist/dev/playback/actors/text-tracks.d.ts +42 -0
- package/dist/dev/playback/actors/text-tracks.d.ts.map +1 -0
- package/dist/dev/playback/behaviors/calculate-presentation-duration.d.ts +17 -0
- package/dist/dev/playback/behaviors/calculate-presentation-duration.d.ts.map +1 -0
- package/dist/dev/playback/behaviors/calculate-presentation-duration.js +58 -0
- package/dist/dev/playback/behaviors/calculate-presentation-duration.js.map +1 -0
- package/dist/dev/playback/behaviors/dom/end-of-stream.js +178 -0
- package/dist/dev/playback/behaviors/dom/end-of-stream.js.map +1 -0
- package/dist/dev/playback/behaviors/dom/load-segments.d.ts +62 -0
- package/dist/dev/playback/behaviors/dom/load-segments.d.ts.map +1 -0
- package/dist/dev/playback/behaviors/dom/load-segments.js +177 -0
- package/dist/dev/playback/behaviors/dom/load-segments.js.map +1 -0
- package/dist/dev/playback/behaviors/dom/setup-buffer-actors.js +173 -0
- package/dist/dev/playback/behaviors/dom/setup-buffer-actors.js.map +1 -0
- package/dist/dev/playback/behaviors/dom/setup-mediasource.js +89 -0
- package/dist/dev/playback/behaviors/dom/setup-mediasource.js.map +1 -0
- package/dist/dev/playback/behaviors/dom/setup-text-track-actors.d.ts +31 -0
- package/dist/dev/playback/behaviors/dom/setup-text-track-actors.d.ts.map +1 -0
- package/dist/dev/playback/behaviors/dom/setup-text-track-actors.js +54 -0
- package/dist/dev/playback/behaviors/dom/setup-text-track-actors.js.map +1 -0
- package/dist/dev/playback/behaviors/dom/sync-text-tracks.js +99 -0
- package/dist/dev/playback/behaviors/dom/sync-text-tracks.js.map +1 -0
- package/dist/dev/playback/behaviors/dom/track-current-time.d.ts +34 -0
- package/dist/dev/playback/behaviors/dom/track-current-time.d.ts.map +1 -0
- package/dist/dev/playback/behaviors/dom/track-current-time.js +46 -0
- package/dist/dev/playback/behaviors/dom/track-current-time.js.map +1 -0
- package/dist/dev/playback/behaviors/dom/track-load-triggers.d.ts +48 -0
- package/dist/dev/playback/behaviors/dom/track-load-triggers.d.ts.map +1 -0
- package/dist/dev/playback/behaviors/dom/track-load-triggers.js +94 -0
- package/dist/dev/playback/behaviors/dom/track-load-triggers.js.map +1 -0
- package/dist/dev/playback/behaviors/dom/track-playback-rate.d.ts +34 -0
- package/dist/dev/playback/behaviors/dom/track-playback-rate.d.ts.map +1 -0
- package/dist/dev/playback/behaviors/dom/track-playback-rate.js +37 -0
- package/dist/dev/playback/behaviors/dom/track-playback-rate.js.map +1 -0
- package/dist/dev/playback/behaviors/dom/update-mediasource-duration.js +90 -0
- package/dist/dev/playback/behaviors/dom/update-mediasource-duration.js.map +1 -0
- package/dist/dev/playback/behaviors/quality-switching.js +96 -0
- package/dist/dev/playback/behaviors/quality-switching.js.map +1 -0
- package/dist/dev/playback/behaviors/resolve-presentation.d.ts +7 -0
- package/dist/dev/playback/behaviors/resolve-presentation.d.ts.map +1 -0
- package/dist/dev/playback/behaviors/resolve-presentation.js +85 -0
- package/dist/dev/playback/behaviors/resolve-presentation.js.map +1 -0
- package/dist/dev/playback/behaviors/resolve-track.js +97 -0
- package/dist/dev/playback/behaviors/resolve-track.js.map +1 -0
- package/dist/dev/playback/behaviors/select-tracks.js +132 -0
- package/dist/dev/playback/behaviors/select-tracks.js.map +1 -0
- package/dist/dev/playback/behaviors/sync-preload.js +59 -0
- package/dist/dev/playback/behaviors/sync-preload.js.map +1 -0
- package/dist/dev/playback/behaviors/track-types.js +61 -0
- package/dist/dev/playback/behaviors/track-types.js.map +1 -0
- package/dist/dev/{dom/playback-engine → playback/engines/hls}/adapter.d.ts +14 -10
- package/dist/dev/playback/engines/hls/adapter.d.ts.map +1 -0
- package/dist/dev/{dom/playback-engine → playback/engines/hls}/adapter.js +36 -25
- package/dist/dev/playback/engines/hls/adapter.js.map +1 -0
- package/dist/dev/playback/engines/hls/engine.d.ts +177 -0
- package/dist/dev/playback/engines/hls/engine.d.ts.map +1 -0
- package/dist/dev/playback/engines/hls/engine.js +102 -0
- package/dist/dev/playback/engines/hls/engine.js.map +1 -0
- package/package.json +8 -9
- package/dist/default/core/abr/bandwidth-estimator.js.map +0 -1
- package/dist/default/core/abr/ewma.js.map +0 -1
- package/dist/default/core/abr/quality-selection.js +0 -53
- package/dist/default/core/abr/quality-selection.js.map +0 -1
- package/dist/default/core/buffer/back-buffer.js.map +0 -1
- package/dist/default/core/buffer/forward-buffer.js.map +0 -1
- package/dist/default/core/create-machine-actor.js.map +0 -1
- package/dist/default/core/create-machine-reactor.js.map +0 -1
- package/dist/default/core/create-transition-actor.js.map +0 -1
- package/dist/default/core/features/calculate-presentation-duration.js +0 -53
- package/dist/default/core/features/calculate-presentation-duration.js.map +0 -1
- package/dist/default/core/features/quality-switching.js +0 -69
- package/dist/default/core/features/quality-switching.js.map +0 -1
- package/dist/default/core/features/resolve-presentation.js +0 -73
- package/dist/default/core/features/resolve-presentation.js.map +0 -1
- package/dist/default/core/features/resolve-track.js +0 -66
- package/dist/default/core/features/resolve-track.js.map +0 -1
- package/dist/default/core/features/select-tracks.js +0 -130
- package/dist/default/core/features/select-tracks.js.map +0 -1
- package/dist/default/core/features/sync-preload-attribute.js +0 -26
- package/dist/default/core/features/sync-preload-attribute.js.map +0 -1
- package/dist/default/core/hls/parse-attributes.js.map +0 -1
- package/dist/default/core/hls/parse-media-playlist.js.map +0 -1
- package/dist/default/core/hls/parse-multivariant.js.map +0 -1
- package/dist/default/core/hls/resolve-url.js.map +0 -1
- package/dist/default/core/task.js.map +0 -1
- package/dist/default/core/types/index.js +0 -15
- package/dist/default/core/types/index.js.map +0 -1
- package/dist/default/core/utils/generate-id.js +0 -21
- package/dist/default/core/utils/generate-id.js.map +0 -1
- package/dist/default/core/utils/track-selection.js +0 -39
- package/dist/default/core/utils/track-selection.js.map +0 -1
- package/dist/default/dom/features/end-of-stream.js +0 -145
- package/dist/default/dom/features/end-of-stream.js.map +0 -1
- package/dist/default/dom/features/load-segments.js +0 -192
- package/dist/default/dom/features/load-segments.js.map +0 -1
- package/dist/default/dom/features/load-text-track-cues.js +0 -104
- package/dist/default/dom/features/load-text-track-cues.js.map +0 -1
- package/dist/default/dom/features/segment-loader-actor.js.map +0 -1
- package/dist/default/dom/features/setup-mediasource.js +0 -48
- package/dist/default/dom/features/setup-mediasource.js.map +0 -1
- package/dist/default/dom/features/setup-sourcebuffer.js +0 -78
- package/dist/default/dom/features/setup-sourcebuffer.js.map +0 -1
- package/dist/default/dom/features/sync-text-tracks.js +0 -95
- package/dist/default/dom/features/sync-text-tracks.js.map +0 -1
- package/dist/default/dom/features/text-track-segment-loader-actor.js +0 -55
- package/dist/default/dom/features/text-track-segment-loader-actor.js.map +0 -1
- package/dist/default/dom/features/text-tracks-actor.js.map +0 -1
- package/dist/default/dom/features/track-current-time.js +0 -49
- package/dist/default/dom/features/track-current-time.js.map +0 -1
- package/dist/default/dom/features/track-playback-initiated.js +0 -66
- package/dist/default/dom/features/track-playback-initiated.js.map +0 -1
- package/dist/default/dom/features/track-playback-rate.js +0 -32
- package/dist/default/dom/features/track-playback-rate.js.map +0 -1
- package/dist/default/dom/features/update-duration.js +0 -78
- package/dist/default/dom/features/update-duration.js.map +0 -1
- package/dist/default/dom/media/append-segment.js.map +0 -1
- package/dist/default/dom/media/buffer-flusher.js.map +0 -1
- package/dist/default/dom/media/mediasource-setup.js.map +0 -1
- package/dist/default/dom/media/source-buffer-actor.js.map +0 -1
- package/dist/default/dom/network/chunked-stream-iterable.js.map +0 -1
- package/dist/default/dom/network/fetch.js +0 -54
- package/dist/default/dom/network/fetch.js.map +0 -1
- package/dist/default/dom/playback-engine/adapter.js.map +0 -1
- package/dist/default/dom/playback-engine/engine.js +0 -142
- package/dist/default/dom/playback-engine/engine.js.map +0 -1
- package/dist/default/dom/playback-engine.js +0 -4
- package/dist/default/dom/text/parse-vtt-segment.js.map +0 -1
- package/dist/dev/core/abr/bandwidth-estimator.d.ts.map +0 -1
- package/dist/dev/core/abr/bandwidth-estimator.js.map +0 -1
- package/dist/dev/core/abr/ewma.js.map +0 -1
- package/dist/dev/core/abr/quality-selection.js +0 -53
- package/dist/dev/core/abr/quality-selection.js.map +0 -1
- package/dist/dev/core/actor.d.ts.map +0 -1
- package/dist/dev/core/buffer/back-buffer.js.map +0 -1
- package/dist/dev/core/buffer/forward-buffer.js.map +0 -1
- package/dist/dev/core/create-machine-actor.d.ts +0 -12
- package/dist/dev/core/create-machine-actor.d.ts.map +0 -1
- package/dist/dev/core/create-machine-actor.js.map +0 -1
- package/dist/dev/core/create-machine-reactor.d.ts +0 -8
- package/dist/dev/core/create-machine-reactor.d.ts.map +0 -1
- package/dist/dev/core/create-machine-reactor.js.map +0 -1
- package/dist/dev/core/create-transition-actor.d.ts +0 -23
- package/dist/dev/core/create-transition-actor.d.ts.map +0 -1
- package/dist/dev/core/create-transition-actor.js.map +0 -1
- package/dist/dev/core/features/calculate-presentation-duration.js +0 -53
- package/dist/dev/core/features/calculate-presentation-duration.js.map +0 -1
- package/dist/dev/core/features/quality-switching.js +0 -69
- package/dist/dev/core/features/quality-switching.js.map +0 -1
- package/dist/dev/core/features/resolve-presentation.js +0 -73
- package/dist/dev/core/features/resolve-presentation.js.map +0 -1
- package/dist/dev/core/features/resolve-track.js +0 -66
- package/dist/dev/core/features/resolve-track.js.map +0 -1
- package/dist/dev/core/features/select-tracks.js +0 -130
- package/dist/dev/core/features/select-tracks.js.map +0 -1
- package/dist/dev/core/features/sync-preload-attribute.js +0 -26
- package/dist/dev/core/features/sync-preload-attribute.js.map +0 -1
- package/dist/dev/core/hls/parse-attributes.js.map +0 -1
- package/dist/dev/core/hls/parse-media-playlist.js.map +0 -1
- package/dist/dev/core/hls/parse-multivariant.js.map +0 -1
- package/dist/dev/core/hls/resolve-url.js.map +0 -1
- package/dist/dev/core/task.js.map +0 -1
- package/dist/dev/core/types/index.d.ts.map +0 -1
- package/dist/dev/core/types/index.js +0 -15
- package/dist/dev/core/types/index.js.map +0 -1
- package/dist/dev/core/utils/generate-id.js +0 -21
- package/dist/dev/core/utils/generate-id.js.map +0 -1
- package/dist/dev/core/utils/track-selection.d.ts +0 -16
- package/dist/dev/core/utils/track-selection.d.ts.map +0 -1
- package/dist/dev/core/utils/track-selection.js +0 -39
- package/dist/dev/core/utils/track-selection.js.map +0 -1
- package/dist/dev/dom/features/end-of-stream.js +0 -145
- package/dist/dev/dom/features/end-of-stream.js.map +0 -1
- package/dist/dev/dom/features/load-segments.d.ts +0 -72
- package/dist/dev/dom/features/load-segments.d.ts.map +0 -1
- package/dist/dev/dom/features/load-segments.js +0 -192
- package/dist/dev/dom/features/load-segments.js.map +0 -1
- package/dist/dev/dom/features/load-text-track-cues.d.ts +0 -85
- package/dist/dev/dom/features/load-text-track-cues.d.ts.map +0 -1
- package/dist/dev/dom/features/load-text-track-cues.js +0 -104
- package/dist/dev/dom/features/load-text-track-cues.js.map +0 -1
- package/dist/dev/dom/features/segment-loader-actor.d.ts +0 -1
- package/dist/dev/dom/features/segment-loader-actor.js.map +0 -1
- package/dist/dev/dom/features/setup-mediasource.js +0 -48
- package/dist/dev/dom/features/setup-mediasource.js.map +0 -1
- package/dist/dev/dom/features/setup-sourcebuffer.d.ts +0 -9
- package/dist/dev/dom/features/setup-sourcebuffer.d.ts.map +0 -1
- package/dist/dev/dom/features/setup-sourcebuffer.js +0 -78
- package/dist/dev/dom/features/setup-sourcebuffer.js.map +0 -1
- package/dist/dev/dom/features/sync-text-tracks.js +0 -95
- package/dist/dev/dom/features/sync-text-tracks.js.map +0 -1
- package/dist/dev/dom/features/text-track-segment-loader-actor.d.ts +0 -12
- package/dist/dev/dom/features/text-track-segment-loader-actor.d.ts.map +0 -1
- package/dist/dev/dom/features/text-track-segment-loader-actor.js +0 -55
- package/dist/dev/dom/features/text-track-segment-loader-actor.js.map +0 -1
- package/dist/dev/dom/features/text-tracks-actor.d.ts +0 -31
- package/dist/dev/dom/features/text-tracks-actor.d.ts.map +0 -1
- package/dist/dev/dom/features/text-tracks-actor.js.map +0 -1
- package/dist/dev/dom/features/track-current-time.d.ts +0 -40
- package/dist/dev/dom/features/track-current-time.d.ts.map +0 -1
- package/dist/dev/dom/features/track-current-time.js +0 -49
- package/dist/dev/dom/features/track-current-time.js.map +0 -1
- package/dist/dev/dom/features/track-playback-initiated.d.ts +0 -46
- package/dist/dev/dom/features/track-playback-initiated.d.ts.map +0 -1
- package/dist/dev/dom/features/track-playback-initiated.js +0 -66
- package/dist/dev/dom/features/track-playback-initiated.js.map +0 -1
- package/dist/dev/dom/features/track-playback-rate.d.ts +0 -34
- package/dist/dev/dom/features/track-playback-rate.d.ts.map +0 -1
- package/dist/dev/dom/features/track-playback-rate.js +0 -32
- package/dist/dev/dom/features/track-playback-rate.js.map +0 -1
- package/dist/dev/dom/features/update-duration.js +0 -78
- package/dist/dev/dom/features/update-duration.js.map +0 -1
- package/dist/dev/dom/media/append-segment.d.ts.map +0 -1
- package/dist/dev/dom/media/append-segment.js.map +0 -1
- package/dist/dev/dom/media/buffer-flusher.d.ts.map +0 -1
- package/dist/dev/dom/media/buffer-flusher.js.map +0 -1
- package/dist/dev/dom/media/mediasource-setup.js.map +0 -1
- package/dist/dev/dom/media/source-buffer-actor.d.ts.map +0 -1
- package/dist/dev/dom/media/source-buffer-actor.js.map +0 -1
- package/dist/dev/dom/network/chunked-stream-iterable.js.map +0 -1
- package/dist/dev/dom/network/fetch.js +0 -54
- package/dist/dev/dom/network/fetch.js.map +0 -1
- package/dist/dev/dom/playback-engine/adapter.d.ts.map +0 -1
- package/dist/dev/dom/playback-engine/adapter.js.map +0 -1
- package/dist/dev/dom/playback-engine/engine.d.ts +0 -124
- package/dist/dev/dom/playback-engine/engine.d.ts.map +0 -1
- package/dist/dev/dom/playback-engine/engine.js +0 -142
- package/dist/dev/dom/playback-engine/engine.js.map +0 -1
- package/dist/dev/dom/playback-engine.d.ts +0 -4
- package/dist/dev/dom/playback-engine.js +0 -4
- package/dist/dev/dom/text/parse-vtt-segment.d.ts +0 -12
- package/dist/dev/dom/text/parse-vtt-segment.d.ts.map +0 -1
- package/dist/dev/dom/text/parse-vtt-segment.js.map +0 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"create-machine-reactor.js","names":[],"sources":["../../../../src/core/reactors/create-machine-reactor.ts"],"sourcesContent":["import type { Machine, MachineSnapshot } from '../machine';\nimport { createMachineCore } from '../machine';\nimport { effect } from '../signals/effect';\nimport { untrack } from '../signals/primitives';\n\n// =============================================================================\n// Definition types\n// =============================================================================\n\n/**\n * A reactive state-deriving function used in the `monitor` field.\n *\n * Returns the target state the reactor should be in. Any signals read inside\n * the fn body create reactive dependencies — the framework re-evaluates it when\n * those signals change and automatically calls `transition()` when the returned\n * state differs from the current one.\n */\nexport type ReactorDeriveFn<State extends string> = () => State;\n\n/**\n * An effect function used in reactor `entry` and `effects` blocks.\n *\n * May return a cleanup function that runs before each re-evaluation and on\n * state exit (including destroy).\n */\nexport type ReactorEffectFn = () => (() => void) | { abort(): void } | void;\n\n/**\n * Per-state effect grouping for a single reactor state.\n *\n * - `entry` effects run once on state entry. The fn body is automatically\n * untracked — no `untrack()` calls are needed inside. Use this for\n * one-time setup: reading current values, attaching event listeners, etc.\n * - `effects` run on state entry and re-run whenever a signal read inside\n * the fn body changes. Use `untrack()` for reads you do not want to track.\n * Use this for work that must stay in sync with reactive state.\n *\n * Both are optional; pass `{}` for states with no effects.\n */\nexport type ReactorStateDefinition = {\n entry?: ReactorEffectFn | ReactorEffectFn[];\n effects?: ReactorEffectFn | ReactorEffectFn[];\n};\n\n/**\n * Full reactor definition passed to `createMachineReactor`.\n *\n * `State` is the set of domain-meaningful states. `'destroying'` and\n * `'destroyed'` are always added by the framework as implicit terminal states —\n * do not include them here.\n */\nexport type ReactorDefinition<State extends string> = {\n /** Initial state. */\n initial: State;\n /**\n * Reactive state derivation. Registered before per-state effects — the\n * ordering guarantee ensures transitions fired here take effect before\n * per-state effects re-evaluate in the same flush.\n */\n monitor?: ReactorDeriveFn<State> | ReactorDeriveFn<State>[];\n /**\n * Per-state effect groupings. Every valid state must be declared — pass `{}`\n * for states with no effects. `entry` and `effects` each become independent\n * `effect()` calls gated on that state, with their own cleanup lifecycles.\n */\n states: Record<State, ReactorStateDefinition>;\n};\n\n// =============================================================================\n// Live reactor interface\n// =============================================================================\n\n/** Live reactor instance returned by `createMachineReactor`. */\nexport type Reactor<State extends string> = Machine<MachineSnapshot<State>>;\n\n// =============================================================================\n// Implementation helpers\n// =============================================================================\n\nconst toArray = <T>(x: T | T[] | undefined): T[] => (x === undefined ? [] : Array.isArray(x) ? x : [x]);\n\n// =============================================================================\n// Implementation\n// =============================================================================\n\n/**\n * Creates a reactive Reactor from a declarative definition.\n *\n * A Reactor is driven by subscriptions to external signals rather than\n * imperative messages. Each state holds an array of effect functions —\n * every element becomes one independent `effect()` call gated on that state,\n * with its own dependency tracking and cleanup lifecycle.\n *\n * `'destroying'` and `'destroyed'` are always implicit terminal states.\n * `destroy()` transitions through both in sequence: `'destroying'` first (for\n * potential async teardown in a future extension), then immediately `'destroyed'`\n * for the synchronous base case. Active effect cleanups fire via disposal.\n *\n * @example\n * const reactor = createMachineReactor({\n * initial: 'waiting',\n * monitor: () => srcSignal.get() ? 'active' : 'waiting',\n * states: {\n * active: {\n * // entry: runs once on state entry; fn body is automatically untracked.\n * entry: () => listen(el, 'play', handler),\n * // effects: re-runs whenever tracked signals change.\n * effects: () => { currentTimeSignal.get(); return cleanup; },\n * },\n * waiting: {},\n * }\n * });\n */\nexport function createMachineReactor<State extends string>(\n def: ReactorDefinition<State>\n): Reactor<State | 'destroying' | 'destroyed'> {\n type FullState = State | 'destroying' | 'destroyed';\n\n const { snapshotSignal, getState, transition } = createMachineCore<FullState, MachineSnapshot<FullState>>({\n value: def.initial as FullState,\n });\n\n const effectDisposals: Array<() => void> = [];\n\n const wrapResult = (result: ReturnType<ReactorEffectFn>) => {\n if (!result) return undefined;\n if (typeof result === 'function') return result;\n return () => result.abort();\n };\n\n type EffectCall = () => ReturnType<ReactorEffectFn>;\n\n type EffectDescriptor = {\n fn: ReactorEffectFn;\n shouldSkip: (snapshot: { value: FullState }) => boolean;\n toFnCall?: (baseCall: EffectCall) => EffectCall;\n };\n\n const untracked: EffectDescriptor['toFnCall'] = (baseCall) => () => untrack(baseCall);\n\n const isTerminal = (snapshot: { value: FullState }) =>\n snapshot.value === 'destroying' || snapshot.value === 'destroyed';\n\n // `monitor` descriptors are built first — the ordering guarantee ensures\n // transitions they trigger take effect before per-state effects re-evaluate\n // in the same flush. See the comment on effect registration order in the\n // previous implementation for full details.\n const descriptors: EffectDescriptor[] = [\n ...toArray(def.monitor).map((fn) => ({\n fn: () => {\n const target = fn();\n if (target !== (getState() as State)) transition(target as FullState);\n },\n shouldSkip: isTerminal,\n })),\n ...(Object.entries(def.states) as Array<[State, ReactorStateDefinition]>).flatMap(([state, stateDef]) => {\n const isNotState = (snapshot: { value: FullState }) => snapshot.value !== state;\n return [\n ...toArray(stateDef.entry).map((fn) => ({ fn, shouldSkip: isNotState, toFnCall: untracked })),\n ...toArray(stateDef.effects).map((fn) => ({ fn, shouldSkip: isNotState })),\n ];\n }),\n ];\n\n const toEffect = ({ fn, shouldSkip, toFnCall = (baseCall) => baseCall }: EffectDescriptor) =>\n effect(() => {\n const snapshot = snapshotSignal.get();\n if (shouldSkip(snapshot)) return;\n const baseCall = () => fn();\n return wrapResult(toFnCall(baseCall)());\n });\n\n effectDisposals.push(...descriptors.map(toEffect));\n\n return {\n get snapshot() {\n return snapshotSignal;\n },\n\n destroy(): void {\n const state = getState();\n if (state === 'destroying' || state === 'destroyed') return;\n // Two-step teardown: transition through 'destroying' first to leave room\n // for async teardown in a future extension, then immediately 'destroyed'\n // for the synchronous base case. Active effect cleanups fire via disposal.\n transition('destroying');\n transition('destroyed');\n for (const dispose of effectDisposals) dispose();\n },\n };\n}\n"],"mappings":";;;;AA+EA,MAAM,WAAc,MAAiC,MAAM,KAAA,IAAY,EAAE,GAAG,MAAM,QAAQ,EAAE,GAAG,IAAI,CAAC,EAAE;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAkCtG,SAAgB,qBACd,KAC6C;CAG7C,MAAM,EAAE,gBAAgB,UAAU,eAAe,kBAAyD,EACxG,OAAO,IAAI,SACZ,CAAC;CAEF,MAAM,kBAAqC,EAAE;CAE7C,MAAM,cAAc,WAAwC;AAC1D,MAAI,CAAC,OAAQ,QAAO,KAAA;AACpB,MAAI,OAAO,WAAW,WAAY,QAAO;AACzC,eAAa,OAAO,OAAO;;CAW7B,MAAM,aAA2C,mBAAmB,QAAQ,SAAS;CAErF,MAAM,cAAc,aAClB,SAAS,UAAU,gBAAgB,SAAS,UAAU;CAMxD,MAAM,cAAkC,CACtC,GAAG,QAAQ,IAAI,QAAQ,CAAC,KAAK,QAAQ;EACnC,UAAU;GACR,MAAM,SAAS,IAAI;AACnB,OAAI,WAAY,UAAU,CAAY,YAAW,OAAoB;;EAEvE,YAAY;EACb,EAAE,EACH,GAAI,OAAO,QAAQ,IAAI,OAAO,CAA4C,SAAS,CAAC,OAAO,cAAc;EACvG,MAAM,cAAc,aAAmC,SAAS,UAAU;AAC1E,SAAO,CACL,GAAG,QAAQ,SAAS,MAAM,CAAC,KAAK,QAAQ;GAAE;GAAI,YAAY;GAAY,UAAU;GAAW,EAAE,EAC7F,GAAG,QAAQ,SAAS,QAAQ,CAAC,KAAK,QAAQ;GAAE;GAAI,YAAY;GAAY,EAAE,CAC3E;GACD,CACH;CAED,MAAM,YAAY,EAAE,IAAI,YAAY,YAAY,aAAa,eAC3D,aAAa;AAEX,MAAI,WADa,eAAe,KAAK,CACb,CAAE;EAC1B,MAAM,iBAAiB,IAAI;AAC3B,SAAO,WAAW,SAAS,SAAS,EAAE,CAAC;GACvC;AAEJ,iBAAgB,KAAK,GAAG,YAAY,IAAI,SAAS,CAAC;AAElD,QAAO;EACL,IAAI,WAAW;AACb,UAAO;;EAGT,UAAgB;GACd,MAAM,QAAQ,UAAU;AACxB,OAAI,UAAU,gBAAgB,UAAU,YAAa;AAIrD,cAAW,aAAa;AACxB,cAAW,YAAY;AACvB,QAAK,MAAM,WAAW,gBAAiB,UAAS;;EAEnD"}
|
|
@@ -1,10 +1,47 @@
|
|
|
1
1
|
import { Signal } from "signal-polyfill";
|
|
2
2
|
|
|
3
3
|
//#region src/core/signals/primitives.d.ts
|
|
4
|
+
/** Read a signal value without tracking it as a dependency. */
|
|
5
|
+
declare const untrack: <T>(fn: () => T) => T;
|
|
4
6
|
/** A writable reactive value (read + write). */
|
|
5
7
|
type Signal$1<T> = Signal.State<T>;
|
|
8
|
+
/** A derived reactive value that re-evaluates when its dependencies change (read-only). */
|
|
9
|
+
type Computed<T> = Signal.Computed<T>;
|
|
6
10
|
/** A read-only view of a reactive value. */
|
|
7
11
|
type ReadonlySignal<T> = Omit<Signal.State<T>, 'set'>;
|
|
12
|
+
interface SignalOptions<T> {
|
|
13
|
+
equals?: (t: T, t2: T) => boolean;
|
|
14
|
+
}
|
|
15
|
+
/** Create a writable reactive value. */
|
|
16
|
+
declare function signal<T>(initialValue: T, options?: SignalOptions<T>): Signal$1<T>;
|
|
17
|
+
/** Create a computed reactive value. */
|
|
18
|
+
declare function computed<T>(fn: () => T, options?: SignalOptions<T>): Computed<T>;
|
|
19
|
+
/**
|
|
20
|
+
* Update a writable signal. Two forms:
|
|
21
|
+
*
|
|
22
|
+
* - **Updater function** `(current) => next`. Works for any signal type,
|
|
23
|
+
* including `Signal<T | undefined>` — handle undefined in the updater.
|
|
24
|
+
* - **Partial object** to merge into the current state. Requires
|
|
25
|
+
* `T extends object`.
|
|
26
|
+
*
|
|
27
|
+
* @example
|
|
28
|
+
* update(state, { playbackRate: 2 });
|
|
29
|
+
* update(state, (s) => ({ ...s, count: s.count + 1 }));
|
|
30
|
+
* update(maybeUndefinedSignal, (current) => current ?? defaultValue);
|
|
31
|
+
*/
|
|
32
|
+
declare function update<T>(signal: Signal$1<T>, updater: (current: T) => T): void;
|
|
33
|
+
declare function update<T extends object>(signal: Signal$1<T>, updater: Partial<T>): void;
|
|
34
|
+
/**
|
|
35
|
+
* Read every signal in a map and return a plain object snapshot. Each read
|
|
36
|
+
* tracks in the surrounding Computed/Effect — equivalent to calling `.get()`
|
|
37
|
+
* on a single `Signal<S>` over the merged shape.
|
|
38
|
+
*
|
|
39
|
+
* Convenience for behaviors that pass whole state/context snapshots to pure
|
|
40
|
+
* helpers; prefer per-field reads when only a few fields are needed.
|
|
41
|
+
*/
|
|
42
|
+
declare function snapshot<M extends Record<string, ReadonlySignal<unknown>>>(map: M): { [K in keyof M]: M[K] extends {
|
|
43
|
+
get(): infer V;
|
|
44
|
+
} ? V : never };
|
|
8
45
|
//#endregion
|
|
9
|
-
export { ReadonlySignal, Signal$1 as Signal };
|
|
46
|
+
export { Computed, ReadonlySignal, Signal$1 as Signal, SignalOptions, computed, signal, snapshot, untrack, update };
|
|
10
47
|
//# sourceMappingURL=primitives.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"primitives.d.ts","names":[],"sources":["../../../../src/core/signals/primitives.ts"],"mappings":"
|
|
1
|
+
{"version":3,"file":"primitives.d.ts","names":[],"sources":["../../../../src/core/signals/primitives.ts"],"mappings":";;;;cAGa,OAAA,MAAa,EAAA,QAAU,CAAA,KAAM,CAAA;;KAqB9B,QAAA,MAAY,MAAA,CAAS,KAAA,CAAM,CAAA;;KAG3B,QAAA,MAAc,MAAA,CAAS,QAAA,CAAS,CAAA;;KAGhC,cAAA,MAAoB,IAAA,CAAK,MAAA,CAAS,KAAA,CAAM,CAAA;AAAA,UAEnC,aAAA;EACf,MAAA,IAAU,CAAA,EAAG,CAAA,EAAG,EAAA,EAAI,CAAA;AAAA;;iBAIN,MAAA,GAAA,CAAU,YAAA,EAAc,CAAA,EAAG,OAAA,GAAU,aAAA,CAAc,CAAA,IAAK,QAAA,CAAO,CAAA;;iBAK/D,QAAA,GAAA,CAAY,EAAA,QAAU,CAAA,EAAG,OAAA,GAAU,aAAA,CAAc,CAAA,IAAK,QAAA,CAAS,CAAA;AAZ/E;;;;;;;;;;;;;AAAA,iBA6BgB,MAAA,GAAA,CAAU,MAAA,EAAQ,QAAA,CAAO,CAAA,GAAI,OAAA,GAAU,OAAA,EAAS,CAAA,KAAM,CAAA;AAAA,iBACtD,MAAA,kBAAA,CAAyB,MAAA,EAAQ,QAAA,CAAO,CAAA,GAAI,OAAA,EAAS,OAAA,CAAQ,CAAA;;;;;;;;;iBAqC7D,QAAA,WAAmB,MAAA,SAAe,cAAA,WAAA,CAChD,GAAA,EAAK,CAAA,iBACU,CAAA,GAAI,CAAA,CAAE,CAAA;EAAa,GAAA;AAAA,IAAmB,CAAA"}
|
|
@@ -2,6 +2,23 @@ import { Signal } from "signal-polyfill";
|
|
|
2
2
|
//#region src/core/signals/primitives.ts
|
|
3
3
|
/** Read a signal value without tracking it as a dependency. */
|
|
4
4
|
const untrack = Signal.subtle.untrack;
|
|
5
|
+
/**
|
|
6
|
+
* Read a signal's current value without tracking it as a dependency. Sugar
|
|
7
|
+
* for `untrack(() => signal.get())` to reduce boilerplate at single-read
|
|
8
|
+
* sites. Structurally typed to accept any signal-like (Signal, Computed,
|
|
9
|
+
* ReadonlySignal).
|
|
10
|
+
*
|
|
11
|
+
* Accepts an optional `transform` to project the value in the same call;
|
|
12
|
+
* the default is the identity function so the single-arg form returns `T`
|
|
13
|
+
* unchanged.
|
|
14
|
+
*
|
|
15
|
+
* @example
|
|
16
|
+
* const value = peek(someSignal);
|
|
17
|
+
* const id = peek(presentationSignal, (p) => p?.id);
|
|
18
|
+
*/
|
|
19
|
+
function peek(source, transform = (v) => v) {
|
|
20
|
+
return untrack(() => transform(source.get()));
|
|
21
|
+
}
|
|
5
22
|
/** Create a writable reactive value. */
|
|
6
23
|
function signal(initialValue, options) {
|
|
7
24
|
return new Signal.State(initialValue, options);
|
|
@@ -10,23 +27,28 @@ function signal(initialValue, options) {
|
|
|
10
27
|
function computed(fn, options) {
|
|
11
28
|
return new Signal.Computed(fn, options);
|
|
12
29
|
}
|
|
13
|
-
/**
|
|
14
|
-
* Update a writable signal. Accepts either a partial object to merge into the
|
|
15
|
-
* current state, or an updater function that receives the current state and
|
|
16
|
-
* returns the next state.
|
|
17
|
-
*
|
|
18
|
-
* @example
|
|
19
|
-
* update(state, { playbackRate: 2 });
|
|
20
|
-
* update(state, (s) => ({ ...s, count: s.count + 1 }));
|
|
21
|
-
*/
|
|
22
30
|
function update(signal, updater) {
|
|
23
31
|
const current = untrack(() => signal.get());
|
|
24
|
-
|
|
32
|
+
if (typeof updater === "function") signal.set(updater(current));
|
|
33
|
+
else signal.set({
|
|
25
34
|
...current,
|
|
26
35
|
...updater
|
|
27
36
|
});
|
|
28
37
|
}
|
|
38
|
+
/**
|
|
39
|
+
* Read every signal in a map and return a plain object snapshot. Each read
|
|
40
|
+
* tracks in the surrounding Computed/Effect — equivalent to calling `.get()`
|
|
41
|
+
* on a single `Signal<S>` over the merged shape.
|
|
42
|
+
*
|
|
43
|
+
* Convenience for behaviors that pass whole state/context snapshots to pure
|
|
44
|
+
* helpers; prefer per-field reads when only a few fields are needed.
|
|
45
|
+
*/
|
|
46
|
+
function snapshot(map) {
|
|
47
|
+
const out = {};
|
|
48
|
+
for (const key in map) out[key] = map[key].get();
|
|
49
|
+
return out;
|
|
50
|
+
}
|
|
29
51
|
//#endregion
|
|
30
|
-
export { computed, signal, untrack, update };
|
|
52
|
+
export { computed, peek, signal, snapshot, untrack, update };
|
|
31
53
|
|
|
32
54
|
//# sourceMappingURL=primitives.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"primitives.js","names":["SignalNS"],"sources":["../../../../src/core/signals/primitives.ts"],"sourcesContent":["import { Signal as SignalNS } from 'signal-polyfill';\n\n/** Read a signal value without tracking it as a dependency. */\nexport const untrack: <T>(fn: () => T) => T = SignalNS.subtle.untrack;\n\n/** A writable reactive value (read + write). */\nexport type Signal<T> = SignalNS.State<T>;\n\n/** A derived reactive value that re-evaluates when its dependencies change (read-only). */\nexport type Computed<T> = SignalNS.Computed<T>;\n\n/** A read-only view of a reactive value. */\nexport type ReadonlySignal<T> = Omit<SignalNS.State<T>, 'set'>;\n\nexport interface SignalOptions<T> {\n equals?: (t: T, t2: T) => boolean;\n}\n\n/** Create a writable reactive value. */\nexport function signal<T>(initialValue: T, options?: SignalOptions<T>): Signal<T> {\n return new SignalNS.State(initialValue, options as SignalNS.Options<T>);\n}\n\n/** Create a computed reactive value. */\nexport function computed<T>(fn: () => T, options?: SignalOptions<T>): Computed<T> {\n return new SignalNS.Computed(fn, options as SignalNS.Options<T>);\n}\n\n/**\n * Update a writable signal.
|
|
1
|
+
{"version":3,"file":"primitives.js","names":["SignalNS"],"sources":["../../../../src/core/signals/primitives.ts"],"sourcesContent":["import { Signal as SignalNS } from 'signal-polyfill';\n\n/** Read a signal value without tracking it as a dependency. */\nexport const untrack: <T>(fn: () => T) => T = SignalNS.subtle.untrack;\n\n/**\n * Read a signal's current value without tracking it as a dependency. Sugar\n * for `untrack(() => signal.get())` to reduce boilerplate at single-read\n * sites. Structurally typed to accept any signal-like (Signal, Computed,\n * ReadonlySignal).\n *\n * Accepts an optional `transform` to project the value in the same call;\n * the default is the identity function so the single-arg form returns `T`\n * unchanged.\n *\n * @example\n * const value = peek(someSignal);\n * const id = peek(presentationSignal, (p) => p?.id);\n */\nexport function peek<T, R = T>(source: { get(): T }, transform: (value: T) => R = (v: T) => v as unknown as R): R {\n return untrack(() => transform(source.get()));\n}\n\n/** A writable reactive value (read + write). */\nexport type Signal<T> = SignalNS.State<T>;\n\n/** A derived reactive value that re-evaluates when its dependencies change (read-only). */\nexport type Computed<T> = SignalNS.Computed<T>;\n\n/** A read-only view of a reactive value. */\nexport type ReadonlySignal<T> = Omit<SignalNS.State<T>, 'set'>;\n\nexport interface SignalOptions<T> {\n equals?: (t: T, t2: T) => boolean;\n}\n\n/** Create a writable reactive value. */\nexport function signal<T>(initialValue: T, options?: SignalOptions<T>): Signal<T> {\n return new SignalNS.State(initialValue, options as SignalNS.Options<T>);\n}\n\n/** Create a computed reactive value. */\nexport function computed<T>(fn: () => T, options?: SignalOptions<T>): Computed<T> {\n return new SignalNS.Computed(fn, options as SignalNS.Options<T>);\n}\n\n/**\n * Update a writable signal. Two forms:\n *\n * - **Updater function** `(current) => next`. Works for any signal type,\n * including `Signal<T | undefined>` — handle undefined in the updater.\n * - **Partial object** to merge into the current state. Requires\n * `T extends object`.\n *\n * @example\n * update(state, { playbackRate: 2 });\n * update(state, (s) => ({ ...s, count: s.count + 1 }));\n * update(maybeUndefinedSignal, (current) => current ?? defaultValue);\n */\nexport function update<T>(signal: Signal<T>, updater: (current: T) => T): void;\nexport function update<T extends object>(signal: Signal<T>, updater: Partial<T>): void;\nexport function update<T>(signal: Signal<T>, updater: ((current: T) => T) | object): void {\n const current = untrack(() => signal.get());\n if (typeof updater === 'function') {\n signal.set((updater as (current: T) => T)(current));\n } else {\n // Partial<T> form — `T extends object` enforced by the public overload.\n signal.set({ ...(current as object), ...updater } as T);\n }\n}\n\n/**\n * Equality comparator for objects with an optional `id` field. Designed for\n * use as a `computed` `equals` option when reacting to identity changes\n * (Ham-shaped objects, JSON-API-shaped resources) while filtering internal\n * updates that preserve the id.\n *\n * Handles undefined inputs symmetrically: both undefined → equal; one\n * undefined → different.\n *\n * @example\n * const presentationById = computed(() => state.presentation.get(), {\n * equals: equalsById,\n * });\n */\nexport function equalsById<T extends { id?: string }>(a: T | undefined, b: T | undefined): boolean {\n return a?.id === b?.id;\n}\n\n/**\n * Read every signal in a map and return a plain object snapshot. Each read\n * tracks in the surrounding Computed/Effect — equivalent to calling `.get()`\n * on a single `Signal<S>` over the merged shape.\n *\n * Convenience for behaviors that pass whole state/context snapshots to pure\n * helpers; prefer per-field reads when only a few fields are needed.\n */\nexport function snapshot<M extends Record<string, ReadonlySignal<unknown>>>(\n map: M\n): { [K in keyof M]: M[K] extends { get(): infer V } ? V : never } {\n const out = {} as { [K in keyof M]: M[K] extends { get(): infer V } ? V : never };\n for (const key in map) {\n out[key] = map[key]!.get() as never;\n }\n return out;\n}\n"],"mappings":";;;AAGA,MAAa,UAAiCA,OAAS,OAAO;;;;;;;;;;;;;;;AAgB9D,SAAgB,KAAe,QAAsB,aAA8B,MAAS,GAAsB;AAChH,QAAO,cAAc,UAAU,OAAO,KAAK,CAAC,CAAC;;;AAiB/C,SAAgB,OAAU,cAAiB,SAAuC;AAChF,QAAO,IAAIA,OAAS,MAAM,cAAc,QAA+B;;;AAIzE,SAAgB,SAAY,IAAa,SAAyC;AAChF,QAAO,IAAIA,OAAS,SAAS,IAAI,QAA+B;;AAkBlE,SAAgB,OAAU,QAAmB,SAA6C;CACxF,MAAM,UAAU,cAAc,OAAO,KAAK,CAAC;AAC3C,KAAI,OAAO,YAAY,WACrB,QAAO,IAAK,QAA8B,QAAQ,CAAC;KAGnD,QAAO,IAAI;EAAE,GAAI;EAAoB,GAAG;EAAS,CAAM;;;;;;;;;;AA8B3D,SAAgB,SACd,KACiE;CACjE,MAAM,MAAM,EAAE;AACd,MAAK,MAAM,OAAO,IAChB,KAAI,OAAO,IAAI,KAAM,KAAK;AAE5B,QAAO"}
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
//#region src/core/tasks/task.d.ts
|
|
2
|
+
/** Recursively marks all properties as readonly. */
|
|
3
|
+
type DeepReadonly<T> = T extends (infer U)[] ? ReadonlyArray<DeepReadonly<U>> : T extends object ? { readonly [K in keyof T]: DeepReadonly<T[K]> } : T;
|
|
4
|
+
type TaskStatus = 'pending' | 'running' | 'done' | 'error';
|
|
5
|
+
/**
|
|
6
|
+
* Configuration for a Task.
|
|
7
|
+
*/
|
|
8
|
+
interface TaskConfig {
|
|
9
|
+
/**
|
|
10
|
+
* Identifier for this task.
|
|
11
|
+
* - string: used as-is
|
|
12
|
+
* - () => string: called once at construction time
|
|
13
|
+
* - undefined: a unique ID is generated via generateId()
|
|
14
|
+
*/
|
|
15
|
+
id?: string | (() => string);
|
|
16
|
+
/**
|
|
17
|
+
* Optional external AbortSignal to compose with the task's internal one.
|
|
18
|
+
* The task's work is aborted when either the internal controller (via abort())
|
|
19
|
+
* or this external signal fires — whichever comes first.
|
|
20
|
+
*/
|
|
21
|
+
signal?: AbortSignal;
|
|
22
|
+
}
|
|
23
|
+
/**
|
|
24
|
+
* Minimal contract for a schedulable unit of async work.
|
|
25
|
+
*/
|
|
26
|
+
interface TaskLike<TValue = void, TError = unknown> {
|
|
27
|
+
readonly id: string;
|
|
28
|
+
readonly status: TaskStatus;
|
|
29
|
+
readonly value: DeepReadonly<TValue> | undefined;
|
|
30
|
+
readonly error: DeepReadonly<TError> | undefined;
|
|
31
|
+
run(): Promise<TValue>;
|
|
32
|
+
abort(): void;
|
|
33
|
+
}
|
|
34
|
+
/**
|
|
35
|
+
* Generic reusable task that wraps an async run function.
|
|
36
|
+
*
|
|
37
|
+
* Owns its own AbortController so it can always be aborted independently.
|
|
38
|
+
* Optionally composes an external AbortSignal so that a parent's cancellation
|
|
39
|
+
* propagates into the task's work without requiring the caller to track the
|
|
40
|
+
* task separately.
|
|
41
|
+
*
|
|
42
|
+
* Ordering guarantee: `value` is written before `status` transitions to `'done'`;
|
|
43
|
+
* `error` is written before `status` transitions to `'error'`. Any reader
|
|
44
|
+
* observing `status === 'done'` is guaranteed `value` is already present.
|
|
45
|
+
*/
|
|
46
|
+
declare class Task<TValue = void, TError = unknown> implements TaskLike<TValue, TError> {
|
|
47
|
+
#private;
|
|
48
|
+
readonly id: string;
|
|
49
|
+
constructor(runFn: (signal: AbortSignal) => Promise<TValue>, config?: TaskConfig);
|
|
50
|
+
get status(): TaskStatus;
|
|
51
|
+
get value(): DeepReadonly<TValue> | undefined;
|
|
52
|
+
get error(): DeepReadonly<TError> | undefined;
|
|
53
|
+
run(): Promise<TValue>;
|
|
54
|
+
abort(): void;
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* Runs tasks concurrently, deduplicated by task id.
|
|
58
|
+
*
|
|
59
|
+
* If a task with a given id is already in flight, subsequent schedule() calls
|
|
60
|
+
* for that id are silently ignored until the first completes. Tasks are stored
|
|
61
|
+
* so abortAll() can cancel any in-flight work (e.g. on engine cleanup).
|
|
62
|
+
*/
|
|
63
|
+
declare class ConcurrentRunner {
|
|
64
|
+
#private;
|
|
65
|
+
schedule<TValue = void, TError = unknown>(task: TaskLike<TValue, TError>): Promise<TValue>;
|
|
66
|
+
/**
|
|
67
|
+
* Registers a callback to fire when all currently in-flight tasks settle.
|
|
68
|
+
* If the runner is already idle, the callback is never called. If abortAll()
|
|
69
|
+
* is called before the batch settles, the callback is superseded and silently
|
|
70
|
+
* dropped — no stale callbacks, no generation token required by the caller.
|
|
71
|
+
*/
|
|
72
|
+
whenSettled(callback: () => void): void;
|
|
73
|
+
abortAll(): void;
|
|
74
|
+
destroy(): void;
|
|
75
|
+
}
|
|
76
|
+
/**
|
|
77
|
+
* Runs tasks one at a time in submission order.
|
|
78
|
+
*
|
|
79
|
+
* Each schedule() call returns a Promise that resolves or rejects with the
|
|
80
|
+
* task's result when it is eventually executed. Tasks wait in queue until the
|
|
81
|
+
* prior task completes.
|
|
82
|
+
*
|
|
83
|
+
* Serialization is achieved by chaining each task's run() onto the tail of a
|
|
84
|
+
* shared promise chain — no explicit queue or drain loop needed.
|
|
85
|
+
*
|
|
86
|
+
* abortAll() aborts all pending (not yet started) tasks and the currently
|
|
87
|
+
* in-flight task. Pending tasks still run briefly but receive an aborted
|
|
88
|
+
* signal and are expected to exit early.
|
|
89
|
+
*/
|
|
90
|
+
declare class SerialRunner {
|
|
91
|
+
#private;
|
|
92
|
+
schedule<TValue = void, TError = unknown>(task: TaskLike<TValue, TError>): Promise<TValue>;
|
|
93
|
+
/**
|
|
94
|
+
* A promise that resolves when all currently-scheduled tasks have settled.
|
|
95
|
+
* Use the reference as a generation token: capture it after scheduling a
|
|
96
|
+
* batch, then check identity in the resolution callback to detect whether
|
|
97
|
+
* a subsequent abortAll() + new batch has superseded this one.
|
|
98
|
+
*/
|
|
99
|
+
get settled(): Promise<void>;
|
|
100
|
+
/**
|
|
101
|
+
* Registers a callback to fire when all currently-pending tasks settle.
|
|
102
|
+
* If the runner is already idle (no pending or running tasks), the callback
|
|
103
|
+
* is never called. If new tasks are scheduled before the current batch
|
|
104
|
+
* settles, the callback is superseded and silently dropped — no stale
|
|
105
|
+
* callbacks, no generation token required by the caller.
|
|
106
|
+
*/
|
|
107
|
+
whenSettled(callback: () => void): void;
|
|
108
|
+
/** Aborts and clears queued tasks without touching the in-flight task. */
|
|
109
|
+
abortPending(): void;
|
|
110
|
+
abortAll(): void;
|
|
111
|
+
destroy(): void;
|
|
112
|
+
}
|
|
113
|
+
//#endregion
|
|
114
|
+
export { ConcurrentRunner, SerialRunner, Task, TaskConfig, TaskLike, TaskStatus };
|
|
115
|
+
//# sourceMappingURL=task.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"task.d.ts","names":[],"sources":["../../../../src/core/tasks/task.ts"],"mappings":";;KAQY,YAAA,MAAkB,CAAA,uBAC1B,aAAA,CAAc,YAAA,CAAa,CAAA,KAC3B,CAAA,yCACyB,CAAA,GAAI,YAAA,CAAa,CAAA,CAAE,CAAA,OAC1C,CAAA;AAAA,KAMM,UAAA;;;;UAKK,UAAA;EAZY;;;;;;EAmB3B,EAAA;EAtBuB;;;;;EA6BvB,MAAA,GAAS,WAAA;AAAA;;;;UAMM,QAAA;EAAA,SACN,EAAA;EAAA,SACA,MAAA,EAAQ,UAAA;EAAA,SACR,KAAA,EAAO,YAAA,CAAa,MAAA;EAAA,SACpB,KAAA,EAAO,YAAA,CAAa,MAAA;EAC7B,GAAA,IAAO,OAAA,CAAQ,MAAA;EACf,KAAA;AAAA;;;AA1BF;;;;;;;;;AAoBA;cAqBa,IAAA,6CAAiD,QAAA,CAAS,MAAA,EAAQ,MAAA;EAAA;WACpE,EAAA;EAST,WAAA,CAAY,KAAA,GAAQ,MAAA,EAAQ,WAAA,KAAgB,OAAA,CAAQ,MAAA,GAAS,MAAA,GAAS,UAAA;EAAA,IASlE,MAAA,CAAA,GAAU,UAAA;EAAA,IAIV,KAAA,CAAA,GAAS,YAAA,CAAa,MAAA;EAAA,IAItB,KAAA,CAAA,GAAS,YAAA,CAAa,MAAA;EAIpB,GAAA,CAAA,GAAO,OAAA,CAAQ,MAAA;EAcrB,KAAA,CAAA;AAAA;;;;;;;;cAgBW,gBAAA;EAAA;EAMX,QAAA,iCAAA,CAA0C,IAAA,EAAM,QAAA,CAAS,MAAA,EAAQ,MAAA,IAAU,OAAA,CAAQ,MAAA;EApFnE;;;;;;EAsHhB,WAAA,CAAY,QAAA;EAYZ,QAAA,CAAA;EAWA,OAAA,CAAA;AAAA;;;;;;;;;;;;;;;cAwBW,YAAA;EAAA;EAMX,QAAA,iCAAA,CAA0C,IAAA,EAAM,QAAA,CAAS,MAAA,EAAQ,MAAA,IAAU,OAAA,CAAQ,MAAA;EA1JnE;;;;;;EAAA,IAwLZ,OAAA,CAAA,GAAW,OAAA;EA9Kf;;;;;;;EAyLA,WAAA,CAAY,QAAA;EAhLR;EA6LJ,YAAA,CAAA;EAKA,QAAA,CAAA;EAKA,OAAA,CAAA;AAAA"}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { generateId } from "./utils/generate-id.js";
|
|
2
1
|
import { anyAbortSignal } from "@videojs/utils/events";
|
|
3
|
-
|
|
2
|
+
import { generateId } from "@videojs/utils/string";
|
|
3
|
+
//#region src/core/tasks/task.ts
|
|
4
4
|
/**
|
|
5
5
|
* Generic reusable task that wraps an async run function.
|
|
6
6
|
*
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"task.js","names":["#runFn","#abortController","#signal","#status","#value","#error","#pending","#destroyed","#settled","#resolveSettled","#chain","#current"],"sources":["../../../../src/core/tasks/task.ts"],"sourcesContent":["import { anyAbortSignal } from '@videojs/utils/events';\nimport { generateId } from '@videojs/utils/string';\n\n// =============================================================================\n// DeepReadonly\n// =============================================================================\n\n/** Recursively marks all properties as readonly. */\nexport type DeepReadonly<T> = T extends (infer U)[]\n ? ReadonlyArray<DeepReadonly<U>>\n : T extends object\n ? { readonly [K in keyof T]: DeepReadonly<T[K]> }\n : T;\n\n// =============================================================================\n// Task\n// =============================================================================\n\nexport type TaskStatus = 'pending' | 'running' | 'done' | 'error';\n\n/**\n * Configuration for a Task.\n */\nexport interface TaskConfig {\n /**\n * Identifier for this task.\n * - string: used as-is\n * - () => string: called once at construction time\n * - undefined: a unique ID is generated via generateId()\n */\n id?: string | (() => string);\n\n /**\n * Optional external AbortSignal to compose with the task's internal one.\n * The task's work is aborted when either the internal controller (via abort())\n * or this external signal fires — whichever comes first.\n */\n signal?: AbortSignal;\n}\n\n/**\n * Minimal contract for a schedulable unit of async work.\n */\nexport interface TaskLike<TValue = void, TError = unknown> {\n readonly id: string;\n readonly status: TaskStatus;\n readonly value: DeepReadonly<TValue> | undefined;\n readonly error: DeepReadonly<TError> | undefined;\n run(): Promise<TValue>;\n abort(): void;\n}\n\n/**\n * Generic reusable task that wraps an async run function.\n *\n * Owns its own AbortController so it can always be aborted independently.\n * Optionally composes an external AbortSignal so that a parent's cancellation\n * propagates into the task's work without requiring the caller to track the\n * task separately.\n *\n * Ordering guarantee: `value` is written before `status` transitions to `'done'`;\n * `error` is written before `status` transitions to `'error'`. Any reader\n * observing `status === 'done'` is guaranteed `value` is already present.\n */\nexport class Task<TValue = void, TError = unknown> implements TaskLike<TValue, TError> {\n readonly id: string;\n readonly #runFn: (signal: AbortSignal) => Promise<TValue>;\n readonly #abortController = new AbortController();\n readonly #signal: AbortSignal;\n\n #status: TaskStatus = 'pending';\n #value: TValue | undefined = undefined;\n #error: TError | undefined = undefined;\n\n constructor(runFn: (signal: AbortSignal) => Promise<TValue>, config?: TaskConfig) {\n this.#runFn = runFn;\n const rawId = config?.id;\n this.id = typeof rawId === 'function' ? rawId() : (rawId ?? generateId());\n this.#signal = config?.signal\n ? anyAbortSignal([this.#abortController.signal, config.signal])\n : this.#abortController.signal;\n }\n\n get status(): TaskStatus {\n return this.#status;\n }\n\n get value(): DeepReadonly<TValue> | undefined {\n return this.#value as DeepReadonly<TValue> | undefined;\n }\n\n get error(): DeepReadonly<TError> | undefined {\n return this.#error as DeepReadonly<TError> | undefined;\n }\n\n async run(): Promise<TValue> {\n this.#status = 'running';\n try {\n const result = await this.#runFn(this.#signal);\n this.#value = result; // value before status — ordering guarantee\n this.#status = 'done';\n return result;\n } catch (e) {\n this.#error = e as TError; // error before status — ordering guarantee\n this.#status = 'error';\n throw e;\n }\n }\n\n abort(): void {\n this.#abortController.abort();\n }\n}\n\n// =============================================================================\n// ConcurrentRunner\n// =============================================================================\n\n/**\n * Runs tasks concurrently, deduplicated by task id.\n *\n * If a task with a given id is already in flight, subsequent schedule() calls\n * for that id are silently ignored until the first completes. Tasks are stored\n * so abortAll() can cancel any in-flight work (e.g. on engine cleanup).\n */\nexport class ConcurrentRunner {\n readonly #pending = new Map<string, { task: TaskLike<unknown, unknown>; promise: Promise<unknown> }>();\n #settled: Promise<void> = Promise.resolve();\n #resolveSettled: (() => void) | null = null;\n #destroyed = false;\n\n schedule<TValue = void, TError = unknown>(task: TaskLike<TValue, TError>): Promise<TValue> {\n if (this.#destroyed) return Promise.resolve() as Promise<TValue>;\n const existing = this.#pending.get(task.id);\n if (existing) return existing.promise as Promise<TValue>;\n\n if (this.#pending.size === 0) {\n this.#settled = new Promise((resolve) => {\n this.#resolveSettled = resolve;\n });\n }\n\n const promise = task.run();\n // Suppress unhandled rejection for callers that ignore the return value.\n promise.catch(() => {});\n // Cleanup: update pending and resolve settled regardless of outcome.\n const cleanup = () => {\n this.#pending.delete(task.id);\n if (this.#pending.size === 0) {\n this.#resolveSettled?.();\n this.#resolveSettled = null;\n }\n };\n promise.then(cleanup, cleanup);\n\n this.#pending.set(task.id, { task: task as TaskLike<unknown, unknown>, promise: promise as Promise<unknown> });\n return promise;\n }\n\n /**\n * Registers a callback to fire when all currently in-flight tasks settle.\n * If the runner is already idle, the callback is never called. If abortAll()\n * is called before the batch settles, the callback is superseded and silently\n * dropped — no stale callbacks, no generation token required by the caller.\n */\n whenSettled(callback: () => void): void {\n if (this.#pending.size === 0) return;\n const captured = this.#settled;\n captured.then(\n () => {\n if (this.#settled !== captured) return;\n callback();\n },\n () => {}\n );\n }\n\n abortAll(): void {\n for (const { task } of this.#pending.values()) task.abort();\n this.#pending.clear();\n // Resolve the current settled promise so any .then() handlers are queued,\n // then replace the reference — whenSettled callbacks that captured the old\n // reference will see the identity mismatch and be dropped.\n this.#resolveSettled?.();\n this.#resolveSettled = null;\n this.#settled = Promise.resolve();\n }\n\n destroy(): void {\n this.#destroyed = true;\n this.abortAll();\n }\n}\n\n// =============================================================================\n// SerialRunner\n// =============================================================================\n\n/**\n * Runs tasks one at a time in submission order.\n *\n * Each schedule() call returns a Promise that resolves or rejects with the\n * task's result when it is eventually executed. Tasks wait in queue until the\n * prior task completes.\n *\n * Serialization is achieved by chaining each task's run() onto the tail of a\n * shared promise chain — no explicit queue or drain loop needed.\n *\n * abortAll() aborts all pending (not yet started) tasks and the currently\n * in-flight task. Pending tasks still run briefly but receive an aborted\n * signal and are expected to exit early.\n */\nexport class SerialRunner {\n #chain: Promise<unknown> = Promise.resolve();\n readonly #pending = new Set<TaskLike<unknown, unknown>>();\n #current: TaskLike<unknown, unknown> | null = null;\n #destroyed = false;\n\n schedule<TValue = void, TError = unknown>(task: TaskLike<TValue, TError>): Promise<TValue> {\n if (this.#destroyed) return Promise.resolve() as Promise<TValue>;\n const t = task as TaskLike<unknown, unknown>;\n this.#pending.add(t);\n\n const result = this.#chain\n .then(() => {\n this.#pending.delete(t);\n this.#current = t;\n return task.run();\n })\n .finally(() => {\n this.#current = null;\n });\n\n // Advance the chain regardless of whether this task succeeds or fails.\n this.#chain = result.then(\n () => {},\n () => {}\n );\n\n return result as Promise<TValue>;\n }\n\n /**\n * A promise that resolves when all currently-scheduled tasks have settled.\n * Use the reference as a generation token: capture it after scheduling a\n * batch, then check identity in the resolution callback to detect whether\n * a subsequent abortAll() + new batch has superseded this one.\n */\n get settled(): Promise<void> {\n return this.#chain as Promise<void>;\n }\n\n /**\n * Registers a callback to fire when all currently-pending tasks settle.\n * If the runner is already idle (no pending or running tasks), the callback\n * is never called. If new tasks are scheduled before the current batch\n * settles, the callback is superseded and silently dropped — no stale\n * callbacks, no generation token required by the caller.\n */\n whenSettled(callback: () => void): void {\n if (this.#pending.size === 0 && this.#current === null) return;\n const currentChain = this.#chain;\n currentChain.then(\n () => {\n if (this.#chain !== currentChain) return;\n callback();\n },\n () => {}\n );\n }\n\n /** Aborts and clears queued tasks without touching the in-flight task. */\n abortPending(): void {\n for (const task of this.#pending) task.abort();\n this.#pending.clear();\n }\n\n abortAll(): void {\n this.abortPending();\n this.#current?.abort();\n }\n\n destroy(): void {\n this.#destroyed = true;\n this.abortAll();\n }\n}\n"],"mappings":";;;;;;;;;;;;;;;AAgEA,IAAa,OAAb,MAAuF;CACrF;CACA;CACA,mBAA4B,IAAI,iBAAiB;CACjD;CAEA,UAAsB;CACtB,SAA6B,KAAA;CAC7B,SAA6B,KAAA;CAE7B,YAAY,OAAiD,QAAqB;AAChF,QAAA,QAAc;EACd,MAAM,QAAQ,QAAQ;AACtB,OAAK,KAAK,OAAO,UAAU,aAAa,OAAO,GAAI,SAAS,YAAY;AACxE,QAAA,SAAe,QAAQ,SACnB,eAAe,CAAC,MAAA,gBAAsB,QAAQ,OAAO,OAAO,CAAC,GAC7D,MAAA,gBAAsB;;CAG5B,IAAI,SAAqB;AACvB,SAAO,MAAA;;CAGT,IAAI,QAA0C;AAC5C,SAAO,MAAA;;CAGT,IAAI,QAA0C;AAC5C,SAAO,MAAA;;CAGT,MAAM,MAAuB;AAC3B,QAAA,SAAe;AACf,MAAI;GACF,MAAM,SAAS,MAAM,MAAA,MAAY,MAAA,OAAa;AAC9C,SAAA,QAAc;AACd,SAAA,SAAe;AACf,UAAO;WACA,GAAG;AACV,SAAA,QAAc;AACd,SAAA,SAAe;AACf,SAAM;;;CAIV,QAAc;AACZ,QAAA,gBAAsB,OAAO;;;;;;;;;;AAejC,IAAa,mBAAb,MAA8B;CAC5B,2BAAoB,IAAI,KAA8E;CACtG,WAA0B,QAAQ,SAAS;CAC3C,kBAAuC;CACvC,aAAa;CAEb,SAA0C,MAAiD;AACzF,MAAI,MAAA,UAAiB,QAAO,QAAQ,SAAS;EAC7C,MAAM,WAAW,MAAA,QAAc,IAAI,KAAK,GAAG;AAC3C,MAAI,SAAU,QAAO,SAAS;AAE9B,MAAI,MAAA,QAAc,SAAS,EACzB,OAAA,UAAgB,IAAI,SAAS,YAAY;AACvC,SAAA,iBAAuB;IACvB;EAGJ,MAAM,UAAU,KAAK,KAAK;AAE1B,UAAQ,YAAY,GAAG;EAEvB,MAAM,gBAAgB;AACpB,SAAA,QAAc,OAAO,KAAK,GAAG;AAC7B,OAAI,MAAA,QAAc,SAAS,GAAG;AAC5B,UAAA,kBAAwB;AACxB,UAAA,iBAAuB;;;AAG3B,UAAQ,KAAK,SAAS,QAAQ;AAE9B,QAAA,QAAc,IAAI,KAAK,IAAI;GAAQ;GAA6C;GAA6B,CAAC;AAC9G,SAAO;;;;;;;;CAST,YAAY,UAA4B;AACtC,MAAI,MAAA,QAAc,SAAS,EAAG;EAC9B,MAAM,WAAW,MAAA;AACjB,WAAS,WACD;AACJ,OAAI,MAAA,YAAkB,SAAU;AAChC,aAAU;WAEN,GACP;;CAGH,WAAiB;AACf,OAAK,MAAM,EAAE,UAAU,MAAA,QAAc,QAAQ,CAAE,MAAK,OAAO;AAC3D,QAAA,QAAc,OAAO;AAIrB,QAAA,kBAAwB;AACxB,QAAA,iBAAuB;AACvB,QAAA,UAAgB,QAAQ,SAAS;;CAGnC,UAAgB;AACd,QAAA,YAAkB;AAClB,OAAK,UAAU;;;;;;;;;;;;;;;;;AAsBnB,IAAa,eAAb,MAA0B;CACxB,SAA2B,QAAQ,SAAS;CAC5C,2BAAoB,IAAI,KAAiC;CACzD,WAA8C;CAC9C,aAAa;CAEb,SAA0C,MAAiD;AACzF,MAAI,MAAA,UAAiB,QAAO,QAAQ,SAAS;EAC7C,MAAM,IAAI;AACV,QAAA,QAAc,IAAI,EAAE;EAEpB,MAAM,SAAS,MAAA,MACZ,WAAW;AACV,SAAA,QAAc,OAAO,EAAE;AACvB,SAAA,UAAgB;AAChB,UAAO,KAAK,KAAK;IACjB,CACD,cAAc;AACb,SAAA,UAAgB;IAChB;AAGJ,QAAA,QAAc,OAAO,WACb,UACA,GACP;AAED,SAAO;;;;;;;;CAST,IAAI,UAAyB;AAC3B,SAAO,MAAA;;;;;;;;;CAUT,YAAY,UAA4B;AACtC,MAAI,MAAA,QAAc,SAAS,KAAK,MAAA,YAAkB,KAAM;EACxD,MAAM,eAAe,MAAA;AACrB,eAAa,WACL;AACJ,OAAI,MAAA,UAAgB,aAAc;AAClC,aAAU;WAEN,GACP;;;CAIH,eAAqB;AACnB,OAAK,MAAM,QAAQ,MAAA,QAAe,MAAK,OAAO;AAC9C,QAAA,QAAc,OAAO;;CAGvB,WAAiB;AACf,OAAK,cAAc;AACnB,QAAA,SAAe,OAAO;;CAGxB,UAAgB;AACd,QAAA,YAAkB;AAClB,OAAK,UAAU"}
|
package/dist/dev/dom.d.ts
CHANGED
|
@@ -1,10 +1,9 @@
|
|
|
1
|
-
import { appendSegment } from "./dom/
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
6
|
-
import {
|
|
7
|
-
import {
|
|
8
|
-
import {
|
|
9
|
-
|
|
10
|
-
export { type CurrentTimeOwners, type CurrentTimeState, type PlaybackInitiatedOwners, type PlaybackInitiatedState, type PlaybackRateOwners, type PlaybackRateState, SpfMedia, type SpfMediaAPI, SpfMediaMixin, appendSegment, destroyVttParser, flushBuffer, loadSegments, loadTextTrackCues, parseVttSegment, trackCurrentTime, trackPlaybackInitiated, trackPlaybackRate };
|
|
1
|
+
import { appendSegment } from "./media/dom/mse/append-segment.js";
|
|
2
|
+
import { flushBuffer } from "./media/dom/mse/buffer-flusher.js";
|
|
3
|
+
import { destroyVttResolver, resolveVttSegment } from "./media/dom/text/resolve-vtt-segment.js";
|
|
4
|
+
import { loadAudioSegments, loadVideoSegments } from "./playback/behaviors/dom/load-segments.js";
|
|
5
|
+
import { setupTextTrackActors } from "./playback/behaviors/dom/setup-text-track-actors.js";
|
|
6
|
+
import { CurrentTimeContext, CurrentTimeState, trackCurrentTime } from "./playback/behaviors/dom/track-current-time.js";
|
|
7
|
+
import { LoadTriggersContext, LoadTriggersState, trackLoadTriggers } from "./playback/behaviors/dom/track-load-triggers.js";
|
|
8
|
+
import { PlaybackRateContext, PlaybackRateState, trackPlaybackRate } from "./playback/behaviors/dom/track-playback-rate.js";
|
|
9
|
+
export { type CurrentTimeContext, type CurrentTimeState, type LoadTriggersContext, type LoadTriggersState, type PlaybackRateContext, type PlaybackRateState, appendSegment, destroyVttResolver, flushBuffer, loadAudioSegments, loadVideoSegments, resolveVttSegment, setupTextTrackActors, trackCurrentTime, trackLoadTriggers, trackPlaybackRate };
|
package/dist/dev/dom.js
CHANGED
|
@@ -1,10 +1,9 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
6
|
-
import {
|
|
7
|
-
import {
|
|
8
|
-
import {
|
|
9
|
-
|
|
10
|
-
export { SpfMedia, SpfMediaMixin, appendSegment, destroyVttParser, flushBuffer, loadSegments, loadTextTrackCues, parseVttSegment, trackCurrentTime, trackPlaybackInitiated, trackPlaybackRate };
|
|
1
|
+
import { appendSegment } from "./media/dom/mse/append-segment.js";
|
|
2
|
+
import { flushBuffer } from "./media/dom/mse/buffer-flusher.js";
|
|
3
|
+
import { destroyVttResolver, resolveVttSegment } from "./media/dom/text/resolve-vtt-segment.js";
|
|
4
|
+
import { loadAudioSegments, loadVideoSegments } from "./playback/behaviors/dom/load-segments.js";
|
|
5
|
+
import { setupTextTrackActors } from "./playback/behaviors/dom/setup-text-track-actors.js";
|
|
6
|
+
import { trackCurrentTime } from "./playback/behaviors/dom/track-current-time.js";
|
|
7
|
+
import { trackLoadTriggers } from "./playback/behaviors/dom/track-load-triggers.js";
|
|
8
|
+
import { trackPlaybackRate } from "./playback/behaviors/dom/track-playback-rate.js";
|
|
9
|
+
export { appendSegment, destroyVttResolver, flushBuffer, loadAudioSegments, loadVideoSegments, resolveVttSegment, setupTextTrackActors, trackCurrentTime, trackLoadTriggers, trackPlaybackRate };
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import { SimpleHlsEngineConfig, SimpleHlsEngineContext, SimpleHlsEngineSignals, SimpleHlsEngineState, createSimpleHlsEngine } from "./playback/engines/hls/engine.js";
|
|
2
|
+
import { SimpleHlsMediaAPI, SimpleHlsMediaElement, SimpleHlsMediaMixin, SimpleHlsMediaProps, simpleHlsMediaDefaultProps } from "./playback/engines/hls/adapter.js";
|
|
3
|
+
export { type SimpleHlsEngineConfig, type SimpleHlsEngineContext, type SimpleHlsEngineSignals, type SimpleHlsEngineState, type SimpleHlsMediaAPI, SimpleHlsMediaElement, SimpleHlsMediaMixin, type SimpleHlsMediaProps, createSimpleHlsEngine, simpleHlsMediaDefaultProps };
|
package/dist/dev/hls.js
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import { createSimpleHlsEngine } from "./playback/engines/hls/engine.js";
|
|
2
|
+
import { SimpleHlsMediaElement, SimpleHlsMediaMixin, simpleHlsMediaDefaultProps } from "./playback/engines/hls/adapter.js";
|
|
3
|
+
export { SimpleHlsMediaElement, SimpleHlsMediaMixin, createSimpleHlsEngine, simpleHlsMediaDefaultProps };
|
package/dist/dev/index.d.ts
CHANGED
|
@@ -1,13 +1,25 @@
|
|
|
1
|
+
import { Computed, ReadonlySignal, Signal, SignalOptions, computed, signal, snapshot, untrack, update } from "./core/signals/primitives.js";
|
|
2
|
+
import { Behavior, BehaviorCleanup, BehaviorDeps, Composition, CompositionOptions, ContextSignals, InferBehaviorConfig, InferBehaviorContext, InferBehaviorState, ResolveBehaviorConfig, ResolveBehaviorContext, ResolveBehaviorState, StateSignals, createComposition, defineBehavior } from "./core/composition/create-composition.js";
|
|
3
|
+
import { ShareSignalsConfig, makeShareSignals } from "./core/composition/share-signals.js";
|
|
4
|
+
import { effect } from "./core/signals/effect.js";
|
|
5
|
+
import { ConcurrentRunner, SerialRunner, Task, TaskConfig, TaskLike, TaskStatus } from "./core/tasks/task.js";
|
|
6
|
+
import { ActorSnapshot, CallbackActor, SignalActor } from "./core/actors/actor.js";
|
|
7
|
+
import { ActorDefinition, ActorStateDefinition, HandlerContext, MessageActor, RunnerLike, createMachineActor } from "./core/actors/create-machine-actor.js";
|
|
8
|
+
import { TransitionActor, createTransitionActor } from "./core/actors/create-transition-actor.js";
|
|
9
|
+
import { Machine, MachineSnapshot } from "./core/machine.js";
|
|
10
|
+
import { Reactor, ReactorDefinition, ReactorDeriveFn, ReactorEffectFn, ReactorStateDefinition, createMachineReactor } from "./core/reactors/create-machine-reactor.js";
|
|
11
|
+
|
|
1
12
|
//#region src/index.d.ts
|
|
2
13
|
/**
|
|
3
14
|
* Stream Processing Framework (SPF) for Video.js 10
|
|
4
15
|
*
|
|
5
|
-
*
|
|
6
|
-
*
|
|
16
|
+
* The compositional primitives: createComposition, signals, tasks, actors,
|
|
17
|
+
* reactors. Media-domain helpers and the HLS playback engine live behind
|
|
18
|
+
* the `./dom` and `./hls` subpaths.
|
|
7
19
|
*
|
|
8
20
|
* @packageDocumentation
|
|
9
21
|
*/
|
|
10
22
|
declare const VERSION = "0.1.0";
|
|
11
23
|
//#endregion
|
|
12
|
-
export { VERSION };
|
|
24
|
+
export { type ActorDefinition, type ActorSnapshot, type ActorStateDefinition, type Behavior, type BehaviorCleanup, type BehaviorDeps, type CallbackActor, type Composition, type CompositionOptions, type Computed, ConcurrentRunner, type ContextSignals, type HandlerContext, type InferBehaviorConfig, type InferBehaviorContext, type InferBehaviorState, type Machine, type MachineSnapshot, type MessageActor, type Reactor, type ReactorDefinition, type ReactorDeriveFn, type ReactorEffectFn, type ReactorStateDefinition, type ReadonlySignal, type ResolveBehaviorConfig, type ResolveBehaviorContext, type ResolveBehaviorState, type RunnerLike, SerialRunner, type ShareSignalsConfig, type Signal, type SignalActor, type SignalOptions, type StateSignals, Task, type TaskConfig, type TaskLike, type TaskStatus, type TransitionActor, VERSION, computed, createComposition, createMachineActor, createMachineReactor, createTransitionActor, defineBehavior, effect, makeShareSignals, signal, snapshot, untrack, update };
|
|
13
25
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/dev/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","names":[],"sources":["../../src/index.ts"],"mappings":"
|
|
1
|
+
{"version":3,"file":"index.d.ts","names":[],"sources":["../../src/index.ts"],"mappings":";;;;;;;;;;;;;;;;;;;;;cAUa,OAAA"}
|
package/dist/dev/index.js
CHANGED
|
@@ -1,14 +1,23 @@
|
|
|
1
|
+
import { computed, signal, snapshot, untrack, update } from "./core/signals/primitives.js";
|
|
2
|
+
import { createComposition, defineBehavior } from "./core/composition/create-composition.js";
|
|
3
|
+
import { makeShareSignals } from "./core/composition/share-signals.js";
|
|
4
|
+
import { effect } from "./core/signals/effect.js";
|
|
5
|
+
import { ConcurrentRunner, SerialRunner, Task } from "./core/tasks/task.js";
|
|
6
|
+
import { createMachineActor } from "./core/actors/create-machine-actor.js";
|
|
7
|
+
import { createTransitionActor } from "./core/actors/create-transition-actor.js";
|
|
8
|
+
import { createMachineReactor } from "./core/reactors/create-machine-reactor.js";
|
|
1
9
|
//#region src/index.ts
|
|
2
10
|
/**
|
|
3
11
|
* Stream Processing Framework (SPF) for Video.js 10
|
|
4
12
|
*
|
|
5
|
-
*
|
|
6
|
-
*
|
|
13
|
+
* The compositional primitives: createComposition, signals, tasks, actors,
|
|
14
|
+
* reactors. Media-domain helpers and the HLS playback engine live behind
|
|
15
|
+
* the `./dom` and `./hls` subpaths.
|
|
7
16
|
*
|
|
8
17
|
* @packageDocumentation
|
|
9
18
|
*/
|
|
10
19
|
const VERSION = "0.1.0";
|
|
11
20
|
//#endregion
|
|
12
|
-
export { VERSION };
|
|
21
|
+
export { ConcurrentRunner, SerialRunner, Task, VERSION, computed, createComposition, createMachineActor, createMachineReactor, createTransitionActor, defineBehavior, effect, makeShareSignals, signal, snapshot, untrack, update };
|
|
13
22
|
|
|
14
23
|
//# sourceMappingURL=index.js.map
|
package/dist/dev/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","names":[],"sources":["../../src/index.ts"],"sourcesContent":["/**\n * Stream Processing Framework (SPF) for Video.js 10\n *\n *
|
|
1
|
+
{"version":3,"file":"index.js","names":[],"sources":["../../src/index.ts"],"sourcesContent":["/**\n * Stream Processing Framework (SPF) for Video.js 10\n *\n * The compositional primitives: createComposition, signals, tasks, actors,\n * reactors. Media-domain helpers and the HLS playback engine live behind\n * the `./dom` and `./hls` subpaths.\n *\n * @packageDocumentation\n */\n\nexport const VERSION = '0.1.0';\n\n// =============================================================================\n// Composition\n// =============================================================================\n\nexport type {\n Behavior,\n BehaviorCleanup,\n BehaviorDeps,\n Composition,\n CompositionOptions,\n ContextSignals,\n InferBehaviorConfig,\n InferBehaviorContext,\n InferBehaviorState,\n ResolveBehaviorConfig,\n ResolveBehaviorContext,\n ResolveBehaviorState,\n StateSignals,\n} from './core/composition/create-composition';\nexport { createComposition, defineBehavior } from './core/composition/create-composition';\nexport type { ShareSignalsConfig } from './core/composition/share-signals';\nexport { makeShareSignals } from './core/composition/share-signals';\n\n// =============================================================================\n// Signals\n// =============================================================================\n\nexport { effect } from './core/signals/effect';\nexport type { Computed, ReadonlySignal, Signal, SignalOptions } from './core/signals/primitives';\nexport { computed, signal, snapshot, untrack, update } from './core/signals/primitives';\n\n// =============================================================================\n// Tasks\n// =============================================================================\n\nexport type { TaskConfig, TaskLike, TaskStatus } from './core/tasks/task';\nexport { ConcurrentRunner, SerialRunner, Task } from './core/tasks/task';\n\n// =============================================================================\n// Machine (shared by actors and reactors)\n// =============================================================================\n\nexport type { Machine, MachineSnapshot } from './core/machine';\n\n// =============================================================================\n// Actors\n// =============================================================================\n\nexport type { ActorSnapshot, CallbackActor, SignalActor } from './core/actors/actor';\nexport type {\n ActorDefinition,\n ActorStateDefinition,\n HandlerContext,\n MessageActor,\n RunnerLike,\n} from './core/actors/create-machine-actor';\nexport { createMachineActor } from './core/actors/create-machine-actor';\nexport type { TransitionActor } from './core/actors/create-transition-actor';\nexport { createTransitionActor } from './core/actors/create-transition-actor';\n\n// =============================================================================\n// Reactors\n// =============================================================================\n\nexport type {\n Reactor,\n ReactorDefinition,\n ReactorDeriveFn,\n ReactorEffectFn,\n ReactorStateDefinition,\n} from './core/reactors/create-machine-reactor';\nexport { createMachineReactor } from './core/reactors/create-machine-reactor';\n"],"mappings":";;;;;;;;;;;;;;;;;;AAUA,MAAa,UAAU"}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
//#region src/media/abr/quality-selection.d.ts
|
|
2
|
+
/**
|
|
3
|
+
* Quality selection configuration.
|
|
4
|
+
*/
|
|
5
|
+
interface QualityConfig {
|
|
6
|
+
/**
|
|
7
|
+
* Safety margin (0-1).
|
|
8
|
+
* To select a track, need: currentBandwidth >= track.bandwidth / safetyMargin.
|
|
9
|
+
* Default 0.85 means track must use ≤85% of available bandwidth (15% headroom).
|
|
10
|
+
*/
|
|
11
|
+
safetyMargin: number;
|
|
12
|
+
/**
|
|
13
|
+
* Upgrade hysteresis ratio (>= 1). When `currentTrack` is supplied, an
|
|
14
|
+
* upgrade is applied only if `optimal.bandwidth >= currentTrack.bandwidth * upgradeMargin`.
|
|
15
|
+
* Downgrades are always applied. Default 1.15 means optimal must clear
|
|
16
|
+
* the current bandwidth by at least 15% to trigger an upgrade.
|
|
17
|
+
*/
|
|
18
|
+
upgradeMargin: number;
|
|
19
|
+
}
|
|
20
|
+
//#endregion
|
|
21
|
+
export { QualityConfig };
|
|
22
|
+
//# sourceMappingURL=quality-selection.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"quality-selection.d.ts","names":[],"sources":["../../../../src/media/abr/quality-selection.ts"],"mappings":";;;;UAiBiB,aAAA;;;;;;EAMf,YAAA;;;;;;;EAOA,aAAA;AAAA"}
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
//#region src/media/abr/quality-selection.ts
|
|
2
|
+
/**
|
|
3
|
+
* Default quality selection configuration.
|
|
4
|
+
* Values match Shaka Player upgrade threshold (0.85 = 15% headroom).
|
|
5
|
+
*/
|
|
6
|
+
const DEFAULT_QUALITY_CONFIG = {
|
|
7
|
+
safetyMargin: .85,
|
|
8
|
+
upgradeMargin: 1.15
|
|
9
|
+
};
|
|
10
|
+
/**
|
|
11
|
+
* Select the track to apply now, given current bandwidth, a current
|
|
12
|
+
* selection (optional), and tuning. Returns:
|
|
13
|
+
*
|
|
14
|
+
* - The bandwidth-fitting optimal when no `currentTrack` is supplied.
|
|
15
|
+
* - The optimal when it's a downgrade vs. `currentTrack` (downgrades
|
|
16
|
+
* apply immediately — no hysteresis).
|
|
17
|
+
* - The optimal when it clears `currentTrack.bandwidth * upgradeMargin`
|
|
18
|
+
* (upgrade clears hysteresis).
|
|
19
|
+
* - `currentTrack` itself when an upgrade doesn't clear the margin
|
|
20
|
+
* (stay put — caller checks identity to no-op).
|
|
21
|
+
*
|
|
22
|
+
* "Optimal" is the highest-bandwidth track where the available bandwidth
|
|
23
|
+
* meets the safety requirement (`currentBandwidth >= track.bandwidth / safetyMargin`).
|
|
24
|
+
* Falls back to the lowest-bandwidth track when nothing fits the safety
|
|
25
|
+
* margin (preserves a definitive pick under under-bandwidth conditions).
|
|
26
|
+
*
|
|
27
|
+
* @example
|
|
28
|
+
* const tracks = [low, mid, high];
|
|
29
|
+
* selectQuality(tracks, 5_000_000, { currentTrack: low });
|
|
30
|
+
* // Returns `high` if 5 Mbps clears safety AND high.bandwidth >= low.bandwidth * upgradeMargin.
|
|
31
|
+
* // Returns `low` (no-op signal) otherwise.
|
|
32
|
+
*/
|
|
33
|
+
function selectQuality(tracks, currentBandwidth, opts = {}) {
|
|
34
|
+
if (tracks.length === 0) return;
|
|
35
|
+
const safetyMargin = opts.safetyMargin ?? DEFAULT_QUALITY_CONFIG.safetyMargin;
|
|
36
|
+
const upgradeMargin = opts.upgradeMargin ?? DEFAULT_QUALITY_CONFIG.upgradeMargin;
|
|
37
|
+
const { currentTrack } = opts;
|
|
38
|
+
const sortedTracks = tracks.slice().sort((a, b) => a.bandwidth - b.bandwidth);
|
|
39
|
+
let chosen;
|
|
40
|
+
for (const track of sortedTracks) if (currentBandwidth >= track.bandwidth / safetyMargin) {
|
|
41
|
+
if (!chosen || track.bandwidth > chosen.bandwidth || track.bandwidth === chosen.bandwidth && hasHigherResolution(track, chosen)) chosen = track;
|
|
42
|
+
}
|
|
43
|
+
const optimal = chosen ?? sortedTracks[0];
|
|
44
|
+
if (!optimal) return void 0;
|
|
45
|
+
if (!currentTrack) return optimal;
|
|
46
|
+
if (optimal.bandwidth < currentTrack.bandwidth) return optimal;
|
|
47
|
+
if (optimal.bandwidth >= currentTrack.bandwidth * upgradeMargin) return optimal;
|
|
48
|
+
return currentTrack;
|
|
49
|
+
}
|
|
50
|
+
/**
|
|
51
|
+
* Select the lowest-bandwidth track from the candidate set.
|
|
52
|
+
*
|
|
53
|
+
* Used as a safety-net fallback by callers that need a definitive pick when
|
|
54
|
+
* a primary selection algorithm declines to choose. Pairs naturally with
|
|
55
|
+
* `selectQuality` — when ABR has no good answer (e.g., all candidates
|
|
56
|
+
* exceed available bandwidth and the algorithm doesn't fall back
|
|
57
|
+
* internally), the lowest bitrate is the safest default.
|
|
58
|
+
*
|
|
59
|
+
* @param tracks - Candidate tracks (can be unsorted)
|
|
60
|
+
* @returns The lowest-bandwidth track, or `undefined` if `tracks` is empty
|
|
61
|
+
*
|
|
62
|
+
* @example
|
|
63
|
+
* const fallback = selectLowestQuality(tracks);
|
|
64
|
+
*/
|
|
65
|
+
function selectLowestQuality(tracks) {
|
|
66
|
+
if (tracks.length === 0) return void 0;
|
|
67
|
+
return tracks.reduce((min, t) => t.bandwidth < min.bandwidth ? t : min);
|
|
68
|
+
}
|
|
69
|
+
/**
|
|
70
|
+
* Check if track A has higher resolution than track B.
|
|
71
|
+
* Compares by total pixel count (width × height).
|
|
72
|
+
*
|
|
73
|
+
* @param trackA - First track to compare
|
|
74
|
+
* @param trackB - Second track to compare
|
|
75
|
+
* @returns True if trackA has more pixels than trackB
|
|
76
|
+
*/
|
|
77
|
+
function hasHigherResolution(trackA, trackB) {
|
|
78
|
+
return (trackA.width ?? 0) * (trackA.height ?? 0) > (trackB.width ?? 0) * (trackB.height ?? 0);
|
|
79
|
+
}
|
|
80
|
+
//#endregion
|
|
81
|
+
export { DEFAULT_QUALITY_CONFIG, selectLowestQuality, selectQuality };
|
|
82
|
+
|
|
83
|
+
//# sourceMappingURL=quality-selection.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"quality-selection.js","names":[],"sources":["../../../../src/media/abr/quality-selection.ts"],"sourcesContent":["/**\n * Quality Selection Algorithm\n *\n * Selects optimal video track based on bandwidth estimate with safety margin.\n * Stateless selection - picks highest quality that fits bandwidth.\n *\n * Key concepts:\n * - **Safety margin** (0.85): Pick track where bandwidth >= track.bandwidth / 0.85\n * - This ensures 15% headroom to avoid buffering\n * - At same bandwidth, prefer higher resolution\n */\n\nimport type { PartiallyResolvedVideoTrack, VideoTrack } from '../types';\n\n/**\n * Quality selection configuration.\n */\nexport interface QualityConfig {\n /**\n * Safety margin (0-1).\n * To select a track, need: currentBandwidth >= track.bandwidth / safetyMargin.\n * Default 0.85 means track must use ≤85% of available bandwidth (15% headroom).\n */\n safetyMargin: number;\n /**\n * Upgrade hysteresis ratio (>= 1). When `currentTrack` is supplied, an\n * upgrade is applied only if `optimal.bandwidth >= currentTrack.bandwidth * upgradeMargin`.\n * Downgrades are always applied. Default 1.15 means optimal must clear\n * the current bandwidth by at least 15% to trigger an upgrade.\n */\n upgradeMargin: number;\n}\n\n/**\n * Default quality selection configuration.\n * Values match Shaka Player upgrade threshold (0.85 = 15% headroom).\n */\nexport const DEFAULT_QUALITY_CONFIG: QualityConfig = {\n safetyMargin: 0.85,\n upgradeMargin: 1.15,\n};\n\n/**\n * Options for `selectQuality`. Spread of `Partial<QualityConfig>` plus a\n * runtime-supplied `currentTrack` for upgrade-vs-downgrade decisions.\n */\nexport interface SelectQualityOpts extends Partial<QualityConfig> {\n /**\n * Track currently selected. When supplied, `selectQuality` returns\n * `currentTrack` (no change) for upgrades that don't clear the\n * `upgradeMargin`. When omitted, no hysteresis is applied — the\n * computed optimal is returned regardless.\n */\n currentTrack?: PartiallyResolvedVideoTrack | VideoTrack;\n}\n\n/**\n * Select the track to apply now, given current bandwidth, a current\n * selection (optional), and tuning. Returns:\n *\n * - The bandwidth-fitting optimal when no `currentTrack` is supplied.\n * - The optimal when it's a downgrade vs. `currentTrack` (downgrades\n * apply immediately — no hysteresis).\n * - The optimal when it clears `currentTrack.bandwidth * upgradeMargin`\n * (upgrade clears hysteresis).\n * - `currentTrack` itself when an upgrade doesn't clear the margin\n * (stay put — caller checks identity to no-op).\n *\n * \"Optimal\" is the highest-bandwidth track where the available bandwidth\n * meets the safety requirement (`currentBandwidth >= track.bandwidth / safetyMargin`).\n * Falls back to the lowest-bandwidth track when nothing fits the safety\n * margin (preserves a definitive pick under under-bandwidth conditions).\n *\n * @example\n * const tracks = [low, mid, high];\n * selectQuality(tracks, 5_000_000, { currentTrack: low });\n * // Returns `high` if 5 Mbps clears safety AND high.bandwidth >= low.bandwidth * upgradeMargin.\n * // Returns `low` (no-op signal) otherwise.\n */\nexport function selectQuality(\n tracks: readonly (PartiallyResolvedVideoTrack | VideoTrack)[],\n currentBandwidth: number,\n opts: SelectQualityOpts = {}\n): PartiallyResolvedVideoTrack | VideoTrack | undefined {\n if (tracks.length === 0) {\n return undefined;\n }\n\n const safetyMargin = opts.safetyMargin ?? DEFAULT_QUALITY_CONFIG.safetyMargin;\n const upgradeMargin = opts.upgradeMargin ?? DEFAULT_QUALITY_CONFIG.upgradeMargin;\n const { currentTrack } = opts;\n\n // Sort tracks by bandwidth (lowest first)\n const sortedTracks = tracks.slice().sort((a, b) => a.bandwidth - b.bandwidth);\n\n // Start with no selection\n let chosen: PartiallyResolvedVideoTrack | VideoTrack | undefined;\n\n for (const track of sortedTracks) {\n // Check if we have enough bandwidth for this track with safety margin\n // Required bandwidth = track.bandwidth / safetyMargin\n const requiredBandwidth = track.bandwidth / safetyMargin;\n\n if (currentBandwidth >= requiredBandwidth) {\n // We can support this track - prefer it if better than current choice\n if (\n !chosen ||\n track.bandwidth > chosen.bandwidth ||\n (track.bandwidth === chosen.bandwidth && hasHigherResolution(track, chosen))\n ) {\n chosen = track;\n }\n }\n }\n\n // If no track fits with safety margin, fall back to lowest quality\n const optimal = chosen ?? sortedTracks[0];\n if (!optimal) return undefined;\n\n // Apply upgrade hysteresis. No currentTrack → no hysteresis, return\n // optimal. Downgrade (optimal.bandwidth < current) → always apply.\n // Upgrade → only when `optimal.bandwidth >= current * upgradeMargin`,\n // else stay put (return currentTrack so caller's id-compare no-ops).\n if (!currentTrack) return optimal;\n if (optimal.bandwidth < currentTrack.bandwidth) return optimal;\n if (optimal.bandwidth >= currentTrack.bandwidth * upgradeMargin) return optimal;\n return currentTrack;\n}\n\n/**\n * Select the lowest-bandwidth track from the candidate set.\n *\n * Used as a safety-net fallback by callers that need a definitive pick when\n * a primary selection algorithm declines to choose. Pairs naturally with\n * `selectQuality` — when ABR has no good answer (e.g., all candidates\n * exceed available bandwidth and the algorithm doesn't fall back\n * internally), the lowest bitrate is the safest default.\n *\n * @param tracks - Candidate tracks (can be unsorted)\n * @returns The lowest-bandwidth track, or `undefined` if `tracks` is empty\n *\n * @example\n * const fallback = selectLowestQuality(tracks);\n */\nexport function selectLowestQuality<T extends { bandwidth: number }>(tracks: readonly T[]): T | undefined {\n if (tracks.length === 0) return undefined;\n return tracks.reduce((min, t) => (t.bandwidth < min.bandwidth ? t : min));\n}\n\n/**\n * Check if track A has higher resolution than track B.\n * Compares by total pixel count (width × height).\n *\n * @param trackA - First track to compare\n * @param trackB - Second track to compare\n * @returns True if trackA has more pixels than trackB\n */\nfunction hasHigherResolution(\n trackA: PartiallyResolvedVideoTrack | VideoTrack,\n trackB: PartiallyResolvedVideoTrack | VideoTrack\n): boolean {\n const pixelsA = (trackA.width ?? 0) * (trackA.height ?? 0);\n const pixelsB = (trackB.width ?? 0) * (trackB.height ?? 0);\n return pixelsA > pixelsB;\n}\n"],"mappings":";;;;;AAqCA,MAAa,yBAAwC;CACnD,cAAc;CACd,eAAe;CAChB;;;;;;;;;;;;;;;;;;;;;;;;AAuCD,SAAgB,cACd,QACA,kBACA,OAA0B,EAAE,EAC0B;AACtD,KAAI,OAAO,WAAW,EACpB;CAGF,MAAM,eAAe,KAAK,gBAAgB,uBAAuB;CACjE,MAAM,gBAAgB,KAAK,iBAAiB,uBAAuB;CACnE,MAAM,EAAE,iBAAiB;CAGzB,MAAM,eAAe,OAAO,OAAO,CAAC,MAAM,GAAG,MAAM,EAAE,YAAY,EAAE,UAAU;CAG7E,IAAI;AAEJ,MAAK,MAAM,SAAS,aAKlB,KAAI,oBAFsB,MAAM,YAAY;MAKxC,CAAC,UACD,MAAM,YAAY,OAAO,aACxB,MAAM,cAAc,OAAO,aAAa,oBAAoB,OAAO,OAAO,CAE3E,UAAS;;CAMf,MAAM,UAAU,UAAU,aAAa;AACvC,KAAI,CAAC,QAAS,QAAO,KAAA;AAMrB,KAAI,CAAC,aAAc,QAAO;AAC1B,KAAI,QAAQ,YAAY,aAAa,UAAW,QAAO;AACvD,KAAI,QAAQ,aAAa,aAAa,YAAY,cAAe,QAAO;AACxE,QAAO;;;;;;;;;;;;;;;;;AAkBT,SAAgB,oBAAqD,QAAqC;AACxG,KAAI,OAAO,WAAW,EAAG,QAAO,KAAA;AAChC,QAAO,OAAO,QAAQ,KAAK,MAAO,EAAE,YAAY,IAAI,YAAY,IAAI,IAAK;;;;;;;;;;AAW3E,SAAS,oBACP,QACA,QACS;AAGT,SAFiB,OAAO,SAAS,MAAM,OAAO,UAAU,MACvC,OAAO,SAAS,MAAM,OAAO,UAAU"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
//#region src/media/buffer/back-buffer.d.ts
|
|
2
|
+
/**
|
|
3
|
+
* Back buffer configuration.
|
|
4
|
+
*/
|
|
5
|
+
interface BackBufferConfig {
|
|
6
|
+
/**
|
|
7
|
+
* Number of segments to keep behind current playback position.
|
|
8
|
+
* Default: 2 segments.
|
|
9
|
+
*/
|
|
10
|
+
keepSegments: number;
|
|
11
|
+
}
|
|
12
|
+
//#endregion
|
|
13
|
+
export { BackBufferConfig };
|
|
14
|
+
//# sourceMappingURL=back-buffer.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"back-buffer.d.ts","names":[],"sources":["../../../../src/media/buffer/back-buffer.ts"],"mappings":";;;;UAYiB,gBAAA;;;;;EAKf,YAAA;AAAA"}
|