stormcloud-video-player 0.2.34 → 0.2.36

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/lib/index.d.cts CHANGED
@@ -181,10 +181,7 @@ declare class StormcloudVideoPlayer {
181
181
  private startAdFailsafeTimer;
182
182
  private clearAdFailsafeTimer;
183
183
  private selectVastTagsForBreak;
184
- private logQueuedAdUrls;
185
184
  private logAdState;
186
- private enforceAdHoldState;
187
- private releaseAdHoldState;
188
185
  private fetchAndParseVastXml;
189
186
  private extractMediaUrlsFromVast;
190
187
  private preloadMediaFile;
package/lib/index.d.ts CHANGED
@@ -181,10 +181,7 @@ declare class StormcloudVideoPlayer {
181
181
  private startAdFailsafeTimer;
182
182
  private clearAdFailsafeTimer;
183
183
  private selectVastTagsForBreak;
184
- private logQueuedAdUrls;
185
184
  private logAdState;
186
- private enforceAdHoldState;
187
- private releaseAdHoldState;
188
185
  private fetchAndParseVastXml;
189
186
  private extractMediaUrlsFromVast;
190
187
  private preloadMediaFile;
package/lib/index.js CHANGED
@@ -626,19 +626,10 @@ function createImaController(video, options) {
626
626
  adsManager.addEventListener(
627
627
  AdEvent.CONTENT_PAUSE_REQUESTED,
628
628
  () => {
629
- console.log("[DEBUG-FLOW] \u{1F3AF} CONTENT_PAUSE_REQUESTED - Ad starting");
629
+ console.log("[DEBUG-FLOW] \u{1F3AF} CONTENT_PAUSE_REQUESTED - Ad request accepted");
630
630
  if (!(options == null ? void 0 : options.continueLiveStreamDuringAds)) {
631
631
  video.pause();
632
632
  }
633
- hideContentVideo();
634
- if (adContainerEl) {
635
- adContainerEl.style.pointerEvents = "auto";
636
- adContainerEl.style.display = "flex";
637
- adContainerEl.style.backgroundColor = "#000";
638
- adContainerEl.offsetHeight;
639
- adContainerEl.style.opacity = "1";
640
- console.log("[DEBUG-LAYER] \u{1F7E1} Ad container VISIBLE");
641
- }
642
633
  adPlaying = true;
643
634
  setAdPlayingFlag(true);
644
635
  emit("content_pause");
@@ -669,7 +660,7 @@ function createImaController(video, options) {
669
660
  console.log("[DEBUG-FLOW] \u23F8\uFE0F CONTENT_RESUME - Single ad done");
670
661
  adPlaying = false;
671
662
  setAdPlayingFlag(false);
672
- console.log("[DEBUG-LAYER] \u26A0\uFE0F Waiting for pod manager decision (more ads or done)");
663
+ console.log("[DEBUG-LAYER] \u26A0\uFE0F Waiting for pod manager (more ads, placeholder, or done)");
673
664
  emit("content_resume");
674
665
  }
675
666
  );
@@ -2437,44 +2428,31 @@ var StormcloudVideoPlayer = class {
2437
2428
  }
2438
2429
  });
2439
2430
  this.ima.on("ad_error", () => {
2440
- if (this.config.debugAdTiming) {
2441
- console.log("[StormcloudVideoPlayer] IMA ad_error event received", {
2442
- showAds: this.showAds,
2443
- inAdBreak: this.inAdBreak,
2444
- remainingAds: this.adPodQueue.length
2445
- });
2446
- }
2431
+ const remaining = this.getRemainingAdMs();
2432
+ console.log(
2433
+ `[DEBUG-POD] \u274C ad_error event | inBreak=${this.inAdBreak}, queue=${this.adPodQueue.length}, remaining=${remaining}ms`
2434
+ );
2447
2435
  if (this.inAdBreak) {
2448
- const remaining = this.getRemainingAdMs();
2449
2436
  if (remaining > 500 && this.adPodQueue.length > 0) {
2450
2437
  const nextPreloaded = this.findNextPreloadedAd();
2451
2438
  if (nextPreloaded) {
2452
2439
  this.currentAdIndex++;
2453
- if (this.config.debugAdTiming) {
2454
- console.log(
2455
- `[StormcloudVideoPlayer] Skipping to next preloaded ad after error`
2456
- );
2457
- }
2440
+ console.log(
2441
+ `[DEBUG-POD] \u27A1\uFE0F Trying next ad after error (${this.currentAdIndex}/${this.totalAdsInBreak})`
2442
+ );
2458
2443
  this.playSingleAd(nextPreloaded).catch(() => {
2459
2444
  this.handleAdFailure();
2460
2445
  });
2461
2446
  } else {
2462
- if (this.config.debugAdTiming) {
2463
- console.log(
2464
- "[StormcloudVideoPlayer] No preloaded ads available, ending ad break"
2465
- );
2466
- }
2447
+ console.log("[DEBUG-POD] \u26A0\uFE0F No more preloaded ads - calling handleAdFailure");
2467
2448
  this.handleAdFailure();
2468
2449
  }
2469
2450
  } else {
2451
+ console.log("[DEBUG-POD] \u26A0\uFE0F No more ads or time - calling handleAdFailure");
2470
2452
  this.handleAdFailure();
2471
2453
  }
2472
2454
  } else {
2473
- if (this.config.debugAdTiming) {
2474
- console.log(
2475
- "[StormcloudVideoPlayer] Ad error before ad break established - cleaning up"
2476
- );
2477
- }
2455
+ console.log("[DEBUG-POD] \u26A0\uFE0F Error before ad break established");
2478
2456
  this.handleAdFailure();
2479
2457
  }
2480
2458
  });
@@ -2484,7 +2462,7 @@ var StormcloudVideoPlayer = class {
2484
2462
  this.clearAdRequestWatchdog();
2485
2463
  this.activeAdRequestToken = null;
2486
2464
  this.showAds = true;
2487
- this.enforceAdHoldState();
2465
+ console.log("[DEBUG-LAYER] \u{1F3AC} Layers: Main=hidden, Ad=visible, Placeholder=no");
2488
2466
  });
2489
2467
  this.ima.on("content_resume", () => {
2490
2468
  console.log(`[DEBUG-POD] \u23F8\uFE0F content_resume | ad ${this.currentAdIndex}/${this.totalAdsInBreak}, queue=${this.adPodQueue.length}, remaining=${this.getRemainingAdMs()}ms`);
@@ -2664,6 +2642,12 @@ var StormcloudVideoPlayer = class {
2664
2642
  });
2665
2643
  }
2666
2644
  if (marker.type === "start") {
2645
+ if (this.inAdBreak) {
2646
+ console.log(
2647
+ `[DEBUG-POD] \u26A0\uFE0F SCTE-35 start marker ignored - already in ad break (currentTime: ${this.video.currentTime})`
2648
+ );
2649
+ return;
2650
+ }
2667
2651
  this.inAdBreak = true;
2668
2652
  const durationMs = marker.durationSeconds != null ? marker.durationSeconds * 1e3 : void 0;
2669
2653
  this.expectedAdBreakDurationMs = durationMs;
@@ -2730,6 +2714,9 @@ var StormcloudVideoPlayer = class {
2730
2714
  return;
2731
2715
  }
2732
2716
  if (marker.type === "progress" && this.inAdBreak) {
2717
+ console.log(
2718
+ `[DEBUG-POD] \u{1F4CA} SCTE-35 progress marker (currentTime: ${this.video.currentTime})`
2719
+ );
2733
2720
  if (marker.durationSeconds != null) {
2734
2721
  this.expectedAdBreakDurationMs = marker.durationSeconds * 1e3;
2735
2722
  }
@@ -2741,7 +2728,8 @@ var StormcloudVideoPlayer = class {
2741
2728
  );
2742
2729
  this.scheduleAdStopCountdown(remainingMs);
2743
2730
  }
2744
- if (!this.ima.isAdPlaying()) {
2731
+ if (!this.ima.isAdPlaying() && this.activeAdRequestToken === null) {
2732
+ console.log("[DEBUG-POD] \u{1F4CA} Progress marker: no ad playing, attempting to start");
2745
2733
  const scheduled = this.findCurrentOrNextBreak(
2746
2734
  this.video.currentTime * 1e3
2747
2735
  );
@@ -2750,25 +2738,31 @@ var StormcloudVideoPlayer = class {
2750
2738
  const first = tags[0];
2751
2739
  const rest = tags.slice(1);
2752
2740
  this.adPodQueue = rest;
2753
- if (!this.showAds) {
2754
- this.ima.updateOriginalMutedState(this.video.muted, this.video.volume);
2755
- }
2756
2741
  this.playSingleAd(first).catch(() => {
2757
2742
  });
2758
2743
  }
2744
+ } else {
2745
+ console.log(
2746
+ `[DEBUG-POD] \u{1F4CA} Progress marker: ad playing or request active (playing=${this.ima.isAdPlaying()}, token=${this.activeAdRequestToken})`
2747
+ );
2759
2748
  }
2760
2749
  return;
2761
2750
  }
2762
2751
  if (marker.type === "end") {
2752
+ console.log(
2753
+ `[DEBUG-POD] \u{1F3C1} SCTE-35 end marker received (currentTime: ${this.video.currentTime})`
2754
+ );
2763
2755
  this.inAdBreak = false;
2764
2756
  this.expectedAdBreakDurationMs = void 0;
2765
2757
  this.currentAdBreakStartWallClockMs = void 0;
2766
2758
  this.clearAdStartTimer();
2767
2759
  this.clearAdStopTimer();
2768
2760
  if (this.ima.isAdPlaying()) {
2761
+ console.log("[DEBUG-POD] \u{1F6D1} Stopping ad due to SCTE-35 end marker");
2769
2762
  this.ima.stop().catch(() => {
2770
2763
  });
2771
2764
  }
2765
+ this.handleAdPodComplete();
2772
2766
  return;
2773
2767
  }
2774
2768
  }
@@ -3099,10 +3093,12 @@ var StormcloudVideoPlayer = class {
3099
3093
  this.vastToMediaUrlMap.clear();
3100
3094
  this.preloadedMediaUrls.clear();
3101
3095
  this.preloadingMediaUrls.clear();
3096
+ const currentMuted = this.video.muted;
3097
+ const currentVolume = this.video.volume;
3102
3098
  console.log(
3103
- `[DEBUG-AUDIO] \u{1F4BE} Capturing original state | muted=${this.video.muted}, volume=${this.video.volume}`
3099
+ `[DEBUG-AUDIO] \u{1F4BE} Capturing ORIGINAL state (once) | muted=${currentMuted}, volume=${currentVolume}`
3104
3100
  );
3105
- this.ima.updateOriginalMutedState(this.video.muted, this.video.volume);
3101
+ this.ima.updateOriginalMutedState(currentMuted, currentVolume);
3106
3102
  this.inAdBreak = true;
3107
3103
  this.currentAdIndex = 0;
3108
3104
  this.totalAdsInBreak = vastTagUrls.length;
@@ -3225,31 +3221,15 @@ var StormcloudVideoPlayer = class {
3225
3221
  const overrunMs = Math.max(0, elapsedSinceStartMs - expectedDurationMs);
3226
3222
  const shouldExtendAdBreak = (adPlaying || pendingAds || this.showAds) && overrunMs < maxExtensionMs;
3227
3223
  if (shouldExtendAdBreak) {
3228
- if (this.config.debugAdTiming) {
3229
- console.log(
3230
- "[StormcloudVideoPlayer] Extending ad break beyond scheduled duration",
3231
- {
3232
- adPlaying,
3233
- pendingAds,
3234
- showAds: this.showAds,
3235
- overrunMs,
3236
- checkIntervalMs,
3237
- maxExtensionMs
3238
- }
3239
- );
3240
- }
3224
+ console.log(
3225
+ `[DEBUG-POD] \u23F3 Extending ad break | elapsed=${elapsedSinceStartMs}ms, expected=${expectedDurationMs}ms, overrun=${overrunMs}ms`
3226
+ );
3241
3227
  this.scheduleAdStopCountdown(checkIntervalMs);
3242
3228
  return;
3243
3229
  }
3244
- if (this.config.debugAdTiming) {
3245
- console.log("[StormcloudVideoPlayer] Ending ad break via timer", {
3246
- adPlaying,
3247
- pendingAds,
3248
- showAds: this.showAds,
3249
- overrunMs,
3250
- maxExtensionMs
3251
- });
3252
- }
3230
+ console.log(
3231
+ `[DEBUG-POD] \u23F1\uFE0F Ad break duration expired | elapsed=${elapsedSinceStartMs}ms, expected=${expectedDurationMs}ms`
3232
+ );
3253
3233
  if (adPlaying) {
3254
3234
  this.ima.stop().catch(() => {
3255
3235
  });
@@ -3332,7 +3312,6 @@ var StormcloudVideoPlayer = class {
3332
3312
  this.clearAdRequestWatchdog();
3333
3313
  this.clearAdFailsafeTimer();
3334
3314
  this.activeAdRequestToken = null;
3335
- this.releaseAdHoldState();
3336
3315
  this.preloadingAdUrls.clear();
3337
3316
  this.vastToMediaUrlMap.clear();
3338
3317
  this.preloadedMediaUrls.clear();
@@ -3349,13 +3328,18 @@ var StormcloudVideoPlayer = class {
3349
3328
  this.totalAdsInBreak = 0;
3350
3329
  this.ima.stop().catch(() => {
3351
3330
  });
3352
- const originalMutedState = this.ima.getOriginalMutedState();
3353
- const originalVolume = typeof this.ima.getOriginalVolume === "function" ? this.ima.getOriginalVolume() : this.video.volume;
3354
- this.video.muted = originalMutedState;
3355
- this.video.volume = originalVolume;
3331
+ const restoredMuted = this.ima.getOriginalMutedState();
3332
+ const restoredVolume = this.ima.getOriginalVolume();
3356
3333
  console.log(
3357
- `[DEBUG-AUDIO] \u{1F50A} Main video restored | muted=${originalMutedState}, volume=${originalVolume}`
3334
+ `[DEBUG-AUDIO] \u{1F50A} Audio restored by IMA | muted=${restoredMuted}, volume=${restoredVolume}`
3358
3335
  );
3336
+ console.log("[DEBUG-LAYER] \u{1F3AC} Layers: Main=visible, Ad=hidden, Placeholder=no");
3337
+ if (this.video.muted !== restoredMuted) {
3338
+ this.video.muted = restoredMuted;
3339
+ }
3340
+ if (Math.abs(this.video.volume - restoredVolume) > 0.01) {
3341
+ this.video.volume = restoredVolume;
3342
+ }
3359
3343
  if (!this.shouldContinueLiveStreamDuringAds() && this.video.paused) {
3360
3344
  console.log("[DEBUG-FLOW] \u25B6\uFE0F Resuming main video playback");
3361
3345
  (_a = this.video.play()) == null ? void 0 : _a.catch((error) => {
@@ -3364,9 +3348,20 @@ var StormcloudVideoPlayer = class {
3364
3348
  }
3365
3349
  }
3366
3350
  handleAdFailure() {
3367
- console.log(
3368
- `[DEBUG-POD] \u274C handleAdFailure | inBreak=${this.inAdBreak}, showAds=${this.showAds}, paused=${this.video.paused}`
3369
- );
3351
+ console.log("[DEBUG-POD] \u274C handleAdFailure - skipping to next ad or ending break");
3352
+ const remaining = this.getRemainingAdMs();
3353
+ if (remaining > 500 && this.adPodQueue.length > 0) {
3354
+ const nextPreloaded = this.findNextPreloadedAd();
3355
+ if (nextPreloaded) {
3356
+ this.currentAdIndex++;
3357
+ console.log(`[DEBUG-POD] \u27A1\uFE0F Trying next ad after failure (${this.currentAdIndex}/${this.totalAdsInBreak})`);
3358
+ this.playSingleAd(nextPreloaded).catch(() => {
3359
+ this.handleAdPodComplete();
3360
+ });
3361
+ return;
3362
+ }
3363
+ }
3364
+ console.log("[DEBUG-POD] \u23F9\uFE0F Ending ad break after failure");
3370
3365
  this.handleAdPodComplete();
3371
3366
  }
3372
3367
  startAdRequestWatchdog(token) {
@@ -3439,12 +3434,6 @@ var StormcloudVideoPlayer = class {
3439
3434
  }
3440
3435
  return [b.vastTagUrl];
3441
3436
  }
3442
- logQueuedAdUrls(urls) {
3443
- if (!this.config.debugAdTiming) {
3444
- return;
3445
- }
3446
- console.log("[StormcloudVideoPlayer] ALL ad URLs queued:", urls);
3447
- }
3448
3437
  logAdState(event, extra = {}) {
3449
3438
  if (!this.config.debugAdTiming) {
3450
3439
  return;
@@ -3459,22 +3448,6 @@ var StormcloudVideoPlayer = class {
3459
3448
  ...extra
3460
3449
  });
3461
3450
  }
3462
- enforceAdHoldState() {
3463
- this.video.dataset.stormcloudAdPlaying = "true";
3464
- this.video.muted = true;
3465
- this.video.volume = 0;
3466
- console.log("[DEBUG-LAYER] \u{1F512} Enforced ad hold state (main video muted)");
3467
- if (typeof this.ima.showPlaceholder === "function") {
3468
- this.ima.showPlaceholder();
3469
- }
3470
- }
3471
- releaseAdHoldState() {
3472
- delete this.video.dataset.stormcloudAdPlaying;
3473
- console.log("[DEBUG-LAYER] \u{1F513} Released ad hold state");
3474
- if (typeof this.ima.hidePlaceholder === "function") {
3475
- this.ima.hidePlaceholder();
3476
- }
3477
- }
3478
3451
  async fetchAndParseVastXml(vastTagUrl) {
3479
3452
  try {
3480
3453
  const response = await fetch(vastTagUrl, { mode: "cors" });
@@ -3839,7 +3812,6 @@ var StormcloudVideoPlayer = class {
3839
3812
  }
3840
3813
  (_a = this.hls) == null ? void 0 : _a.destroy();
3841
3814
  (_b = this.ima) == null ? void 0 : _b.destroy();
3842
- this.releaseAdHoldState();
3843
3815
  this.preloadingAdUrls.clear();
3844
3816
  this.vastToMediaUrlMap.clear();
3845
3817
  this.preloadedMediaUrls.clear();