@tidal-music/player-web-components 0.2.1 → 0.3.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.
Files changed (31) hide show
  1. package/dist/active-device-changed-BDbOSq7P-DQ6vFR_K.js +7 -0
  2. package/dist/active-device-mode-changed-OmLVES_4-zwN5exje.js +7 -0
  3. package/dist/audio-context-store-Bf50rcqa-DUuCXOzU.js +36 -0
  4. package/dist/basePlayer-D9LFxFnB-BNIKxMHD.js +380 -0
  5. package/dist/browserPlayer-BzBNrx-C-DjxeaFTq.js +170 -0
  6. package/dist/generate-guid-BMGZjV-R-D16yCCHx.js +1716 -0
  7. package/dist/index.js +368 -10
  8. package/dist/load-L6Urw8gV-CQAMBwcN.js +29443 -0
  9. package/dist/media-element-error-circuit-breaker-BUJbK6sd-DNlFckiw.js +22 -0
  10. package/dist/nativePlayer-DtYpfmo5-nNN5yO4E.js +232 -0
  11. package/dist/output-devices-CPJfYcO--BP7JMB6k.js +156 -0
  12. package/dist/pushkin-C7W2HCqN-BHqS8oLX.js +117 -0
  13. package/dist/pushkin-dg1sQNx0-CAPg-zq7.js +2 -0
  14. package/dist/shakaPlayer-CqIY64ST-BhwOXSvi.js +1448 -0
  15. package/dist/src/helpers.d.ts +18 -0
  16. package/dist/src/index.d.ts +7 -0
  17. package/dist/src/tidal-current-time.d.ts +9 -0
  18. package/dist/src/tidal-duration-time.d.ts +9 -0
  19. package/dist/src/tidal-play-trigger.d.ts +2 -0
  20. package/dist/src/tidal-progress-bar.d.ts +2 -0
  21. package/dist/src/tidal-video-view.d.ts +2 -0
  22. package/dist/state-BT7sE_jc-iVaBwnBC.js +210 -0
  23. package/package.json +15 -13
  24. package/dist/_commonjsHelpers-DaMA6jEr-DtILRGNx.js +0 -8
  25. package/dist/basePlayer-Rqi9yRuo-4eKn-Akv.js +0 -528
  26. package/dist/browserPlayer-CXURpXdL-DjOb2ySS.js +0 -259
  27. package/dist/index-DHnVYeec.js +0 -3391
  28. package/dist/index.d.ts +0 -24
  29. package/dist/nativePlayer-b92CavhC-CABrQPGS.js +0 -323
  30. package/dist/output-devices-CUurcKto-C_F_9nLk.js +0 -224
  31. package/dist/shakaPlayer-D0NCOzx8-Dd1YFBoR.js +0 -24403
