stormcloud-video-player 0.8.22 → 0.8.23

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.
@@ -2317,12 +2317,14 @@ var ANDROID_ID_TYPES = /* @__PURE__ */ new Set([
2317
2317
  "adid"
2318
2318
  ]);
2319
2319
  function resolveVastEnvironmentSignals(isCtv) {
2320
- var _ref, _bridgeSignals_limitAdTracking;
2320
+ var _ref;
2321
2321
  var bridgeSignals = readNativeBridgeSignals();
2322
+ var platformDevice = readPlatformNativeDeviceId();
2322
2323
  var lg = isCtv && isLgWebOS();
2323
- var deviceId = bridgeSignals.deviceId || readStoredDeviceId() || (lg ? getLgTestDeviceId() : void 0);
2324
- var deviceIdType = bridgeSignals.deviceIdType || readStoredString("deviceIdType") || readStoredString("idtype") || inferDeviceIdType() || (lg ? "lgudid" : void 0);
2325
- var limitAdTracking = deviceId != null ? (_ref = (_bridgeSignals_limitAdTracking = bridgeSignals.limitAdTracking) !== null && _bridgeSignals_limitAdTracking !== void 0 ? _bridgeSignals_limitAdTracking : readStoredLimitAdTracking()) !== null && _ref !== void 0 ? _ref : false : void 0;
2324
+ var deviceId = bridgeSignals.deviceId || readStoredDeviceId() || platformDevice.deviceId || (lg && platformDevice.limitAdTracking !== true ? getLgTestDeviceId() : void 0);
2325
+ var deviceIdType = bridgeSignals.deviceIdType || readStoredString("deviceIdType") || readStoredString("idtype") || platformDevice.deviceIdType || inferDeviceIdType() || (lg ? "lgudid" : void 0);
2326
+ var platformLat = bridgeSignals.deviceId ? bridgeSignals.limitAdTracking : platformDevice.limitAdTracking;
2327
+ var limitAdTracking = deviceId != null ? (_ref = platformLat !== null && platformLat !== void 0 ? platformLat : readStoredLimitAdTracking()) !== null && _ref !== void 0 ? _ref : false : void 0;
2326
2328
  if (isCtv) {
2327
2329
  return _object_spread_props(_object_spread({
2328
2330
  isCtv: true,
@@ -2393,6 +2395,72 @@ function createUuid() {
2393
2395
  return nibble.toString(16);
2394
2396
  });
2395
2397
  }
2398
+ function readPlatformNativeDeviceId() {
2399
+ if (typeof window === "undefined") return {};
2400
+ try {
2401
+ var _window_webapis;
2402
+ var adinfo = (_window_webapis = window.webapis) === null || _window_webapis === void 0 ? void 0 : _window_webapis.adinfo;
2403
+ if (adinfo) {
2404
+ var tifa = typeof adinfo.getTIFA === "function" ? adinfo.getTIFA() : adinfo.tifa;
2405
+ if (typeof tifa === "string" && tifa && !isMacroPlaceholder(tifa)) {
2406
+ var lat = typeof adinfo.isLATEnabled === "function" ? adinfo.isLATEnabled() : void 0;
2407
+ return _object_spread({
2408
+ deviceId: tifa,
2409
+ deviceIdType: "tifa"
2410
+ }, typeof lat === "boolean" ? {
2411
+ limitAdTracking: lat
2412
+ } : {});
2413
+ }
2414
+ }
2415
+ } catch (unused) {}
2416
+ try {
2417
+ var webOSDev = window.webOSDev;
2418
+ if (webOSDev) {
2419
+ var _webOSDev_lgudid;
2420
+ var lgudid = typeof webOSDev.LGUDID === "function" ? webOSDev.LGUDID() : (_webOSDev_lgudid = webOSDev.lgudid) !== null && _webOSDev_lgudid !== void 0 ? _webOSDev_lgudid : webOSDev.LGUDID;
2421
+ if (typeof lgudid === "string" && lgudid) {
2422
+ if (isZeroedAdId(lgudid)) {
2423
+ return {
2424
+ deviceIdType: "lgudid",
2425
+ limitAdTracking: true
2426
+ };
2427
+ }
2428
+ if (!isMacroPlaceholder(lgudid)) {
2429
+ return {
2430
+ deviceId: lgudid,
2431
+ deviceIdType: "lgudid",
2432
+ limitAdTracking: false
2433
+ };
2434
+ }
2435
+ }
2436
+ }
2437
+ } catch (unused) {}
2438
+ try {
2439
+ var roku = window.Roku;
2440
+ if (roku) {
2441
+ var rida = typeof roku.getPublisherUniqueId === "function" ? roku.getPublisherUniqueId() : roku.rida;
2442
+ if (typeof rida === "string" && rida && !isMacroPlaceholder(rida)) {
2443
+ return {
2444
+ deviceId: rida,
2445
+ deviceIdType: "rida",
2446
+ limitAdTracking: false
2447
+ };
2448
+ }
2449
+ }
2450
+ } catch (unused) {}
2451
+ return {};
2452
+ }
2453
+ var ZEROED_AD_ID_PATTERNS = /* @__PURE__ */ new Set([
2454
+ "38400000-8cf0-11bd-b23e-10b96e40000d",
2455
+ "00000000-0000-0000-0000-000000000000"
2456
+ ]);
2457
+ function isMacroPlaceholder(value) {
2458
+ var t = value.trim();
2459
+ return !t || /^(\[[^\]]*\]|\{[^}]*\}|%%[^%]*%%)$/.test(t) || /^(unknown|null|undefined|none|n\/a|\$\{[^}]+\})$/i.test(t) || ZEROED_AD_ID_PATTERNS.has(t.toLowerCase());
2460
+ }
2461
+ function isZeroedAdId(value) {
2462
+ return ZEROED_AD_ID_PATTERNS.has(value.trim().toLowerCase());
2463
+ }
2396
2464
  function readNativeBridgeSignals() {
2397
2465
  if (typeof window === "undefined") {
2398
2466
  return {};
@@ -2733,7 +2801,7 @@ var INLINE_DEVICE_MACRO_REPLACEMENTS = [
2733
2801
  }
2734
2802
  }
2735
2803
  ];
