stormcloud-video-player 0.6.1 → 0.6.2
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/stormcloud-vp.min.js +1 -1
- package/lib/index.cjs +88 -17
- package/lib/index.cjs.map +1 -1
- package/lib/index.d.cts +2 -0
- package/lib/index.d.ts +2 -0
- package/lib/index.js +88 -17
- package/lib/index.js.map +1 -1
- package/lib/player/StormcloudVideoPlayer.cjs +88 -17
- package/lib/player/StormcloudVideoPlayer.cjs.map +1 -1
- package/lib/player/StormcloudVideoPlayer.d.cts +1 -1
- package/lib/players/HlsPlayer.cjs +88 -17
- package/lib/players/HlsPlayer.cjs.map +1 -1
- package/lib/players/HlsPlayer.d.cts +1 -1
- package/lib/players/index.cjs +88 -17
- package/lib/players/index.cjs.map +1 -1
- package/lib/sdk/vastAdLayer.cjs +28 -5
- package/lib/sdk/vastAdLayer.cjs.map +1 -1
- package/lib/sdk/vastAdLayer.d.cts +2 -1
- package/lib/sdk/vastManager.d.cts +1 -1
- package/lib/{types-CwDRIvJm.d.cts → types-BYwfSJb5.d.cts} +1 -0
- package/lib/ui/StormcloudVideoPlayer.cjs +88 -17
- package/lib/ui/StormcloudVideoPlayer.cjs.map +1 -1
- package/lib/ui/StormcloudVideoPlayer.d.cts +1 -1
- package/lib/utils/tracking.d.cts +1 -1
- package/package.json +1 -1
package/lib/index.d.cts
CHANGED
|
@@ -35,6 +35,7 @@ interface StormcloudVideoPlayerConfig {
|
|
|
35
35
|
disableAds?: boolean;
|
|
36
36
|
disableFiller?: boolean;
|
|
37
37
|
adTransitionGapMs?: number;
|
|
38
|
+
singlePipelineMode?: boolean;
|
|
38
39
|
}
|
|
39
40
|
interface ClientInfo {
|
|
40
41
|
brand: string;
|
|
@@ -4008,6 +4009,7 @@ interface VastAdLayerOptions {
|
|
|
4008
4009
|
mainHlsInstance?: Hls;
|
|
4009
4010
|
smartTVMode?: boolean;
|
|
4010
4011
|
singleElementMode?: boolean;
|
|
4012
|
+
forceMP4Ads?: boolean;
|
|
4011
4013
|
debug?: boolean;
|
|
4012
4014
|
}
|
|
4013
4015
|
interface VastAdLayerOptionsUpdate {
|
package/lib/index.d.ts
CHANGED
|
@@ -35,6 +35,7 @@ interface StormcloudVideoPlayerConfig {
|
|
|
35
35
|
disableAds?: boolean;
|
|
36
36
|
disableFiller?: boolean;
|
|
37
37
|
adTransitionGapMs?: number;
|
|
38
|
+
singlePipelineMode?: boolean;
|
|
38
39
|
}
|
|
39
40
|
interface ClientInfo {
|
|
40
41
|
brand: string;
|
|
@@ -4008,6 +4009,7 @@ interface VastAdLayerOptions {
|
|
|
4008
4009
|
mainHlsInstance?: Hls;
|
|
4009
4010
|
smartTVMode?: boolean;
|
|
4010
4011
|
singleElementMode?: boolean;
|
|
4012
|
+
forceMP4Ads?: boolean;
|
|
4011
4013
|
debug?: boolean;
|
|
4012
4014
|
}
|
|
4013
4015
|
interface VastAdLayerOptionsUpdate {
|
package/lib/index.js
CHANGED
|
@@ -944,7 +944,7 @@ function resolveBidToVastAd(winner, logPrefix) {
|
|
|
944
944
|
return Promise.resolve(null);
|
|
945
945
|
}
|
|
946
946
|
function createVastAdLayer(contentVideo, options) {
|
|
947
|
-
var _ref, _ref1, _ref2, _ref3;
|
|
947
|
+
var _ref, _ref1, _ref2, _ref3, _ref4;
|
|
948
948
|
var adPlaying = false;
|
|
949
949
|
var originalMutedState = false;
|
|
950
950
|
var originalVolume = Math.max(0, Math.min(1, contentVideo.volume || 1));
|
|
@@ -953,7 +953,8 @@ function createVastAdLayer(contentVideo, options) {
|
|
|
953
953
|
var continueLiveStreamDuringAds = (_ref = options === null || options === void 0 ? void 0 : options.continueLiveStreamDuringAds) !== null && _ref !== void 0 ? _ref : false;
|
|
954
954
|
var smartTVMode = (_ref1 = options === null || options === void 0 ? void 0 : options.smartTVMode) !== null && _ref1 !== void 0 ? _ref1 : false;
|
|
955
955
|
var singleElementMode = (_ref2 = options === null || options === void 0 ? void 0 : options.singleElementMode) !== null && _ref2 !== void 0 ? _ref2 : false;
|
|
956
|
-
var
|
|
956
|
+
var forceMP4Ads = (_ref3 = options === null || options === void 0 ? void 0 : options.forceMP4Ads) !== null && _ref3 !== void 0 ? _ref3 : smartTVMode || singleElementMode;
|
|
957
|
+
var debug = (_ref4 = options === null || options === void 0 ? void 0 : options.debug) !== null && _ref4 !== void 0 ? _ref4 : false;
|
|
957
958
|
var adVideoElement;
|
|
958
959
|
var adHls;
|
|
959
960
|
var adContainerEl;
|
|
@@ -1024,14 +1025,26 @@ function createVastAdLayer(contentVideo, options) {
|
|
|
1024
1025
|
var _ref;
|
|
1025
1026
|
var _scoredFiles_;
|
|
1026
1027
|
if (mediaFiles.length === 0) throw new Error("No media files available");
|
|
1027
|
-
var
|
|
1028
|
-
if (
|
|
1028
|
+
var candidates = mediaFiles;
|
|
1029
|
+
if (forceMP4Ads) {
|
|
1030
|
+
var mp4Only = candidates.filter(function(f) {
|
|
1031
|
+
return !isHlsMediaFile(f);
|
|
1032
|
+
});
|
|
1033
|
+
if (mp4Only.length > 0) {
|
|
1034
|
+
candidates = mp4Only;
|
|
1035
|
+
if (debug) console.log("".concat(LOG, " forceMP4Ads: filtered to ").concat(mp4Only.length, " MP4-only file(s)"));
|
|
1036
|
+
} else if (debug) {
|
|
1037
|
+
console.warn("".concat(LOG, " forceMP4Ads: no MP4 files available, falling back to all media files"));
|
|
1038
|
+
}
|
|
1039
|
+
}
|
|
1040
|
+
var firstFile = candidates[0];
|
|
1041
|
+
if (candidates.length === 1) return firstFile;
|
|
1029
1042
|
var mainQuality = getMainStreamQuality();
|
|
1030
1043
|
if (!mainQuality) {
|
|
1031
1044
|
if (debug) console.log("".concat(LOG, " No main stream quality info, using first media file"));
|
|
1032
1045
|
return firstFile;
|
|
1033
1046
|
}
|
|
1034
|
-
var scoredFiles =
|
|
1047
|
+
var scoredFiles = candidates.map(function(file) {
|
|
1035
1048
|
var widthDiff = Math.abs(file.width - mainQuality.width);
|
|
1036
1049
|
var heightDiff = Math.abs(file.height - mainQuality.height);
|
|
1037
1050
|
var resolutionDiff = widthDiff + heightDiff;
|
|
@@ -1248,6 +1261,16 @@ function createVastAdLayer(contentVideo, options) {
|
|
|
1248
1261
|
}
|
|
1249
1262
|
function startPlayback(mediaFile) {
|
|
1250
1263
|
if (!adVideoElement) return;
|
|
1264
|
+
if (singleElementMode && isHlsMediaFile(mediaFile)) {
|
|
1265
|
+
var mp4Fallback = currentAd === null || currentAd === void 0 ? void 0 : currentAd.mediaFiles.find(function(f) {
|
|
1266
|
+
return !isHlsMediaFile(f);
|
|
1267
|
+
});
|
|
1268
|
+
if (mp4Fallback) {
|
|
1269
|
+
if (debug) console.log("".concat(LOG, " singleElementMode: HLS ad blocked, using MP4 fallback"));
|
|
1270
|
+
startNativePlayback(mp4Fallback);
|
|
1271
|
+
return;
|
|
1272
|
+
}
|
|
1273
|
+
}
|
|
1251
1274
|
if (isHlsMediaFile(mediaFile)) {
|
|
1252
1275
|
startHlsPlayback(mediaFile);
|
|
1253
1276
|
} else {
|
|
@@ -2946,10 +2969,12 @@ var StormcloudVideoPlayer = /*#__PURE__*/ function() {
|
|
|
2946
2969
|
debug: !!config.debugAdTiming
|
|
2947
2970
|
} : {});
|
|
2948
2971
|
var browserForAdLayer = detectBrowser();
|
|
2972
|
+
var isSinglePipeline = browserForAdLayer.isSmartTV || !!this.config.singlePipelineMode;
|
|
2949
2973
|
this.adLayer = createVastAdLayer(this.video, {
|
|
2950
2974
|
continueLiveStreamDuringAds: false,
|
|
2951
|
-
smartTVMode:
|
|
2952
|
-
singleElementMode:
|
|
2975
|
+
smartTVMode: isSinglePipeline,
|
|
2976
|
+
singleElementMode: isSinglePipeline,
|
|
2977
|
+
forceMP4Ads: isSinglePipeline,
|
|
2953
2978
|
debug: !!config.debugAdTiming
|
|
2954
2979
|
});
|
|
2955
2980
|
}
|
|
@@ -3595,6 +3620,16 @@ var StormcloudVideoPlayer = /*#__PURE__*/ function() {
|
|
|
3595
3620
|
if (_this.fillerVideo) {
|
|
3596
3621
|
_this.fillerVideo.style.display = "none";
|
|
3597
3622
|
}
|
|
3623
|
+
if (!_this.adLayer.isAdPlaying()) {
|
|
3624
|
+
if (_this.config.debugAdTiming) {
|
|
3625
|
+
console.log("[StormcloudVideoPlayer] Filler video failed \u2014 restoring main video");
|
|
3626
|
+
}
|
|
3627
|
+
_this.adLayer.hidePlaceholder();
|
|
3628
|
+
if (_this.video.paused && _this.video.readyState >= 2) {
|
|
3629
|
+
var _this_video_play;
|
|
3630
|
+
(_this_video_play = _this.video.play()) === null || _this_video_play === void 0 ? void 0 : _this_video_play.catch(function() {});
|
|
3631
|
+
}
|
|
3632
|
+
}
|
|
3598
3633
|
});
|
|
3599
3634
|
if (this.config.debugAdTiming) {
|
|
3600
3635
|
console.log("[StormcloudVideoPlayer] Showing filler video layer");
|
|
@@ -4311,6 +4346,9 @@ var StormcloudVideoPlayer = /*#__PURE__*/ function() {
|
|
|
4311
4346
|
if (!this.isLiveStream) {
|
|
4312
4347
|
return false;
|
|
4313
4348
|
}
|
|
4349
|
+
if (this.config.singlePipelineMode) {
|
|
4350
|
+
return false;
|
|
4351
|
+
}
|
|
4314
4352
|
var browser = detectBrowser();
|
|
4315
4353
|
if (browser.isSmartTV) {
|
|
4316
4354
|
return false;
|
|
@@ -5461,32 +5499,56 @@ var StormcloudVideoPlayer = /*#__PURE__*/ function() {
|
|
|
5461
5499
|
this.video.volume = restoredVolume;
|
|
5462
5500
|
}
|
|
5463
5501
|
var browser = detectBrowser();
|
|
5464
|
-
var isSmartTV = browser.tizenVersion !== void 0 || browser.webOSVersion !== void 0;
|
|
5502
|
+
var isSmartTV = browser.tizenVersion !== void 0 || browser.webOSVersion !== void 0 || !!this.config.singlePipelineMode;
|
|
5465
5503
|
if (isSmartTV && this.hls) {
|
|
5466
5504
|
var hlsRef = this.hls;
|
|
5467
5505
|
var savedMuted = restoredMuted;
|
|
5468
5506
|
var savedVolume = restoredVolume;
|
|
5507
|
+
var videoRef = this.video;
|
|
5508
|
+
var debugEnabled = this.config.debugAdTiming;
|
|
5509
|
+
var tryPlay = function tryPlay1(attempt) {
|
|
5510
|
+
var _videoRef_play;
|
|
5511
|
+
if (_this.inAdBreak || _this.adLayer.isAdPlaying()) return;
|
|
5512
|
+
(_videoRef_play = videoRef.play()) === null || _videoRef_play === void 0 ? void 0 : _videoRef_play.catch(function() {
|
|
5513
|
+
if (attempt < 3) {
|
|
5514
|
+
if (debugEnabled) {
|
|
5515
|
+
console.log("[StormcloudVideoPlayer] Smart TV: play() retry ".concat(attempt + 1, "/3 in ").concat(500 * (attempt + 1), "ms"));
|
|
5516
|
+
}
|
|
5517
|
+
setTimeout(function() {
|
|
5518
|
+
return tryPlay(attempt + 1);
|
|
5519
|
+
}, 500 * (attempt + 1));
|
|
5520
|
+
}
|
|
5521
|
+
});
|
|
5522
|
+
};
|
|
5469
5523
|
var onManifestParsedRestore = function onManifestParsedRestore1() {
|
|
5470
5524
|
hlsRef.off(Hls2.Events.MANIFEST_PARSED, onManifestParsedRestore);
|
|
5471
5525
|
if (!_this.inAdBreak && !_this.adLayer.isAdPlaying()) {
|
|
5472
|
-
|
|
5473
|
-
if (
|
|
5474
|
-
if (
|
|
5475
|
-
if (_this.config.debugAdTiming) {
|
|
5526
|
+
if (videoRef.muted !== savedMuted) videoRef.muted = savedMuted;
|
|
5527
|
+
if (Math.abs(videoRef.volume - savedVolume) > 0.01) videoRef.volume = savedVolume;
|
|
5528
|
+
if (debugEnabled) {
|
|
5476
5529
|
console.log("[StormcloudVideoPlayer] Smart TV: audio state restored on MANIFEST_PARSED after re-attach");
|
|
5477
5530
|
}
|
|
5478
5531
|
hlsRef.startLoad(-1);
|
|
5479
|
-
(
|
|
5480
|
-
if (
|
|
5532
|
+
tryPlay(0);
|
|
5533
|
+
if (debugEnabled) {
|
|
5481
5534
|
console.log("[StormcloudVideoPlayer] Smart TV: seeking to live edge and resuming playback after re-attach");
|
|
5482
5535
|
}
|
|
5483
5536
|
}
|
|
5484
5537
|
};
|
|
5485
5538
|
hlsRef.on(Hls2.Events.MANIFEST_PARSED, onManifestParsedRestore);
|
|
5486
|
-
|
|
5487
|
-
if (
|
|
5488
|
-
console.log("[StormcloudVideoPlayer] Smart TV:
|
|
5539
|
+
var pipelineDelayMs = 300;
|
|
5540
|
+
if (debugEnabled) {
|
|
5541
|
+
console.log("[StormcloudVideoPlayer] Smart TV: waiting ".concat(pipelineDelayMs, "ms for hardware pipeline release before re-attach"));
|
|
5489
5542
|
}
|
|
5543
|
+
setTimeout(function() {
|
|
5544
|
+
if (_this.inAdBreak || _this.adLayer.isAdPlaying()) return;
|
|
5545
|
+
if (_this.hls) {
|
|
5546
|
+
_this.hls.attachMedia(_this.video);
|
|
5547
|
+
if (debugEnabled) {
|
|
5548
|
+
console.log("[StormcloudVideoPlayer] Smart TV: re-attached HLS to video element after ad break to restore media pipeline");
|
|
5549
|
+
}
|
|
5550
|
+
}
|
|
5551
|
+
}, pipelineDelayMs);
|
|
5490
5552
|
} else {
|
|
5491
5553
|
if (this.shouldContinueLiveStreamDuringAds()) {
|
|
5492
5554
|
var _this_video_play;
|
|
@@ -5560,6 +5622,15 @@ var StormcloudVideoPlayer = /*#__PURE__*/ function() {
|
|
|
5560
5622
|
}
|
|
5561
5623
|
this.showPlaceholderLayer();
|
|
5562
5624
|
this.adLayer.showPlaceholder();
|
|
5625
|
+
} else if (this.inAdBreak) {
|
|
5626
|
+
if (this.config.debugAdTiming) {
|
|
5627
|
+
console.log("[CONTINUOUS-FETCH] Ad failure with no filler \u2014 restoring main video temporarily");
|
|
5628
|
+
}
|
|
5629
|
+
this.adLayer.hidePlaceholder();
|
|
5630
|
+
if (!this.adLayer.isAdPlaying() && this.video.paused && this.video.readyState >= 2) {
|
|
5631
|
+
var _this_video_play;
|
|
5632
|
+
(_this_video_play = this.video.play()) === null || _this_video_play === void 0 ? void 0 : _this_video_play.catch(function() {});
|
|
5633
|
+
}
|
|
5563
5634
|
}
|
|
5564
5635
|
}
|
|
5565
5636
|
},
|