@@ -0,0 +1,7 @@
1
+ //#region ../player/dist/active-device-changed-BDbOSq7P.js
2
+ var e = "active-device-changed";
3
+ function t(t) {
4
+ return new CustomEvent(e, { detail: t });
5
+ }
6
+ //#endregion
7
+ export { t };
@@ -0,0 +1,7 @@
1
+ //#region ../player/dist/active-device-mode-changed-OmLVES_4.js
2
+ var e = "active-device-mode-changed";
3
+ function t(t) {
4
+ return new CustomEvent(e, { detail: t });
5
+ }
6
+ //#endregion
7
+ export { t };
@@ -0,0 +1,36 @@
1
+ //#region ../player/dist/audio-context-store-Bf50rcqa.js
2
+ var e = (e, t, n) => {
3
+ for (let r of e) {
4
+ let e = r.addedNodes[0];
5
+ r.type === "childList" && e.id === t && n();
6
+ }
7
+ };
8
+ function t() {
9
+ let t = document.getElementById("tidal-player-root");
10
+ if (!t) return Promise.reject("No player root");
11
+ if ("video-one" in t.children) return Promise.resolve();
12
+ let n = [];
13
+ return "video-one" in t.children || n.push(new Promise((n) => {
14
+ new MutationObserver((t) => e(t, "video-one", n)).observe(t, { childList: !0 });
15
+ })), Promise.all(n);
16
+ }
17
+ var n = document.createElement("video"), r = document.createElement("video"), i = (e) => {
18
+ e.setAttribute("crossorigin", "anonymous"), e.setAttribute("playsinline", "playsinline");
19
+ };
20
+ i(n), n.id = "video-one", i(r), r.id = "video-two";
21
+ var a = "tidal-player-root";
22
+ function o() {
23
+ let e = document.getElementById(a);
24
+ return e && !(e instanceof HTMLDivElement) && (e.remove(), e = null), e || (e = document.createElement("div"), e.id = a, e.style.position = "absolute", e.style.width = "0", e.style.height = "0", e.style.overflow = "hidden", document.body.appendChild(e)), s();
25
+ }
26
+ function s() {
27
+ let e = document.getElementById(a);
28
+ return e && (e.contains(n) || e.appendChild(n), e.contains(r) || e.appendChild(r)), t();
29
+ }
30
+ function c() {
31
+ return new Promise((e) => document.addEventListener("click", () => {
32
+ n.readyState === HTMLMediaElement.HAVE_NOTHING && !n.src && n.load(), r.readyState === HTMLMediaElement.HAVE_NOTHING && !r.src && r.load(), e();
33
+ }, { once: !0 }));
34
+ }
35
+ //#endregion
36
+ export { s as a, r as i, n, o as r, c as t };
@@ -0,0 +1,380 @@
1
+ import { a as e, i as t, l as n, o as r, t as i, u as a } from "./state-BT7sE_jc-iVaBwnBC.js";
2
+ import { t as o } from "./pushkin-C7W2HCqN-BHqS8oLX.js";
3
+ import { a as s, c, d as l, f as u, i as d, l as f, o as p, s as m, t as h, u as g } from "./load-L6Urw8gV-CQAMBwcN.js";
4
+ //#region ../player/dist/basePlayer-D9LFxFnB.js
5
+ function _(e, t) {
6
+ return new CustomEvent("media-product-transition", { detail: {
7
+ mediaProduct: e,
8
+ playbackContext: t
9
+ } });
10
+ }
11
+ var v = ({ assetPosition: e, duration: t, playbackInfo: n, streamInfo: r }) => ({
12
+ actualAssetPresentation: n.assetPresentation,
13
+ actualAudioMode: "audioMode" in n ? n.audioMode : null,
14
+ actualAudioQuality: "audioQuality" in n ? n.audioQuality : null,
15
+ actualDuration: t,
16
+ actualProductId: String("videoId" in n ? n.videoId : n.trackId),
17
+ actualStreamType: "streamType" in n ? n.streamType : null,
18
+ actualVideoQuality: "videoQuality" in n ? n.videoQuality : null,
19
+ assetPosition: e,
20
+ bandwidth: null,
21
+ bitDepth: r.bitDepth ?? null,
22
+ codec: r.codec ?? null,
23
+ playbackSessionId: r.streamingSessionId,
24
+ previewReason: n.previewReason ?? void 0,
25
+ sampleRate: r.sampleRate ?? null
26
+ });
27
+ function y(e, t) {
28
+ return new CustomEvent("ended", { detail: {
29
+ mediaProduct: t,
30
+ reason: e
31
+ } });
32
+ }
33
+ function b(e) {
34
+ return new CustomEvent("playback-state-change", { detail: { state: e } });
35
+ }
36
+ function x() {
37
+ return new CustomEvent("preload-request");
38
+ }
39
+ function S(e) {
40
+ return Math.min(10 ** ((4 + e) / 20), 1 / 1);
41
+ }
42
+ var C = 500;
43
+ function w(e) {
44
+ if (typeof e == "string") return T(e);
45
+ if (!e || typeof e != "object") return e;
46
+ if (e instanceof Error) return {
47
+ message: e.message,
48
+ name: e.name,
49
+ stack: e.stack
50
+ };
51
+ if (e instanceof Event || e instanceof Element) return e;
52
+ if (Array.isArray(e)) return e.map(w);
53
+ let t = {};
54
+ for (let [n, r] of Object.entries(e)) {
55
+ if (E(n)) {
56
+ t[n] = typeof r == "string" ? `[redacted ${n}, ${r.length} chars]` : `[redacted ${n}]`;
57
+ continue;
58
+ }
59
+ t[n] = w(r);
60
+ }
61
+ return t;
62
+ }
63
+ function T(e) {
64
+ if (e.startsWith("data:")) return `[redacted data URL, ${e.length} chars]`;
65
+ if (e.startsWith("http://") || e.startsWith("https://")) {
66
+ let t = e.indexOf("?");
67
+ if (t !== -1) return `${e.slice(0, t)}?[redacted query, ${e.length - t - 1} chars]`;
68
+ }
69
+ return e.length > C ? `${e.slice(0, C)}...[truncated ${e.length} chars]` : e;
70
+ }
71
+ function E(e) {
72
+ return e === "manifest" || e === "streamUrl" ? !0 : /token/i.test(e);
73
+ }
74
+ function D(e) {
75
+ switch (e) {
76
+ case "completed": return "COMPLETE";
77
+ case "error": return "ERROR";
78
+ default: return "OTHER";
79
+ }
80
+ }
81
+ var O = class {
82
+ #e;
83
+ #t;
84
+ #n;
85
+ #r = void 0;
86
+ #i;
87
+ #a = "IDLE";
88
+ #o;
89
+ #s;
90
+ name;
91
+ constructor() {
92
+ n.addEventListener("desiredVolumeLevel", () => {
93
+ this.isActivePlayer && this.updateVolumeLevel();
94
+ });
95
+ }
96
+ #c() {
97
+ let t = a("crossfadeInMs") / 1e3;
98
+ this.duration && Math.abs(this.#t - this.duration + t) <= 15 && this.#r === !1 && (this.debugLog("maybeDispatchPreloadRequest", {
99
+ crossfadeInS: t,
100
+ currentTime: this.#t,
101
+ duration: this.duration
102
+ }, Math.abs(this.#t - this.duration + t)), this.#r = !0, e.dispatchEvent(x()));
103
+ }
104
+ #l({ endAssetPosition: n, endReason: r, isSeamlessTransition: a = !1, streamingSessionId: s }) {
105
+ this.debugLog("mediaProductEnded"), !a && i.preloadedStreamingSessionId && performance.mark("streaming_metrics:playback_statistics:idealStartTimestamp", {
106
+ detail: i.preloadedStreamingSessionId,
107
+ startTime: o.now()
108
+ });
109
+ let c = t.getMediaProductTransition(s);
110
+ !a && c && e.dispatchEvent(y(r, c.mediaProduct)), this.eventTrackingStreamingEnded(s, {
111
+ endAssetPosition: n,
112
+ endReason: r
113
+ }), t.deleteSession(s), this.currentStreamingSessionId === s && (this.currentStreamingSessionId = void 0), a || this.updateVolumeLevelForNextProduct();
114
+ }
115
+ adjustedVolume(e) {
116
+ let t = a("desiredVolumeLevel"), n = a("loudnessNormalizationMode"), r = t;
117
+ return n === "ALBUM" && e.albumReplayGain && (r *= S(e.albumReplayGain)), n === "TRACK" && e.trackReplayGain && (r *= S(e.trackReplayGain)), this.debugLog("adjustedVolume", `Volume adjusted from ${t} to ${r}`), parseFloat(r.toFixed(2));
118
+ }
119
+ attachPlaybackEngineEndedHandler() {
120
+ this.#n || (this.#n = this.playbackEngineEndedHandler.bind(this), e.addEventListener("ended", this.#n));
121
+ }
122
+ cleanUpStoredPreloadInfo() {
123
+ this.preloadedStreamingSessionId && this.preloadedStreamingSessionId !== this.currentStreamingSessionId && (t.deleteSession(this.preloadedStreamingSessionId), this.preloadedStreamingSessionId = void 0);
124
+ }
125
+ get currentMediaProduct() {
126
+ return t.getMediaProductTransition(this.currentStreamingSessionId)?.mediaProduct ?? null;
127
+ }
128
+ set currentStreamingSessionId(e) {
129
+ this.#e = e;
130
+ }
131
+ get currentStreamingSessionId() {
132
+ return this.#e;
133
+ }
134
+ set currentTime(e) {
135
+ this.#t = e, this.#c();
136
+ }
137
+ get currentTime() {
138
+ return this.#t;
139
+ }
140
+ debugLog(...e) {
141
+ (document.location.hostname === "localhost" || document.location.hostname === "dev.tidal.com") && document.location.hash.includes("debug") && console.debug(`[%cPlayerSDK${this.name ? `%c${i.activePlayer?.name === this.name ? "⚯" : "⚮"}%c` + this.name : ""}${this.#e ? "%c::%c" + this.#e?.split("-").pop() : ""}%c]`, "color:#00d6ff", ...this.name ? ["color:inherit", "color:#b7fa34"] : [], ...this.#e ? ["color:inherit", "color:#d947ff"] : [], "color:inherit", ...e.map(w));
142
+ }
143
+ detachPlaybackEngineEndedHandler() {
144
+ this.#n &&= (e.removeEventListener("ended", this.#n), void 0);
145
+ }
146
+ get duration() {
147
+ let e = t.getMediaProductTransition(this.currentStreamingSessionId);
148
+ return e ? e.playbackContext.actualDuration : null;
149
+ }
150
+ eventTrackingStreamingEnded(e, { endAssetPosition: t, endReason: n }) {
151
+ let r = o.now();
152
+ u([d({
153
+ endAssetPosition: t,
154
+ endTimestamp: r,
155
+ streamingSessionId: e
156
+ })]).catch(console.error), l([s({
157
+ endReason: D(n),
158
+ endTimestamp: r,
159
+ streamingSessionId: e
160
+ }), g({
161
+ streamingSessionId: e,
162
+ timestamp: r
163
+ })]).catch(console.error);
164
+ }
165
+ eventTrackingStreamingStarted(e) {
166
+ if (!e) return;
167
+ performance.mark("streaming_metrics:playback_statistics:actualStartTimestamp", {
168
+ detail: e,
169
+ startTime: o.now()
170
+ }), performance.measure("idealStartTimestamp -> actualStartTimestamp", {
171
+ detail: e,
172
+ end: "streaming_metrics:playback_statistics:actualStartTimestamp",
173
+ start: "streaming_metrics:playback_statistics:idealStartTimestamp"
174
+ });
175
+ try {
176
+ s({
177
+ actualStartTimestamp: o.timestamp("streaming_metrics:playback_statistics:actualStartTimestamp", e),
178
+ idealStartTimestamp: o.timestamp("streaming_metrics:playback_statistics:idealStartTimestamp", e),
179
+ outputDevice: this.#i,
180
+ streamingSessionId: e
181
+ });
182
+ } catch (e) {
183
+ console.error(e, "actualStartTimestamp or idealStartTimestamp is missing for this streaming session");
184
+ } finally {
185
+ performance.clearMarks("streaming_metrics:playback_statistics:actualStartTimestamp"), performance.clearMarks("streaming_metrics:playback_statistics:idealStartTimestamp");
186
+ }
187
+ let n = t.getMediaProductTransition(e);
188
+ if (!n) {
189
+ t.hasStartedStreamInfo(e) ? console.error(`A media product transition for streaming session #${e} has not been saved and could thus not be found for play log reporting.`) : (t.deleteStreamInfo(e), console.warn(`Streaming session #${e} has been discarded due to a new load. This could mean you have a bug in your code where you call load on Player more than once time in a very short time frame.`));
190
+ return;
191
+ }
192
+ let { mediaProduct: r, playbackContext: i } = n, a = o.now();
193
+ d({
194
+ actualAssetPresentation: i.actualAssetPresentation,
195
+ actualAudioMode: "actualAudioMode" in i ? i.actualAudioMode : null,
196
+ actualProductId: i.actualProductId,
197
+ actualQuality: i.actualAudioQuality || i.actualVideoQuality,
198
+ extras: r.extras,
199
+ isPostPaywall: p(i.actualAssetPresentation, r),
200
+ playbackSessionId: e,
201
+ productType: f(r.productType),
202
+ requestedProductId: r.productId,
203
+ sourceId: r.sourceId,
204
+ sourceType: r.sourceType,
205
+ startAssetPosition: this.startAssetPosition,
206
+ startTimestamp: a,
207
+ streamingSessionId: e
208
+ }).catch(console.error);
209
+ }
210
+ get expired() {
211
+ let e = t.getStreamInfo(this.currentStreamingSessionId);
212
+ return e ? e.expires <= Date.now() : !1;
213
+ }
214
+ finishCurrentMediaProduct(e, n = !1) {
215
+ if (!this.hasStarted()) return;
216
+ let r = this.#e, i = r ? t.hasStreamInfo(r) : !1;
217
+ !n && !this.preloadedStreamingSessionId && (this.playbackState = "IDLE"), r && i && this.#l({
218
+ endAssetPosition: this.currentTime,
219
+ endReason: e,
220
+ isSeamlessTransition: n,
221
+ streamingSessionId: r
222
+ });
223
+ }
224
+ getPosition() {
225
+ return 0;
226
+ }
227
+ async hardReload(e, t) {
228
+ return this.currentStreamingSessionId && this.finishCurrentMediaProduct("skip"), m(e, t);
229
+ }
230
+ hasNextItem() {
231
+ return this.preloadedStreamingSessionId;
232
+ }
233
+ hasStarted() {
234
+ return this.currentStreamingSessionId && t.hasStartedStreamInfo(this.currentStreamingSessionId);
235
+ }
236
+ get isActivePlayer() {
237
+ return i.activePlayer && this.name === i.activePlayer.name;
238
+ }
239
+ load(e, t) {
240
+ return Promise.resolve();
241
+ }
242
+ async maybeHardReload() {
243
+ let e = this.prefetched || this.expired;
244
+ return this.currentMediaProduct && e ? (await this.hardReload(this.currentMediaProduct, this.currentTime), !0) : !1;
245
+ }
246
+ mediaProductStarted(e) {
247
+ !e || t.hasStartedStreamInfo(e) || (this.debugLog("mediaProductStarted"), this.eventTrackingStreamingStarted(e), t.setStartedStreamInfo(e), this.updateVolumeLevel(), this.#r = !1, this.preloadedStreamingSessionId = void 0, this.unloadPreloadedMediaProduct().catch(console.error), this.attachPlaybackEngineEndedHandler());
248
+ }
249
+ next(e) {
250
+ return Promise.resolve();
251
+ }
252
+ get nextItem() {
253
+ if (this.preloadedStreamingSessionId) return t.getMediaProductTransition(this.preloadedStreamingSessionId);
254
+ }
255
+ set outputDeviceType(e) {
256
+ this.#i = e ? c(e) : void 0;
257
+ }
258
+ overwriteMediaProduct(e, n) {
259
+ let r = t.getMediaProductTransition(e);
260
+ if (r) {
261
+ t.deleteMediaProductTransition(e);
262
+ let i = {
263
+ mediaProduct: {
264
+ ...r.mediaProduct,
265
+ ...n
266
+ },
267
+ playbackContext: { ...r.playbackContext }
268
+ };
269
+ t.saveMediaProductTransition(e, i);
270
+ }
271
+ }
272
+ pause() {}
273
+ play() {
274
+ return Promise.resolve();
275
+ }
276
+ playbackEngineEndedHandler(e) {
277
+ return Promise.resolve();
278
+ }
279
+ set playbackState(t) {
280
+ let n = this.#a;
281
+ if (n === t || !this.currentStreamingSessionId) return;
282
+ let r = (e, r) => n === e && r === t;
283
+ switch (!0) {
284
+ case r("NOT_PLAYING", "STALLED"):
285
+ case r("IDLE", "STALLED"): return;
286
+ case r("PLAYING", "NOT_PLAYING"):
287
+ case r("PLAYING", "IDLE"):
288
+ this.duration && this.currentTime < this.duration && h(this.currentStreamingSessionId, {
289
+ actionType: "PLAYBACK_STOP",
290
+ assetPosition: this.currentTime,
291
+ timestamp: o.now()
292
+ }).catch(console.error);
293
+ break;
294
+ case r("IDLE", "PLAYING"):
295
+ case r("NOT_PLAYING", "PLAYING"):
296
+ this.currentTime !== this.startAssetPosition && h(this.currentStreamingSessionId, {
297
+ actionType: "PLAYBACK_START",
298
+ assetPosition: this.currentTime,
299
+ timestamp: o.now()
300
+ }).catch(console.error);
301
+ break;
302
+ default: break;
303
+ }
304
+ this.#a = t, this.debugLog(`playbackState: ${t}`);
305
+ let a = i.activePlayer === void 0;
306
+ (this.isActivePlayer || a) && e.dispatchEvent(b(this.#a));
307
+ }
308
+ get playbackState() {
309
+ return this.#a;
310
+ }
311
+ get prefetched() {
312
+ return t.getStreamInfo(this.currentStreamingSessionId)?.prefetched;
313
+ }
314
+ set preloadedStreamingSessionId(e) {
315
+ this.#o = e;
316
+ }
317
+ get preloadedStreamingSessionId() {
318
+ return this.#o;
319
+ }
320
+ reset(e) {
321
+ return Promise.resolve();
322
+ }
323
+ seek(e) {}
324
+ seekEnd(t) {
325
+ let n = this.currentStreamingSessionId;
326
+ if (n) {
327
+ let r = () => h(n, {
328
+ actionType: "PLAYBACK_START",
329
+ assetPosition: t,
330
+ timestamp: o.now()
331
+ });
332
+ if (this.playbackState === "PLAYING") r().catch(console.error);
333
+ else {
334
+ let t = () => {
335
+ this.playbackState === "PLAYING" && (r().catch(console.error), e.removeEventListener("playback-state-change", t));
336
+ };
337
+ e.addEventListener("playback-state-change", t);
338
+ }
339
+ }
340
+ }
341
+ seekStart(e) {
342
+ this.currentStreamingSessionId && h(this.currentStreamingSessionId, {
343
+ actionType: "PLAYBACK_STOP",
344
+ assetPosition: e,
345
+ timestamp: o.now()
346
+ }).catch(console.error);
347
+ }
348
+ async setStateToXIfNotYInZMs(e, t, n) {
349
+ await r(e), this.playbackState !== t && (this.playbackState = n);
350
+ }
351
+ skipToPreloadedMediaProduct() {
352
+ return Promise.resolve();
353
+ }
354
+ get startAssetPosition() {
355
+ return this.#s;
356
+ }
357
+ set startAssetPosition(e) {
358
+ this.#s = e;
359
+ }
360
+ unloadPreloadedMediaProduct() {
361
+ return Promise.resolve();
362
+ }
363
+ updateOutputDevice() {
364
+ return Promise.resolve();
365
+ }
366
+ updateVolumeLevel() {
367
+ let e = t.getStreamInfo(this.currentStreamingSessionId);
368
+ e && (this.volume = this.adjustedVolume(e));
369
+ }
370
+ updateVolumeLevelForNextProduct() {
371
+ let e = t.getStreamInfo(this.preloadedStreamingSessionId);
372
+ e && (this.volume = this.adjustedVolume(e));
373
+ }
374
+ get volume() {
375
+ return 1;
376
+ }
377
+ set volume(e) {}
378
+ };
379
+ //#endregion
380
+ export { _ as n, v as r, O as t };
@@ -0,0 +1,170 @@
1
+ import { a as e, i as t, o as n, u as r } from "./state-BT7sE_jc-iVaBwnBC.js";
2
+ import { a as i, n as a } from "./audio-context-store-Bf50rcqa-DUuCXOzU.js";
3
+ import { n as o, r as s, t as c } from "./basePlayer-D9LFxFnB-BNIKxMHD.js";
4
+ import { t as l } from "./media-element-error-circuit-breaker-BUJbK6sd-DNlFckiw.js";
5
+ //#region ../player/dist/browserPlayer-BzBNrx-C.js
6
+ var u = class extends c {
7
+ #e;
8
+ #t;
9
+ #n = !0;
10
+ #r;
11
+ #i = l();
12
+ #a;
13
+ #o = document.createElement("video");
14
+ #s = !1;
15
+ name = "browserPlayer";
16
+ constructor() {
17
+ super(), this.playbackState = "IDLE";
18
+ let e = () => {
19
+ this.mediaElement && !this.mediaElement.paused && (this.playbackState = "PLAYING");
20
+ }, r = (e) => {
21
+ this.currentStreamingSessionId && e.target instanceof HTMLMediaElement && t.overwriteDuration(this.currentStreamingSessionId, e.target.duration);
22
+ }, o = () => {
23
+ this.playbackState = "STALLED";
24
+ }, s = () => {
25
+ (async () => {
26
+ let e = this.#e;
27
+ if (e) {
28
+ if (this.preloadedStreamingSessionId && e.currentTime === e.duration && (await n(1e3), e.currentTime !== e.duration)) return;
29
+ this.playbackState = "NOT_PLAYING";
30
+ }
31
+ })().catch(console.error);
32
+ }, c = (e) => {
33
+ if (e instanceof Event) {
34
+ let t = e.target;
35
+ t.readyState > HTMLMediaElement.HAVE_NOTHING && (this.currentTime = t.currentTime);
36
+ }
37
+ }, l = (e) => {
38
+ c(e), this.finishCurrentMediaProduct("completed");
39
+ }, u = (e) => this.#i.handleError(e), d = () => {
40
+ this.mediaElement && (this.currentTime = this.mediaElement.currentTime, this.seekEnd(this.currentTime));
41
+ };
42
+ this.#a = {
43
+ durationChangeHandler: r,
44
+ endedHandler: l,
45
+ errorHandler: u,
46
+ pauseHandler: s,
47
+ playHandler: e,
48
+ playingHandler: e,
49
+ seekedHandler: d,
50
+ stalledHandler: o,
51
+ timeUpdateHandler: c,
52
+ waitingHandler: o
53
+ }, i().then().catch(console.error), this.#t = a, this.currentPlayer = this.#t;
54
+ }
55
+ #c(e, t) {
56
+ this.debugLog("mediaElementEvents", t ? "adding to" : "removing from", e);
57
+ let n = t ? "addEventListener" : "removeEventListener";
58
+ e[n]("durationchange", this.#a.durationChangeHandler, { passive: !0 }), e[n]("play", this.#a.playHandler, { passive: !0 }), e[n]("playing", this.#a.playingHandler, { passive: !0 }), e[n]("timeupdate", this.#a.timeUpdateHandler, { passive: !0 }), e[n]("pause", this.#a.pauseHandler, { passive: !0 }), e[n]("ended", this.#a.endedHandler, { passive: !0 }), e[n]("error", this.#a.errorHandler, { passive: !0 }), e[n]("waiting", this.#a.waitingHandler, { passive: !0 }), e[n]("stalled", this.#a.stalledHandler, { passive: !0 }), e[n]("seeked", this.#a.seekedHandler, { passive: !0 });
59
+ }
60
+ get currentPlayer() {
61
+ return this.#e;
62
+ }
63
+ set currentPlayer(e) {
64
+ this.debugLog("set currentPlayer", e), this.#e && (this.#c(this.#e, !1), this.#e.load()), e && (this.#e = e, this.#c(e, !0));
65
+ }
66
+ getPosition() {
67
+ return this.debugLog("getPosition"), this.mediaElement && (this.mediaElement.ended ? this.currentTime = 0 : this.currentTime = this.mediaElement.currentTime), this.currentTime;
68
+ }
69
+ async load(n, r) {
70
+ this.debugLog("load", n), this.currentTime = n.assetPosition, this.startAssetPosition = n.assetPosition, await i(), await this.reset(), this.#n = !1, r === "explicit" && (this.playbackState = "NOT_PLAYING");
71
+ let { assetPosition: a, mediaProduct: c, playbackInfo: l, streamInfo: u } = n;
72
+ this.currentStreamingSessionId = u.streamingSessionId;
73
+ let { currentPlayer: d } = this;
74
+ if (!d) return;
75
+ let f = new Promise((e) => d.addEventListener("canplay", () => e(), { once: !0 }));
76
+ d.src = u.streamUrl, d.currentTime = a, d.load();
77
+ let p = new Promise((e) => d.addEventListener("durationchange", (t) => {
78
+ t.target instanceof HTMLMediaElement && e(t.target.duration);
79
+ }, { once: !0 }));
80
+ if (await f, this.currentStreamingSessionId !== u.streamingSessionId) return;
81
+ let m = s({
82
+ assetPosition: a,
83
+ duration: await p,
84
+ playbackInfo: l,
85
+ streamInfo: u
86
+ });
87
+ return t.saveMediaProductTransition(u.streamingSessionId, {
88
+ mediaProduct: c,
89
+ playbackContext: m
90
+ }), this.debugLog("dispatching mediaProductTransition"), e.dispatchEvent(o(c, m)), this.#s ? (this.#s = !1, this.play()) : Promise.resolve();
91
+ }
92
+ get mediaElement() {
93
+ return this.currentPlayer ?? null;
94
+ }
95
+ async next(e) {
96
+ this.debugLog("next", e), this.playbackState === "IDLE" && (this.playbackState = "NOT_PLAYING");
97
+ let { mediaProduct: n, playbackInfo: r, streamInfo: i } = e, a = this.#o;
98
+ if (this.preloadedStreamingSessionId = i.streamingSessionId, !a) return;
99
+ a.src = i.streamUrl, a.load();
100
+ let o = s({
101
+ assetPosition: 0,
102
+ duration: await new Promise((e) => a.addEventListener("durationchange", (t) => {
103
+ t.target instanceof HTMLMediaElement && e(t.target.duration);
104
+ }, { once: !0 })),
105
+ playbackInfo: r,
106
+ streamInfo: i
107
+ });
108
+ t.saveMediaProductTransition(i.streamingSessionId, {
109
+ mediaProduct: n,
110
+ playbackContext: o
111
+ }), this.#n = !1;
112
+ }
113
+ pause() {
114
+ this.debugLog("pause"), this.mediaElement && this.mediaElement.pause();
115
+ }
116
+ async play() {
117
+ if (this.debugLog("play"), await this.maybeHardReload(), this.playbackState === "IDLE") return this.debugLog("is IDLE, returning early"), this.#s = !0, Promise.resolve();
118
+ "setSinkId" in a && await this.updateOutputDevice(), this.currentStreamingSessionId && this.mediaProductStarted(this.currentStreamingSessionId), this.setStateToXIfNotYInZMs(1e3, "PLAYING", "STALLED"), this.currentPlayer && await this.currentPlayer.play().catch(console.error);
119
+ }
120
+ async playbackEngineEndedHandler(e) {
121
+ if (this.isActivePlayer) {
122
+ let { reason: t } = e.detail;
123
+ t === "completed" && (this.hasNextItem() ? (await this.skipToPreloadedMediaProduct(), await this.play()) : (console.warn("No item preloaded, not progressing."), this.playbackState = "NOT_PLAYING"));
124
+ }
125
+ }
126
+ get ready() {
127
+ return this.#r;
128
+ }
129
+ async reset({ keepPreload: e } = { keepPreload: !1 }) {
130
+ if (this.#i.reset(), this.#n) return Promise.resolve();
131
+ this.debugLog("reset"), this.playbackState !== "IDLE" && this.finishCurrentMediaProduct("skip"), this.playbackState = "IDLE", this.detachPlaybackEngineEndedHandler(), this.currentStreamingSessionId = void 0, e || (this.preloadedStreamingSessionId = void 0);
132
+ let { currentPlayer: t } = this;
133
+ return t && t.readyState !== 0 && (t.load(), await new Promise((e) => t.addEventListener("emptied", () => e(), { passive: !0 }))), this.#n = !0, Promise.resolve();
134
+ }
135
+ seek(e) {
136
+ this.debugLog("seek", e);
137
+ let { currentPlayer: t } = this, n = e;
138
+ if (t) return this.seekStart(this.currentTime), "fastSeek" in t ? t.fastSeek(n) : t.currentTime = n, new Promise((e) => {
139
+ t.addEventListener("seeked", () => e(t.currentTime), { once: !0 });
140
+ });
141
+ }
142
+ async skipToPreloadedMediaProduct() {
143
+ let n = t.getMediaProductTransition(this.preloadedStreamingSessionId);
144
+ if (!n) {
145
+ this.playbackState = "NOT_PLAYING";
146
+ return;
147
+ }
148
+ if (this.debugLog("skipToPreloadedMediaProduct", this.preloadedStreamingSessionId), this.#o.src && this.currentPlayer) {
149
+ this.currentPlayer.src = this.#o.src, this.currentStreamingSessionId = String(this.preloadedStreamingSessionId), this.preloadedStreamingSessionId = void 0;
150
+ let { mediaProduct: t, playbackContext: r } = n;
151
+ e.dispatchEvent(o(t, r)), this.playbackState === "IDLE" && (this.playbackState = "NOT_PLAYING");
152
+ }
153
+ }
154
+ togglePlayback() {
155
+ this.debugLog("togglePlayback"), this.mediaElement && (this.mediaElement.paused ? this.mediaElement.play().catch(console.error) : this.mediaElement.pause());
156
+ }
157
+ async unloadPreloadedMediaProduct() {
158
+ this.debugLog("unloadPreloadedMediaProduct", this.preloadedStreamingSessionId), this.cleanUpStoredPreloadInfo();
159
+ let e = this.#o;
160
+ e && (e.src = "", e.load());
161
+ }
162
+ get volume() {
163
+ return r("desiredVolumeLevel");
164
+ }
165
+ set volume(e) {
166
+ this.debugLog("Setting volume to", e), this.currentPlayer && (this.currentPlayer.volume = e);
167
+ }
168
+ };
169
+ //#endregion
170
+ export { u as default };