2736
- function isMacroPlaceholder(value) {
2804
+ function isMacroPlaceholder2(value) {
2737
2805
  if (value == null) return true;
2738
2806
  var trimmed = value.trim();
2739
2807
  if (!trimmed) return true;
@@ -2792,11 +2860,11 @@ function applyDeviceIdentityParams(params, ctx) {
2792
2860
  if (runtimeId) {
2793
2861
  params.set("rdid", runtimeId);
2794
2862
  params.set("idtype", runtimeType || tagType || "aaid");
2795
- params.set("is_lat", latValue !== null && latValue !== void 0 ? latValue : isMacroPlaceholder(tagLat) ? "0" : tagLat);
2863
+ params.set("is_lat", latValue !== null && latValue !== void 0 ? latValue : isMacroPlaceholder2(tagLat) ? "0" : tagLat);
2796
2864
  return;
2797
2865
  }
2798
- var tagRdidValid = Boolean(tagRdid && !isMacroPlaceholder(tagRdid));
2799
- var tagTypeValid = Boolean(tagType && !isMacroPlaceholder(tagType));
2866
+ var tagRdidValid = Boolean(tagRdid && !isMacroPlaceholder2(tagRdid));
2867
+ var tagTypeValid = Boolean(tagType && !isMacroPlaceholder2(tagType));
2800
2868
  if (tagRdidValid && tagTypeValid && runtimeType && !isEquivalentDeviceIdType(tagType, runtimeType)) {
2801
2869
  params.delete("rdid");
2802
2870
  params.delete("idtype");
@@ -2804,10 +2872,10 @@ function applyDeviceIdentityParams(params, ctx) {
2804
2872
  return;
2805
2873
  }
2806
2874
  if (tagRdidValid) {
2807
- if (isMacroPlaceholder(tagType) && runtimeType) {
2875
+ if (isMacroPlaceholder2(tagType) && runtimeType) {
2808
2876
  params.set("idtype", runtimeType);
2809
2877
  }
2810
- if (isMacroPlaceholder(tagLat)) {
2878
+ if (isMacroPlaceholder2(tagLat)) {
2811
2879
  params.set("is_lat", latValue !== null && latValue !== void 0 ? latValue : "0");
2812
2880
  }
2813
2881
  return;
@@ -2993,7 +3061,7 @@ function applyVastMacros(baseUrl, ctx) {
2993
3061
  }
2994
3062
  var staleKeys = [];
2995
3063
  params.forEach(function(value, key) {
2996
- if (isMacroPlaceholder(value)) {
3064
+ if (isMacroPlaceholder2(value)) {
2997
3065
  staleKeys.push(key);
2998
3066
  }
2999
3067
  });
@@ -5942,7 +6010,7 @@ var HlsEngine = /*#__PURE__*/ function() {
5942
6010
  key: "setupNativeHls",
5943
6011
  value: function setupNativeHls() {
5944
6012
  return _async_to_generator(function() {
5945
- var _this_config_isLiveStream, _this_config_lowLatencyMode, _this_video_play;
6013
+ var _this_config_isLiveStream, _this_config_lowLatencyMode, adBehavior, _this_video_play;
5946
6014
  return _ts_generator(this, function(_state) {
5947
6015
  switch(_state.label){
5948
6016
  case 0:
@@ -5951,10 +6019,11 @@ var HlsEngine = /*#__PURE__*/ function() {
5951
6019
  this.video.src = this.config.src;
5952
6020
  this.isLiveStream = (_this_config_isLiveStream = this.config.isLiveStream) !== null && _this_config_isLiveStream !== void 0 ? _this_config_isLiveStream : (_this_config_lowLatencyMode = this.config.lowLatencyMode) !== null && _this_config_lowLatencyMode !== void 0 ? _this_config_lowLatencyMode : false;
5953
6021
  if (this.debug) {
5954
- console.log("[StormcloudVideoPlayer] Using native HLS playback - VOD mode:", {
6022
+ adBehavior = this.isLiveStream ? "live (main video continues muted during ads)" : "vod (main video pauses during ads)";
6023
+ console.log("[StormcloudVideoPlayer] Using native HLS playback:", {
5955
6024
  isLive: this.isLiveStream,
5956
6025
  allowNativeHls: this.config.allowNativeHls,
5957
- adBehavior: "vod (main video pauses during ads)"
6026
+ adBehavior: adBehavior
5958
6027
  });
5959
6028
  }
5960
6029
  if (!this.config.autoplay) return [
@@ -6363,6 +6432,14 @@ var HlsEngine = /*#__PURE__*/ function() {
6363
6432
  });
6364
6433
  }
6365
6434
  },
6435
+ {
6436
+ key: "getLiveSyncPosition",
6437
+ value: function getLiveSyncPosition() {
6438
+ var _this_hls;
6439
+ var pos = (_this_hls = this.hls) === null || _this_hls === void 0 ? void 0 : _this_hls.liveSyncPosition;
6440
+ return typeof pos === "number" && Number.isFinite(pos) ? pos : void 0;
6441
+ }
6442
+ },
6366
6443
  {
6367
6444
  key: "destroy",
6368
6445
  value: function destroy() {
@@ -7937,6 +8014,13 @@ var AdBreakOrchestrator = /*#__PURE__*/ function() {
7937
8014
  this.host.video.volume = restoredVolume;
7938
8015
  }
7939
8016
  if (this.host.shouldContinueLiveStreamDuringAds()) {
8017
+ var liveSyncPos = this.host.getLiveSyncPosition();
8018
+ if (liveSyncPos != null && liveSyncPos > this.host.video.currentTime) {
8019
+ if (this.debug) {
8020
+ console.log("[StormcloudVideoPlayer] Live break end — snapping to live edge: ".concat(this.host.video.currentTime.toFixed(2), "s → ").concat(liveSyncPos.toFixed(2), "s"));
8021
+ }
8022
+ this.host.video.currentTime = liveSyncPos;
8023
+ }
7940
8024
  if (this.host.video.paused) {
7941
8025
  var _this_host_video_play;
7942
8026
  if (this.debug) console.log("[StormcloudVideoPlayer] Content video paused in live mode after ads, resuming playback");
@@ -8079,6 +8163,9 @@ var StormcloudVideoPlayer = /*#__PURE__*/ function() {
8079
8163
  shouldContinueLiveStreamDuringAds: function shouldContinueLiveStreamDuringAds() {
8080
8164
  return _this.shouldContinueLiveStreamDuringAds();
8081
8165
  },
8166
+ getLiveSyncPosition: function getLiveSyncPosition() {
8167
+ return _this.hlsEngine.getLiveSyncPosition();
8168
+ },
8082
8169
  generateVastUrls: function generateVastUrls(base, count) {
8083
8170
  return _this.generateVastUrls(base, count);
8084
8171
  }
@@ -8120,7 +8207,7 @@ var StormcloudVideoPlayer = /*#__PURE__*/ function() {
8120
8207
  // ───────────────────────────────────────────────────────────────
8121
8208
  function load() {
8122
8209
  return _async_to_generator(function() {
8123
- var _this, _this_config_lowLatencyMode, error;
8210
+ var _this, _this_config_lowLatencyMode, error, continueLiveStreamDuringAds;
8124
8211
  return _ts_generator(this, function(_state) {
8125
8212
  switch(_state.label){
8126
8213
  case 0:
@@ -8174,15 +8261,22 @@ var StormcloudVideoPlayer = /*#__PURE__*/ function() {
8174
8261
  3,
8175
8262
  6
8176
8263
  ];
8177
- this.adPlayer.destroy();
8178
- this.adPlayer = this.createAdPlayer(false);
8179
- this.adPlayer.initialize();
8180
8264
  return [
8181
8265
  4,
8182
8266
  this.hlsEngine.setupNativeHls()
8183
8267
  ];
8184
8268
  case 5:
8185
8269
  _state.sent();
8270
+ continueLiveStreamDuringAds = this.shouldContinueLiveStreamDuringAds();
8271
+ if (this.debug) {
8272
+ console.log("[StormcloudVideoPlayer] Native HLS ad behavior:", {
8273
+ isLive: this.hlsEngine.isLiveStream,
8274
+ continueLiveStreamDuringAds: continueLiveStreamDuringAds
8275
+ });
8276
+ }
8277
+ this.adPlayer.destroy();
8278
+ this.adPlayer = this.createAdPlayer(continueLiveStreamDuringAds);
8279
+ this.adPlayer.initialize();
8186
8280
  return [
8187
8281
  2
8188
8282
  ];
@@ -8290,9 +8384,14 @@ var StormcloudVideoPlayer = /*#__PURE__*/ function() {
8290
8384
  {
8291
8385
  key: "shouldContinueLiveStreamDuringAds",
8292
8386
  value: function shouldContinueLiveStreamDuringAds() {
8293
- if (this.config.allowNativeHls) return false;
8294
- if (!this.hlsEngine.isLiveStream) return false;
8295
- return true;
8387
+ if (this.hlsEngine.isLiveStream) {
8388
+ return true;
8389
+ }
8390
+ var duration = this.video.duration;
8391
+ if (!Number.isFinite(duration) || duration === Infinity) {
8392
+ return true;
8393
+ }
8394
+ return false;
8296
8395
  }
8297
8396
  },
8298
8397
  {
@@ -8590,9 +8689,6 @@ var StormcloudVideoPlayer = /*#__PURE__*/ function() {
8590
8689
  this.adBreak.showAds = true;
8591
8690
  this.adBreak.inAdBreak = true;
8592
8691
  this.timing.currentAdBreakStartWallClockMs = Date.now();
8593
- if (!this.video.paused) {
8594
- this.video.pause();
8595
- }
8596
8692
  _state.label = 1;
8597
8693
  case 1:
8598
8694
  _state.trys.push([