hls.js 1.6.0-beta.4.0.canary.11044 → 1.6.0-beta.4.0.canary.11046
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/hls.d.mts +3 -1
- package/dist/hls.d.ts +3 -1
- package/dist/hls.js +197 -167
- package/dist/hls.js.d.ts +3 -1
- package/dist/hls.js.map +1 -1
- package/dist/hls.light.js +39 -33
- package/dist/hls.light.js.map +1 -1
- package/dist/hls.light.min.js +1 -1
- package/dist/hls.light.min.js.map +1 -1
- package/dist/hls.light.mjs +38 -32
- package/dist/hls.light.mjs.map +1 -1
- package/dist/hls.min.js +1 -1
- package/dist/hls.min.js.map +1 -1
- package/dist/hls.mjs +149 -116
- package/dist/hls.mjs.map +1 -1
- package/dist/hls.worker.js +1 -1
- package/package.json +1 -1
- package/src/controller/base-stream-controller.ts +81 -69
- package/src/controller/buffer-controller.ts +2 -3
- package/src/controller/interstitial-player.ts +6 -3
- package/src/controller/interstitials-controller.ts +51 -27
- package/src/controller/interstitials-schedule.ts +21 -12
- package/src/controller/subtitle-stream-controller.ts +15 -14
- package/src/utils/level-helper.ts +6 -9
package/dist/hls.mjs
CHANGED
@@ -402,7 +402,7 @@ function enableLogs(debugConfig, context, id) {
|
|
402
402
|
// Some browsers don't allow to use bind on console object anyway
|
403
403
|
// fallback to default if needed
|
404
404
|
try {
|
405
|
-
newLogger.log(`Debug logs enabled for "${context}" in hls.js version ${"1.6.0-beta.4.0.canary.
|
405
|
+
newLogger.log(`Debug logs enabled for "${context}" in hls.js version ${"1.6.0-beta.4.0.canary.11046"}`);
|
406
406
|
} catch (e) {
|
407
407
|
/* log fn threw an exception. All logger methods are no-ops. */
|
408
408
|
return createLogger();
|
@@ -7955,15 +7955,12 @@ function findPart(partList, sn, partIndex) {
|
|
7955
7955
|
function reassignFragmentLevelIndexes(levels) {
|
7956
7956
|
levels.forEach((level, index) => {
|
7957
7957
|
var _level$details;
|
7958
|
-
|
7959
|
-
|
7960
|
-
|
7961
|
-
fragment.level = index;
|
7962
|
-
|
7963
|
-
|
7964
|
-
}
|
7965
|
-
});
|
7966
|
-
}
|
7958
|
+
(_level$details = level.details) == null ? void 0 : _level$details.fragments.forEach(fragment => {
|
7959
|
+
fragment.level = index;
|
7960
|
+
if (fragment.initSegment) {
|
7961
|
+
fragment.initSegment.level = index;
|
7962
|
+
}
|
7963
|
+
});
|
7967
7964
|
});
|
7968
7965
|
}
|
7969
7966
|
|
@@ -8374,6 +8371,7 @@ class BaseStreamController extends TaskLoop {
|
|
8374
8371
|
this.media = this.mediaBuffer = null;
|
8375
8372
|
this.loopSn = undefined;
|
8376
8373
|
if (transferringMedia) {
|
8374
|
+
this.resetLoadingState();
|
8377
8375
|
this.resetTransmuxer();
|
8378
8376
|
return;
|
8379
8377
|
}
|
@@ -8416,42 +8414,6 @@ class BaseStreamController extends TaskLoop {
|
|
8416
8414
|
super.onHandlerDestroyed();
|
8417
8415
|
}
|
8418
8416
|
loadFragment(frag, level, targetBufferTime) {
|
8419
|
-
const config = this.hls.config;
|
8420
|
-
if (config.interstitialsController && config.enableInterstitialPlayback !== false && frag.type !== PlaylistLevelType.SUBTITLE) {
|
8421
|
-
// Do not load fragments outside the buffering schedule segment
|
8422
|
-
const interstitials = this.hls.interstitialsManager;
|
8423
|
-
const bufferingItem = interstitials == null ? void 0 : interstitials.bufferingItem;
|
8424
|
-
if (bufferingItem) {
|
8425
|
-
const bufferingInterstitial = bufferingItem.event;
|
8426
|
-
if (bufferingInterstitial) {
|
8427
|
-
// Do not stream fragments while buffering Interstitial Events (except for overlap at the start)
|
8428
|
-
if (bufferingInterstitial.appendInPlace || Math.abs(frag.start - bufferingItem.start) > 1 || bufferingItem.start === 0) {
|
8429
|
-
return;
|
8430
|
-
}
|
8431
|
-
} else {
|
8432
|
-
var _level$details;
|
8433
|
-
// Limit fragment loading to media in schedule item
|
8434
|
-
if (frag.end <= bufferingItem.start && ((_level$details = level.details) == null ? void 0 : _level$details.live) === false) {
|
8435
|
-
// fragment ends by schedule item start
|
8436
|
-
return;
|
8437
|
-
}
|
8438
|
-
if (frag.start > bufferingItem.end && bufferingItem.nextEvent) {
|
8439
|
-
// fragment is past schedule item end
|
8440
|
-
return;
|
8441
|
-
}
|
8442
|
-
}
|
8443
|
-
}
|
8444
|
-
// Skip loading of fragments that overlap completely with appendInPlace interstitials
|
8445
|
-
const playerQueue = interstitials == null ? void 0 : interstitials.playerQueue;
|
8446
|
-
if (playerQueue) {
|
8447
|
-
for (let i = playerQueue.length; i--;) {
|
8448
|
-
const interstitial = playerQueue[i].interstitial;
|
8449
|
-
if (interstitial.appendInPlace && frag.start >= interstitial.startTime && frag.end <= interstitial.resumeTime) {
|
8450
|
-
return;
|
8451
|
-
}
|
8452
|
-
}
|
8453
|
-
}
|
8454
|
-
}
|
8455
8417
|
this.startFragRequested = true;
|
8456
8418
|
this._loadFragForPlayback(frag, level, targetBufferTime);
|
8457
8419
|
}
|
@@ -8800,9 +8762,9 @@ class BaseStreamController extends TaskLoop {
|
|
8800
8762
|
}
|
8801
8763
|
doFragPartsLoad(frag, fromPart, level, progressCallback) {
|
8802
8764
|
return new Promise((resolve, reject) => {
|
8803
|
-
var _level$
|
8765
|
+
var _level$details;
|
8804
8766
|
const partsLoaded = [];
|
8805
|
-
const initialPartList = (_level$
|
8767
|
+
const initialPartList = (_level$details = level.details) == null ? void 0 : _level$details.partList;
|
8806
8768
|
const loadPart = part => {
|
8807
8769
|
this.fragmentLoader.loadPart(frag, part, progressCallback).then(partLoadedData => {
|
8808
8770
|
partsLoaded[part.index] = partLoadedData;
|
@@ -9077,6 +9039,7 @@ class BaseStreamController extends TaskLoop {
|
|
9077
9039
|
const end = this.loadingParts ? levelDetails.partEnd : levelDetails.fragmentEnd;
|
9078
9040
|
frag = this.getFragmentAtPosition(pos, end, levelDetails);
|
9079
9041
|
}
|
9042
|
+
frag = this.filterReplacedPrimary(frag, levelDetails);
|
9080
9043
|
return this.mapToInitFragWhenRequired(frag);
|
9081
9044
|
}
|
9082
9045
|
isLoopLoading(frag, targetBufferTime) {
|
@@ -9104,6 +9067,48 @@ class BaseStreamController extends TaskLoop {
|
|
9104
9067
|
this.loopSn = undefined;
|
9105
9068
|
return nextFragment;
|
9106
9069
|
}
|
9070
|
+
filterReplacedPrimary(frag, details) {
|
9071
|
+
if (!frag) {
|
9072
|
+
return frag;
|
9073
|
+
}
|
9074
|
+
const config = this.hls.config;
|
9075
|
+
if (config.interstitialsController && config.enableInterstitialPlayback !== false && frag.type !== PlaylistLevelType.SUBTITLE) {
|
9076
|
+
// Do not load fragments outside the buffering schedule segment
|
9077
|
+
const interstitials = this.hls.interstitialsManager;
|
9078
|
+
const bufferingItem = interstitials == null ? void 0 : interstitials.bufferingItem;
|
9079
|
+
if (bufferingItem) {
|
9080
|
+
const bufferingInterstitial = bufferingItem.event;
|
9081
|
+
if (bufferingInterstitial) {
|
9082
|
+
// Do not stream fragments while buffering Interstitial Events (except for overlap at the start)
|
9083
|
+
if (bufferingInterstitial.appendInPlace || Math.abs(frag.start - bufferingItem.start) > 1 || bufferingItem.start === 0) {
|
9084
|
+
return null;
|
9085
|
+
}
|
9086
|
+
} else {
|
9087
|
+
// Limit fragment loading to media in schedule item
|
9088
|
+
if (frag.end <= bufferingItem.start && (details == null ? void 0 : details.live) === false) {
|
9089
|
+
// fragment ends by schedule item start
|
9090
|
+
// this.fragmentTracker.fragBuffered(frag, true);
|
9091
|
+
return null;
|
9092
|
+
}
|
9093
|
+
if (frag.start > bufferingItem.end && bufferingItem.nextEvent) {
|
9094
|
+
// fragment is past schedule item end
|
9095
|
+
return null;
|
9096
|
+
}
|
9097
|
+
}
|
9098
|
+
}
|
9099
|
+
// Skip loading of fragments that overlap completely with appendInPlace interstitials
|
9100
|
+
const playerQueue = interstitials == null ? void 0 : interstitials.playerQueue;
|
9101
|
+
if (playerQueue) {
|
9102
|
+
for (let i = playerQueue.length; i--;) {
|
9103
|
+
const interstitial = playerQueue[i].interstitial;
|
9104
|
+
if (interstitial.appendInPlace && frag.start >= interstitial.startTime && frag.end <= interstitial.resumeTime) {
|
9105
|
+
return null;
|
9106
|
+
}
|
9107
|
+
}
|
9108
|
+
}
|
9109
|
+
}
|
9110
|
+
return frag;
|
9111
|
+
}
|
9107
9112
|
mapToInitFragWhenRequired(frag) {
|
9108
9113
|
// If an initSegment is present, it must be buffered first
|
9109
9114
|
if (frag != null && frag.initSegment && !(frag != null && frag.initSegment.data) && !this.bitrateTest) {
|
@@ -9476,7 +9481,6 @@ class BaseStreamController extends TaskLoop {
|
|
9476
9481
|
this.fragmentTracker.removeFragmentsInRange(start, Infinity, this.playlistType, false, true);
|
9477
9482
|
}
|
9478
9483
|
updateLevelTiming(frag, part, level, partial) {
|
9479
|
-
var _this$transmuxer;
|
9480
9484
|
const details = level.details;
|
9481
9485
|
if (!details) {
|
9482
9486
|
this.warn('level.details undefined');
|
@@ -9507,25 +9511,28 @@ class BaseStreamController extends TaskLoop {
|
|
9507
9511
|
}
|
9508
9512
|
return result;
|
9509
9513
|
}, false);
|
9510
|
-
if (!parsed
|
9511
|
-
|
9514
|
+
if (!parsed) {
|
9515
|
+
var _this$transmuxer;
|
9512
9516
|
if (level.fragmentError === 0) {
|
9513
9517
|
// Mark and track the odd empty segment as a gap to avoid reloading
|
9514
9518
|
this.treatAsGap(frag, level);
|
9515
9519
|
}
|
9516
|
-
this.
|
9517
|
-
|
9518
|
-
|
9519
|
-
|
9520
|
-
|
9521
|
-
|
9522
|
-
|
9523
|
-
|
9524
|
-
|
9525
|
-
|
9526
|
-
|
9520
|
+
if (((_this$transmuxer = this.transmuxer) == null ? void 0 : _this$transmuxer.error) === null) {
|
9521
|
+
const error = new Error(`Found no media in fragment ${frag.sn} of ${this.playlistLabel()} ${frag.level} resetting transmuxer to fallback to playlist timing`);
|
9522
|
+
this.warn(error.message);
|
9523
|
+
this.hls.trigger(Events.ERROR, {
|
9524
|
+
type: ErrorTypes.MEDIA_ERROR,
|
9525
|
+
details: ErrorDetails.FRAG_PARSING_ERROR,
|
9526
|
+
fatal: false,
|
9527
|
+
error,
|
9528
|
+
frag,
|
9529
|
+
reason: `Found no media in msn ${frag.sn} of ${this.playlistLabel()} "${level.url}"`
|
9530
|
+
});
|
9531
|
+
if (!this.hls) {
|
9532
|
+
return;
|
9533
|
+
}
|
9534
|
+
this.resetTransmuxer();
|
9527
9535
|
}
|
9528
|
-
this.resetTransmuxer();
|
9529
9536
|
// For this error fallthrough. Marking parsed will allow advancing to next fragment.
|
9530
9537
|
}
|
9531
9538
|
this.state = State.PARSED;
|
@@ -9968,7 +9975,7 @@ function requireEventemitter3 () {
|
|
9968
9975
|
var eventemitter3Exports = requireEventemitter3();
|
9969
9976
|
var EventEmitter = /*@__PURE__*/getDefaultExportFromCjs(eventemitter3Exports);
|
9970
9977
|
|
9971
|
-
const version = "1.6.0-beta.4.0.canary.
|
9978
|
+
const version = "1.6.0-beta.4.0.canary.11046";
|
9972
9979
|
|
9973
9980
|
// ensure the worker ends up in the bundle
|
9974
9981
|
// If the worker should not be included this gets aliased to empty.js
|
@@ -17851,15 +17858,14 @@ class BufferController extends Logger {
|
|
17851
17858
|
if (!media || !mediaSource) {
|
17852
17859
|
return;
|
17853
17860
|
}
|
17861
|
+
// once received, don't listen anymore to sourceopen event
|
17862
|
+
mediaSource.removeEventListener('sourceopen', this._onMediaSourceOpen);
|
17854
17863
|
media.removeEventListener('emptied', this._onMediaEmptied);
|
17855
17864
|
this.updateDuration();
|
17856
17865
|
this.hls.trigger(Events.MEDIA_ATTACHED, {
|
17857
17866
|
media,
|
17858
17867
|
mediaSource: mediaSource
|
17859
17868
|
});
|
17860
|
-
|
17861
|
-
// once received, don't listen anymore to sourceopen event
|
17862
|
-
mediaSource.removeEventListener('sourceopen', this._onMediaSourceOpen);
|
17863
17869
|
if (this.mediaSource !== null) {
|
17864
17870
|
this.checkPendingTracks();
|
17865
17871
|
}
|
@@ -23036,6 +23042,7 @@ class HlsAssetPlayer {
|
|
23036
23042
|
this.tracks = null;
|
23037
23043
|
this.hasDetails = false;
|
23038
23044
|
this.mediaAttached = null;
|
23045
|
+
this._currentTime = void 0;
|
23039
23046
|
this.checkPlayout = () => {
|
23040
23047
|
const interstitial = this.interstitial;
|
23041
23048
|
const playoutLimit = interstitial.playoutLimit;
|
@@ -23089,7 +23096,7 @@ class HlsAssetPlayer {
|
|
23089
23096
|
get bufferedEnd() {
|
23090
23097
|
const media = this.media || this.mediaAttached;
|
23091
23098
|
if (!media) {
|
23092
|
-
return
|
23099
|
+
return this.currentTime;
|
23093
23100
|
}
|
23094
23101
|
const bufferInfo = BufferHelper.bufferInfo(media, media.currentTime, 0.001);
|
23095
23102
|
return this.getAssetTime(bufferInfo.end);
|
@@ -23097,7 +23104,7 @@ class HlsAssetPlayer {
|
|
23097
23104
|
get currentTime() {
|
23098
23105
|
const media = this.media || this.mediaAttached;
|
23099
23106
|
if (!media) {
|
23100
|
-
return 0;
|
23107
|
+
return this._currentTime || 0;
|
23101
23108
|
}
|
23102
23109
|
return this.getAssetTime(media.currentTime);
|
23103
23110
|
}
|
@@ -23142,6 +23149,7 @@ class HlsAssetPlayer {
|
|
23142
23149
|
removeMediaListeners() {
|
23143
23150
|
const media = this.mediaAttached;
|
23144
23151
|
if (media) {
|
23152
|
+
this._currentTime = media.currentTime;
|
23145
23153
|
media.removeEventListener('timeupdate', this.checkPlayout);
|
23146
23154
|
}
|
23147
23155
|
}
|
@@ -23158,6 +23166,7 @@ class HlsAssetPlayer {
|
|
23158
23166
|
}
|
23159
23167
|
detachMedia() {
|
23160
23168
|
this.removeMediaListeners();
|
23169
|
+
this.mediaAttached = null;
|
23161
23170
|
this.hls.detachMedia();
|
23162
23171
|
}
|
23163
23172
|
resumeBuffering() {
|
@@ -23179,7 +23188,8 @@ class HlsAssetPlayer {
|
|
23179
23188
|
this.hls.off(event, listener);
|
23180
23189
|
}
|
23181
23190
|
toString() {
|
23182
|
-
|
23191
|
+
var _this$hls4, _this$interstitial;
|
23192
|
+
return `HlsAssetPlayer: ${eventAssetToString(this.assetItem)} ${(_this$hls4 = this.hls) == null ? void 0 : _this$hls4.sessionId} ${(_this$interstitial = this.interstitial) != null && _this$interstitial.appendInPlace ? 'append-in-place' : ''}`;
|
23183
23193
|
}
|
23184
23194
|
}
|
23185
23195
|
|
@@ -23336,7 +23346,7 @@ class InterstitialsSchedule extends Logger {
|
|
23336
23346
|
}
|
23337
23347
|
return null;
|
23338
23348
|
}
|
23339
|
-
parseInterstitialDateRanges(mediaSelection) {
|
23349
|
+
parseInterstitialDateRanges(mediaSelection, enableAppendInPlace) {
|
23340
23350
|
const details = mediaSelection.main.details;
|
23341
23351
|
const {
|
23342
23352
|
dateRanges
|
@@ -23344,7 +23354,7 @@ class InterstitialsSchedule extends Logger {
|
|
23344
23354
|
const previousInterstitialEvents = this.events;
|
23345
23355
|
const interstitialEvents = this.parseDateRanges(dateRanges, {
|
23346
23356
|
url: details.url
|
23347
|
-
});
|
23357
|
+
}, enableAppendInPlace);
|
23348
23358
|
const ids = Object.keys(dateRanges);
|
23349
23359
|
const removedInterstitials = previousInterstitialEvents ? previousInterstitialEvents.filter(event => !ids.includes(event.identifier)) : [];
|
23350
23360
|
if (interstitialEvents.length) {
|
@@ -23400,7 +23410,7 @@ class InterstitialsSchedule extends Logger {
|
|
23400
23410
|
}
|
23401
23411
|
}
|
23402
23412
|
}
|
23403
|
-
parseDateRanges(dateRanges, baseData) {
|
23413
|
+
parseDateRanges(dateRanges, baseData, enableAppendInPlace) {
|
23404
23414
|
const interstitialEvents = [];
|
23405
23415
|
const ids = Object.keys(dateRanges);
|
23406
23416
|
for (let i = 0; i < ids.length; i++) {
|
@@ -23415,6 +23425,9 @@ class InterstitialsSchedule extends Logger {
|
|
23415
23425
|
} else {
|
23416
23426
|
interstitial = new InterstitialEvent(dateRange, baseData);
|
23417
23427
|
this.eventMap[id] = interstitial;
|
23428
|
+
if (enableAppendInPlace === false) {
|
23429
|
+
interstitial.appendInPlace = enableAppendInPlace;
|
23430
|
+
}
|
23418
23431
|
}
|
23419
23432
|
interstitialEvents.push(interstitial);
|
23420
23433
|
}
|
@@ -23618,13 +23631,11 @@ class InterstitialsSchedule extends Logger {
|
|
23618
23631
|
interstitial.appendInPlace = false;
|
23619
23632
|
}
|
23620
23633
|
}
|
23621
|
-
if (!interstitial.appendInPlace) {
|
23634
|
+
if (!interstitial.appendInPlace && i + 1 < interstitialEvents.length) {
|
23622
23635
|
// abutting Interstitials must use the same MediaSource strategy, this applies to all whether or not they are back to back:
|
23623
|
-
|
23624
|
-
|
23625
|
-
|
23626
|
-
interstitialEvents[j].appendInPlace = false;
|
23627
|
-
}
|
23636
|
+
const timeBetween = interstitialEvents[i + 1].startTime - interstitialEvents[i].resumeTime;
|
23637
|
+
if (timeBetween < ABUTTING_THRESHOLD_SECONDS) {
|
23638
|
+
interstitialEvents[i + 1].appendInPlace = false;
|
23628
23639
|
}
|
23629
23640
|
}
|
23630
23641
|
// Update cumulativeDuration for next abutting interstitial with the same start date
|
@@ -23951,9 +23962,6 @@ class InterstitialsController extends Logger {
|
|
23951
23962
|
const removedIds = removedInterstitials.map(interstitial => interstitial.identifier);
|
23952
23963
|
const interstitialsUpdated = !!(interstitialEvents.length || removedIds.length);
|
23953
23964
|
if (interstitialsUpdated) {
|
23954
|
-
if (this.hls.config.interstitialAppendInPlace === false) {
|
23955
|
-
interstitialEvents.forEach(event => event.appendInPlace = false);
|
23956
|
-
}
|
23957
23965
|
this.log(`INTERSTITIALS_UPDATED (${interstitialEvents.length}): ${interstitialEvents}
|
23958
23966
|
Schedule: ${scheduleItems.map(seg => segmentToString(seg))}`);
|
23959
23967
|
}
|
@@ -24083,10 +24091,12 @@ Schedule: ${scheduleItems.map(seg => segmentToString(seg))}`);
|
|
24083
24091
|
this.pauseBuffering();
|
24084
24092
|
}
|
24085
24093
|
resumeBuffering() {
|
24086
|
-
|
24094
|
+
var _this$getBufferingPla;
|
24095
|
+
(_this$getBufferingPla = this.getBufferingPlayer()) == null ? void 0 : _this$getBufferingPla.resumeBuffering();
|
24087
24096
|
}
|
24088
24097
|
pauseBuffering() {
|
24089
|
-
|
24098
|
+
var _this$getBufferingPla2;
|
24099
|
+
(_this$getBufferingPla2 = this.getBufferingPlayer()) == null ? void 0 : _this$getBufferingPla2.pauseBuffering();
|
24090
24100
|
}
|
24091
24101
|
destroy() {
|
24092
24102
|
this.unregisterListeners();
|
@@ -24524,33 +24534,48 @@ Schedule: ${scheduleItems.map(seg => segmentToString(seg))}`);
|
|
24524
24534
|
}
|
24525
24535
|
transferMediaTo(player, media) {
|
24526
24536
|
var _this$detachedData2, _attachMediaSourceDat;
|
24537
|
+
if (player.media === media) {
|
24538
|
+
return;
|
24539
|
+
}
|
24527
24540
|
let attachMediaSourceData = null;
|
24528
24541
|
const primaryPlayer = this.hls;
|
24529
24542
|
const isAssetPlayer = player !== primaryPlayer;
|
24530
24543
|
const appendInPlace = isAssetPlayer && player.interstitial.appendInPlace;
|
24531
24544
|
const detachedMediaSource = (_this$detachedData2 = this.detachedData) == null ? void 0 : _this$detachedData2.mediaSource;
|
24532
24545
|
let logFromSource;
|
24533
|
-
if (primaryPlayer.media
|
24534
|
-
|
24535
|
-
|
24546
|
+
if (primaryPlayer.media) {
|
24547
|
+
if (appendInPlace) {
|
24548
|
+
attachMediaSourceData = primaryPlayer.transferMedia();
|
24549
|
+
this.detachedData = attachMediaSourceData;
|
24550
|
+
}
|
24536
24551
|
logFromSource = `Primary`;
|
24537
24552
|
} else if (detachedMediaSource) {
|
24538
24553
|
const bufferingPlayer = this.getBufferingPlayer();
|
24539
24554
|
if (bufferingPlayer) {
|
24540
24555
|
attachMediaSourceData = bufferingPlayer.transferMedia();
|
24556
|
+
logFromSource = `${bufferingPlayer}`;
|
24557
|
+
} else {
|
24558
|
+
logFromSource = `detached MediaSource`;
|
24541
24559
|
}
|
24542
|
-
logFromSource = `${bufferingPlayer}`;
|
24543
24560
|
} else {
|
24544
|
-
logFromSource =
|
24561
|
+
logFromSource = `detached media`;
|
24545
24562
|
}
|
24546
|
-
this.log(`transferring to ${isAssetPlayer ? player : 'Primary'}
|
24547
|
-
MediaSource ${stringify(attachMediaSourceData)} from ${logFromSource}`);
|
24548
24563
|
if (!attachMediaSourceData) {
|
24549
24564
|
if (detachedMediaSource) {
|
24550
24565
|
attachMediaSourceData = this.detachedData;
|
24551
24566
|
this.log(`using detachedData: MediaSource ${stringify(attachMediaSourceData)}`);
|
24552
|
-
} else if (!this.detachedData ||
|
24553
|
-
//
|
24567
|
+
} else if (!this.detachedData || primaryPlayer.media === media) {
|
24568
|
+
// Keep interstitial media transition consistent
|
24569
|
+
const playerQueue = this.playerQueue;
|
24570
|
+
if (playerQueue.length > 1) {
|
24571
|
+
playerQueue.forEach(queuedPlayer => {
|
24572
|
+
if (isAssetPlayer && queuedPlayer.interstitial.appendInPlace !== appendInPlace) {
|
24573
|
+
const interstitial = queuedPlayer.interstitial;
|
24574
|
+
this.clearInterstitial(queuedPlayer.interstitial, null);
|
24575
|
+
interstitial.appendInPlace = false;
|
24576
|
+
}
|
24577
|
+
});
|
24578
|
+
}
|
24554
24579
|
this.hls.detachMedia();
|
24555
24580
|
this.detachedData = {
|
24556
24581
|
media
|
@@ -24559,7 +24584,7 @@ MediaSource ${stringify(attachMediaSourceData)} from ${logFromSource}`);
|
|
24559
24584
|
}
|
24560
24585
|
const transferring = attachMediaSourceData && 'mediaSource' in attachMediaSourceData && ((_attachMediaSourceDat = attachMediaSourceData.mediaSource) == null ? void 0 : _attachMediaSourceDat.readyState) !== 'closed';
|
24561
24586
|
const dataToAttach = transferring && attachMediaSourceData ? attachMediaSourceData : media;
|
24562
|
-
this.log(`${transferring ? 'transfering MediaSource' : 'attaching media'} to ${isAssetPlayer ? player : 'Primary'}`);
|
24587
|
+
this.log(`${transferring ? 'transfering MediaSource' : 'attaching media'} to ${isAssetPlayer ? player : 'Primary'} from ${logFromSource}`);
|
24563
24588
|
if (dataToAttach === attachMediaSourceData) {
|
24564
24589
|
const isAssetAtEndOfSchedule = isAssetPlayer && player.assetId === this.schedule.assetIdAtEnd;
|
24565
24590
|
// Prevent asset players from marking EoS on transferred MediaSource
|
@@ -24656,6 +24681,7 @@ MediaSource ${stringify(attachMediaSourceData)} from ${logFromSource}`);
|
|
24656
24681
|
const assetId = playingAsset == null ? void 0 : playingAsset.identifier;
|
24657
24682
|
const player = assetId ? this.getAssetPlayer(assetId) : null;
|
24658
24683
|
if (player && assetId && (!this.eventItemsMatch(currentItem, scheduledItem) || assetListIndex !== undefined && assetId !== ((_interstitial$assetLi = interstitial.assetList) == null ? void 0 : _interstitial$assetLi[assetListIndex].identifier))) {
|
24684
|
+
var _this$detachedData3;
|
24659
24685
|
const _assetListIndex = interstitial.findAssetIndex(playingAsset);
|
24660
24686
|
this.log(`INTERSTITIAL_ASSET_ENDED ${_assetListIndex + 1}/${interstitial.assetList.length} ${eventAssetToString(playingAsset)}`);
|
24661
24687
|
this.endedAsset = playingAsset;
|
@@ -24669,7 +24695,7 @@ MediaSource ${stringify(attachMediaSourceData)} from ${logFromSource}`);
|
|
24669
24695
|
player
|
24670
24696
|
});
|
24671
24697
|
this.retreiveMediaSource(assetId, scheduledItem);
|
24672
|
-
if (player.media && !this.detachedData) {
|
24698
|
+
if (player.media && !((_this$detachedData3 = this.detachedData) != null && _this$detachedData3.mediaSource)) {
|
24673
24699
|
player.detachMedia();
|
24674
24700
|
}
|
24675
24701
|
}
|
@@ -24810,13 +24836,13 @@ MediaSource ${stringify(attachMediaSourceData)} from ${logFromSource}`);
|
|
24810
24836
|
return !!((_this$primaryDetails = this.primaryDetails) != null && _this$primaryDetails.live);
|
24811
24837
|
}
|
24812
24838
|
resumePrimary(scheduledItem, index, fromItem) {
|
24813
|
-
var _this$
|
24839
|
+
var _this$detachedData4;
|
24814
24840
|
this.playingItem = scheduledItem;
|
24815
24841
|
this.playingAsset = this.endedAsset = null;
|
24816
24842
|
this.waitingItem = this.endedItem = null;
|
24817
24843
|
this.bufferedToItem(scheduledItem);
|
24818
24844
|
this.log(`resuming ${segmentToString(scheduledItem)}`);
|
24819
|
-
if (!((_this$
|
24845
|
+
if (!((_this$detachedData4 = this.detachedData) != null && _this$detachedData4.mediaSource)) {
|
24820
24846
|
let timelinePos = this.timelinePos;
|
24821
24847
|
if (timelinePos < scheduledItem.start || timelinePos >= scheduledItem.end) {
|
24822
24848
|
timelinePos = this.getPrimaryResumption(scheduledItem, index);
|
@@ -24917,7 +24943,7 @@ MediaSource ${stringify(attachMediaSourceData)} from ${logFromSource}`);
|
|
24917
24943
|
main
|
24918
24944
|
});
|
24919
24945
|
this.mediaSelection = currentSelection;
|
24920
|
-
this.schedule.parseInterstitialDateRanges(currentSelection);
|
24946
|
+
this.schedule.parseInterstitialDateRanges(currentSelection, this.hls.config.interstitialAppendInPlace);
|
24921
24947
|
if (!this.effectivePlayingItem && this.schedule.items) {
|
24922
24948
|
this.checkStart();
|
24923
24949
|
}
|
@@ -24999,6 +25025,8 @@ MediaSource ${stringify(attachMediaSourceData)} from ${logFromSource}`);
|
|
24999
25025
|
if (!this.playingLastItem && playingItem) {
|
25000
25026
|
const playingIndex = this.findItemIndex(playingItem);
|
25001
25027
|
this.setSchedulePosition(playingIndex + 1);
|
25028
|
+
} else {
|
25029
|
+
this.shouldPlay = false;
|
25002
25030
|
}
|
25003
25031
|
}
|
25004
25032
|
updateItem(previousItem, time) {
|
@@ -25167,16 +25195,16 @@ MediaSource ${stringify(attachMediaSourceData)} from ${logFromSource}`);
|
|
25167
25195
|
}
|
25168
25196
|
}
|
25169
25197
|
preloadAssets(interstitial, assetListIndex) {
|
25198
|
+
const uri = interstitial.assetUrl;
|
25170
25199
|
const assetListLength = interstitial.assetList.length;
|
25171
25200
|
const neverLoaded = assetListLength === 0 && !interstitial.assetListLoader;
|
25172
25201
|
const playOnce = interstitial.cue.once;
|
25173
25202
|
if (neverLoaded) {
|
25174
|
-
this.log(`Load interstitial asset ${assetListIndex + 1}/${assetListLength} ${interstitial}`);
|
25203
|
+
this.log(`Load interstitial asset ${assetListIndex + 1}/${uri ? 1 : assetListLength} ${interstitial}`);
|
25175
25204
|
const timelineStart = interstitial.timelineStart;
|
25176
25205
|
if (interstitial.appendInPlace) {
|
25177
25206
|
this.flushFrontBuffer(timelineStart + 0.25);
|
25178
25207
|
}
|
25179
|
-
const uri = interstitial.assetUrl;
|
25180
25208
|
if (uri) {
|
25181
25209
|
return this.createAsset(interstitial, 0, 0, timelineStart, interstitial.duration, uri);
|
25182
25210
|
}
|
@@ -25474,12 +25502,10 @@ MediaSource ${stringify(attachMediaSourceData)} from ${logFromSource}`);
|
|
25474
25502
|
}
|
25475
25503
|
|
25476
25504
|
// detach media and attach to interstitial player if it does not have another element attached
|
25477
|
-
|
25478
|
-
this.bufferAssetPlayer(player, media);
|
25479
|
-
}
|
25505
|
+
this.bufferAssetPlayer(player, media);
|
25480
25506
|
}
|
25481
25507
|
bufferAssetPlayer(player, media) {
|
25482
|
-
var _this$schedule$items4, _this$
|
25508
|
+
var _this$schedule$items4, _this$detachedData5;
|
25483
25509
|
const {
|
25484
25510
|
interstitial,
|
25485
25511
|
assetItem,
|
@@ -25496,8 +25522,13 @@ MediaSource ${stringify(attachMediaSourceData)} from ${logFromSource}`);
|
|
25496
25522
|
if (bufferingPlayer === player) {
|
25497
25523
|
return;
|
25498
25524
|
}
|
25499
|
-
const
|
25500
|
-
if (
|
25525
|
+
const appendInPlaceNext = interstitial.appendInPlace;
|
25526
|
+
if (appendInPlaceNext && (bufferingPlayer == null ? void 0 : bufferingPlayer.interstitial.appendInPlace) === false) {
|
25527
|
+
// Media is detached and not available to append in place
|
25528
|
+
return;
|
25529
|
+
}
|
25530
|
+
const activeTracks = (bufferingPlayer == null ? void 0 : bufferingPlayer.tracks) || ((_this$detachedData5 = this.detachedData) == null ? void 0 : _this$detachedData5.tracks) || this.requiredTracks;
|
25531
|
+
if (appendInPlaceNext && assetItem !== this.playingAsset) {
|
25501
25532
|
// Do not buffer another item if tracks are unknown or incompatible
|
25502
25533
|
if (!player.tracks) {
|
25503
25534
|
return;
|
@@ -25569,7 +25600,6 @@ MediaSource ${stringify(attachMediaSourceData)} from ${logFromSource}`);
|
|
25569
25600
|
if (playingItem) {
|
25570
25601
|
this.log(`Fallback to primary from event "${interstitial.identifier}" start: ${flushStart} pos: ${this.timelinePos} playing: ${playingItem ? segmentToString(playingItem) : '<none>'} error: ${interstitial.error}`);
|
25571
25602
|
if (interstitial.appendInPlace) {
|
25572
|
-
interstitial.appendInPlace = false;
|
25573
25603
|
this.attachPrimary(flushStart, null);
|
25574
25604
|
this.flushFrontBuffer(flushStart);
|
25575
25605
|
}
|
@@ -25581,6 +25611,8 @@ MediaSource ${stringify(attachMediaSourceData)} from ${logFromSource}`);
|
|
25581
25611
|
if (!this.itemsMatch(playingItem, newPlayingItem)) {
|
25582
25612
|
const scheduleIndex = this.schedule.findItemIndexAtTime(timelinePos);
|
25583
25613
|
this.setSchedulePosition(scheduleIndex);
|
25614
|
+
} else {
|
25615
|
+
this.clearInterstitial(interstitial, null);
|
25584
25616
|
}
|
25585
25617
|
} else {
|
25586
25618
|
this.checkStart();
|
@@ -25985,21 +26017,22 @@ class SubtitleStreamController extends BaseStreamController {
|
|
25985
26017
|
} else {
|
25986
26018
|
foundFrag = fragments[fragLen - 1];
|
25987
26019
|
}
|
26020
|
+
foundFrag = this.filterReplacedPrimary(foundFrag, track.details);
|
25988
26021
|
if (!foundFrag) {
|
25989
26022
|
return;
|
25990
26023
|
}
|
25991
|
-
|
25992
|
-
|
25993
|
-
|
25994
|
-
|
25995
|
-
|
25996
|
-
if (prevFrag && prevFrag.cc === foundFrag.cc && this.fragmentTracker.getState(prevFrag) === FragmentState.NOT_LOADED) {
|
25997
|
-
foundFrag = prevFrag;
|
25998
|
-
}
|
26024
|
+
// Load earlier fragment in same discontinuity to make up for misaligned playlists and cues that extend beyond end of segment
|
26025
|
+
const curSNIdx = foundFrag.sn - trackDetails.startSN;
|
26026
|
+
const prevFrag = fragments[curSNIdx - 1];
|
26027
|
+
if (prevFrag && prevFrag.cc === foundFrag.cc && this.fragmentTracker.getState(prevFrag) === FragmentState.NOT_LOADED) {
|
26028
|
+
foundFrag = prevFrag;
|
25999
26029
|
}
|
26000
26030
|
if (this.fragmentTracker.getState(foundFrag) === FragmentState.NOT_LOADED) {
|
26001
26031
|
// only load if fragment is not loaded
|
26002
|
-
this.
|
26032
|
+
const fragToLoad = this.mapToInitFragWhenRequired(foundFrag);
|
26033
|
+
if (fragToLoad) {
|
26034
|
+
this.loadFragment(fragToLoad, track, targetBufferTime);
|
26035
|
+
}
|
26003
26036
|
}
|
26004
26037
|
}
|
26005
26038
|
}
|