playsvideo 0.2.1 → 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +8 -3
- package/dist/engine.d.ts +74 -2
- package/dist/engine.d.ts.map +1 -1
- package/dist/engine.js +430 -47
- package/dist/engine.js.map +1 -1
- package/dist/external-subtitle-picker.d.ts +13 -0
- package/dist/external-subtitle-picker.d.ts.map +1 -0
- package/dist/external-subtitle-picker.js +41 -0
- package/dist/external-subtitle-picker.js.map +1 -0
- package/dist/index.d.ts +3 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -0
- package/dist/index.js.map +1 -1
- package/dist/pipeline/codec-probe.d.ts.map +1 -1
- package/dist/pipeline/codec-probe.js +8 -0
- package/dist/pipeline/codec-probe.js.map +1 -1
- package/dist/pipeline/segment-plan.d.ts.map +1 -1
- package/dist/pipeline/segment-plan.js +25 -11
- package/dist/pipeline/segment-plan.js.map +1 -1
- package/dist/playback-selection.d.ts +82 -0
- package/dist/playback-selection.d.ts.map +1 -0
- package/dist/playback-selection.js +194 -0
- package/dist/playback-selection.js.map +1 -0
- package/dist/transcode-protocol.d.ts +16 -0
- package/dist/transcode-protocol.d.ts.map +1 -1
- package/dist/transcode-worker.js +54 -0
- package/dist/transcode-worker.js.map +1 -1
- package/dist/worker-protocol.d.ts +9 -0
- package/dist/worker-protocol.d.ts.map +1 -0
- package/dist/worker-protocol.js +2 -0
- package/dist/worker-protocol.js.map +1 -0
- package/dist/worker.js +29 -0
- package/dist/worker.js.map +1 -1
- package/package.json +2 -1
package/README.md
CHANGED
|
@@ -18,7 +18,7 @@ Many video files won't play in a browser — not because the browser can't *deco
|
|
|
18
18
|
|---|---|---|
|
|
19
19
|
| **Containers** | MKV, MP4, AVI, TS, WebM | Demuxed and remuxed to fMP4 |
|
|
20
20
|
| **Video** | H.264, H.265 (HEVC), VP9, AV1 | Passthrough — plays ~99% of files (~90% on Firefox; HEVC transcode planned) |
|
|
21
|
-
| **Audio** | AAC, MP3, AC-3, E-AC-3, DTS, FLAC, Opus |
|
|
21
|
+
| **Audio** | AAC, MP3, AC-3, E-AC-3, DTS, FLAC, Opus | Transcoded to AAC when the active playback path cannot use them safely |
|
|
22
22
|
| **Subtitles** | SRT, ASS/SSA | Extracted and displayed as WebVTT |
|
|
23
23
|
|
|
24
24
|
See [supported media](docs/supported-media.md) for the full codec matrix, browser compatibility, and transcode details.
|
|
@@ -30,13 +30,15 @@ Video file (MKV, MP4, AVI, …)
|
|
|
30
30
|
→ mediabunny demux (streaming, any file size)
|
|
31
31
|
→ keyframe-aligned segment plan
|
|
32
32
|
→ per segment:
|
|
33
|
-
video passed through
|
|
34
|
-
audio transcoded only if needed (AC-3/DTS/MP3/FLAC/Opus → AAC)
|
|
33
|
+
video remuxed / passed through
|
|
34
|
+
audio transcoded only if needed (AC-3/E-AC-3/DTS/MP3/FLAC/Opus → AAC)
|
|
35
35
|
muxed to fMP4
|
|
36
36
|
→ hls.js plays segments on demand
|
|
37
37
|
→ subtitles extracted to WebVTT
|
|
38
38
|
```
|
|
39
39
|
|
|
40
|
+
Note: passthrough/native playback and remuxed HLS/MSE playback are evaluated separately. A source file can play fine via direct passthrough in both Chrome and Safari on macOS, yet still be unsafe once routed through the remuxed HLS/fMP4 pipeline. That is what we observed with AC-3: the original file played directly, but Safari produced audible stalls after remuxing to HLS/fMP4, while Chrome continued to play correctly. The remux pipeline therefore treats AC-3/E-AC-3 as unsafe there and transcodes them to AAC, without affecting native passthrough decisions.
|
|
41
|
+
|
|
40
42
|
Video transcode is almost never needed — browsers natively decode the vast majority of video codecs. When audio transcode is needed, a lightweight 1.8 MB ffmpeg.wasm build is lazy-loaded entirely in-browser. No SharedArrayBuffer required — works on any host without special CORS headers.
|
|
41
43
|
|
|
42
44
|
### Under the hood
|
|
@@ -67,6 +69,9 @@ engine.loadFile(file);
|
|
|
67
69
|
// Or play from a URL (requires CORS + range request support)
|
|
68
70
|
engine.loadUrl('https://example.com/video.mkv');
|
|
69
71
|
|
|
72
|
+
// Or attach an external .srt/.vtt subtitle file after loading
|
|
73
|
+
await engine.loadExternalSubtitle(subtitleFile);
|
|
74
|
+
|
|
70
75
|
engine.destroy(); // clean up
|
|
71
76
|
```
|
|
72
77
|
|
package/dist/engine.d.ts
CHANGED
|
@@ -1,11 +1,13 @@
|
|
|
1
1
|
import type { Source } from 'mediabunny';
|
|
2
2
|
import type { FfmpegRunner, KeyframeIndex, SubtitleTrackInfo } from './pipeline/types.js';
|
|
3
|
+
import type { TranscodeWorkerSnapshot } from './transcode-protocol.js';
|
|
3
4
|
export type EnginePhase = 'idle' | 'demuxing' | 'ready' | 'error';
|
|
4
5
|
export interface ReadyDetail {
|
|
5
6
|
totalSegments: number;
|
|
6
7
|
durationSec: number;
|
|
7
8
|
subtitleTracks: SubtitleTrackInfo[];
|
|
8
9
|
passthrough?: boolean;
|
|
10
|
+
codecPath: CodecPath;
|
|
9
11
|
}
|
|
10
12
|
export interface ErrorDetail {
|
|
11
13
|
message: string;
|
|
@@ -14,6 +16,35 @@ export interface LoadingDetail {
|
|
|
14
16
|
file?: File;
|
|
15
17
|
url?: string;
|
|
16
18
|
}
|
|
19
|
+
export interface SubtitleStatusDetail {
|
|
20
|
+
message: string;
|
|
21
|
+
}
|
|
22
|
+
export interface WasmWorkerState extends TranscodeWorkerSnapshot {
|
|
23
|
+
id: number;
|
|
24
|
+
}
|
|
25
|
+
export interface WorkerStateDetail {
|
|
26
|
+
workers: WasmWorkerState[];
|
|
27
|
+
}
|
|
28
|
+
export type SegmentPhase = 'requested' | 'queued' | 'prefetching' | 'processing' | 'ready' | 'cache-hit' | 'delivered' | 'canceled' | 'aborted' | 'error';
|
|
29
|
+
export interface SegmentTimelineEvent {
|
|
30
|
+
phase: SegmentPhase;
|
|
31
|
+
atMs: number;
|
|
32
|
+
sizeBytes: number | null;
|
|
33
|
+
message: string | null;
|
|
34
|
+
}
|
|
35
|
+
export interface SegmentState {
|
|
36
|
+
index: number;
|
|
37
|
+
phase: SegmentPhase;
|
|
38
|
+
requestCount: number;
|
|
39
|
+
sizeBytes: number | null;
|
|
40
|
+
latencyMs: number | null;
|
|
41
|
+
error: string | null;
|
|
42
|
+
prefetched: boolean;
|
|
43
|
+
events: SegmentTimelineEvent[];
|
|
44
|
+
}
|
|
45
|
+
export interface SegmentStateDetail {
|
|
46
|
+
segments: SegmentState[];
|
|
47
|
+
}
|
|
17
48
|
export interface EngineOptions {
|
|
18
49
|
/**
|
|
19
50
|
* Number of internal audio transcode workers to create for worker-mode playback.
|
|
@@ -21,16 +52,36 @@ export interface EngineOptions {
|
|
|
21
52
|
*/
|
|
22
53
|
transcodeWorkers?: number;
|
|
23
54
|
}
|
|
55
|
+
export interface ExternalSubtitleOptions {
|
|
56
|
+
label?: string;
|
|
57
|
+
language?: string;
|
|
58
|
+
kind?: 'subtitles' | 'captions';
|
|
59
|
+
}
|
|
60
|
+
export interface CodecDescriptor {
|
|
61
|
+
short: string | null;
|
|
62
|
+
full: string | null;
|
|
63
|
+
}
|
|
64
|
+
export interface CodecPath {
|
|
65
|
+
mode: 'passthrough' | 'pipeline';
|
|
66
|
+
sourceVideo: CodecDescriptor;
|
|
67
|
+
sourceAudio: CodecDescriptor;
|
|
68
|
+
outputVideo: CodecDescriptor;
|
|
69
|
+
outputAudio: CodecDescriptor;
|
|
70
|
+
}
|
|
24
71
|
interface EngineEventMap {
|
|
25
72
|
ready: CustomEvent<ReadyDetail>;
|
|
26
73
|
error: CustomEvent<ErrorDetail>;
|
|
27
74
|
loading: CustomEvent<LoadingDetail>;
|
|
75
|
+
workerstatechange: CustomEvent<WorkerStateDetail>;
|
|
76
|
+
segmentstatechange: CustomEvent<SegmentStateDetail>;
|
|
28
77
|
}
|
|
29
78
|
export declare class PlaysVideoEngine extends EventTarget {
|
|
30
79
|
readonly video: HTMLVideoElement;
|
|
31
80
|
readonly options: Required<EngineOptions>;
|
|
32
81
|
private worker;
|
|
33
82
|
private transcodeWorkers;
|
|
83
|
+
private _transcodeWorkerStates;
|
|
84
|
+
private _segmentStates;
|
|
34
85
|
private hls;
|
|
35
86
|
private pendingSegments;
|
|
36
87
|
private playlist;
|
|
@@ -38,7 +89,7 @@ export declare class PlaysVideoEngine extends EventTarget {
|
|
|
38
89
|
private pendingInit;
|
|
39
90
|
private pendingPlaylist;
|
|
40
91
|
private segmentRequestTimes;
|
|
41
|
-
private
|
|
92
|
+
private attachedSubtitleTracks;
|
|
42
93
|
private _subtitleTracks;
|
|
43
94
|
private _phase;
|
|
44
95
|
private _totalSegments;
|
|
@@ -46,6 +97,7 @@ export declare class PlaysVideoEngine extends EventTarget {
|
|
|
46
97
|
private _passthrough;
|
|
47
98
|
private _blobUrl;
|
|
48
99
|
private _pendingFileType;
|
|
100
|
+
private _codecPath;
|
|
49
101
|
private _keyframeIndex;
|
|
50
102
|
private _source;
|
|
51
103
|
private _sourceDemux;
|
|
@@ -62,6 +114,9 @@ export declare class PlaysVideoEngine extends EventTarget {
|
|
|
62
114
|
get durationSec(): number;
|
|
63
115
|
get subtitleTracks(): SubtitleTrackInfo[];
|
|
64
116
|
get passthrough(): boolean;
|
|
117
|
+
get codecPath(): CodecPath;
|
|
118
|
+
get transcodeWorkerStates(): WasmWorkerState[];
|
|
119
|
+
get segmentStates(): SegmentState[];
|
|
65
120
|
constructor(video: HTMLVideoElement, options?: EngineOptions);
|
|
66
121
|
loadFile(file: File, opts?: {
|
|
67
122
|
keyframeIndex?: KeyframeIndex;
|
|
@@ -69,6 +124,8 @@ export declare class PlaysVideoEngine extends EventTarget {
|
|
|
69
124
|
loadUrl(url: string, opts?: {
|
|
70
125
|
keyframeIndex?: KeyframeIndex;
|
|
71
126
|
}): void;
|
|
127
|
+
loadExternalSubtitle(file: File, options?: ExternalSubtitleOptions): Promise<void>;
|
|
128
|
+
clearExternalSubtitles(): void;
|
|
72
129
|
/**
|
|
73
130
|
* Load from an external Source (e.g. TorrentSource).
|
|
74
131
|
*
|
|
@@ -91,7 +148,19 @@ export declare class PlaysVideoEngine extends EventTarget {
|
|
|
91
148
|
destroy(): void;
|
|
92
149
|
addEventListener<K extends keyof EngineEventMap>(type: K, listener: (ev: EngineEventMap[K]) => void, options?: boolean | AddEventListenerOptions): void;
|
|
93
150
|
addEventListener(type: string, listener: EventListenerOrEventListenerObject, options?: boolean | AddEventListenerOptions): void;
|
|
94
|
-
private
|
|
151
|
+
private dispatchWorkerStateChange;
|
|
152
|
+
private dispatchSegmentStateChange;
|
|
153
|
+
private handleTranscodeWorkerMessage;
|
|
154
|
+
private updateTranscodeWorkerState;
|
|
155
|
+
private noteSegmentState;
|
|
156
|
+
private handleWorkerSegmentState;
|
|
157
|
+
private createPlaybackCapabilities;
|
|
158
|
+
private evaluateInitialPlayback;
|
|
159
|
+
private evaluateHlsPlayback;
|
|
160
|
+
private logPlaybackDiagnostics;
|
|
161
|
+
private throwPlaybackSelectionError;
|
|
162
|
+
private failPlaybackSelection;
|
|
163
|
+
private makeCodecPathFromSource;
|
|
95
164
|
private startPassthrough;
|
|
96
165
|
private handleWorkerMessage;
|
|
97
166
|
private requestSegment;
|
|
@@ -102,6 +171,9 @@ export declare class PlaysVideoEngine extends EventTarget {
|
|
|
102
171
|
private startHls;
|
|
103
172
|
private addSubtitleTrack;
|
|
104
173
|
private removeSubtitleTracks;
|
|
174
|
+
private showTextTrack;
|
|
175
|
+
private dispatchSubtitleStatus;
|
|
176
|
+
private restoreDefaultTextTrack;
|
|
105
177
|
}
|
|
106
178
|
export {};
|
|
107
179
|
//# sourceMappingURL=engine.d.ts.map
|
package/dist/engine.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"engine.d.ts","sourceRoot":"","sources":["../src/engine.ts"],"names":[],"mappings":"AASA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,YAAY,CAAC;
|
|
1
|
+
{"version":3,"file":"engine.d.ts","sourceRoot":"","sources":["../src/engine.ts"],"names":[],"mappings":"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"}
|