stormcloud-video-player 0.2.31 β†’ 0.2.33

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/sdk/ima.cjs CHANGED
@@ -311,15 +311,17 @@ function createImaController(video, options) {
311
311
  let adsLoadedResolve;
312
312
  let adsLoadedReject;
313
313
  function makeAdsRequest(google, vastTagUrl) {
314
+ console.log("[IMA] \u{1F4CB} === makeAdsRequest() - Building IMA request ===");
314
315
  const adsRequest = new google.ima.AdsRequest();
315
316
  const preloadedResponse = preloadedVast.get(vastTagUrl);
316
317
  if (preloadedResponse) {
317
318
  adsRequest.adsResponse = preloadedResponse;
318
319
  console.log(
319
- "[IMA] Using preloaded VAST response for immediate ad request"
320
+ "[IMA] \u26A1 Using preloaded VAST response for immediate ad request"
320
321
  );
321
322
  } else {
322
323
  adsRequest.adTagUrl = vastTagUrl;
324
+ console.log("[IMA] \u{1F310} Will fetch VAST from URL:", vastTagUrl);
323
325
  }
324
326
  const videoWidth = video.offsetWidth || video.clientWidth || 640;
325
327
  const videoHeight = video.offsetHeight || video.clientHeight || 360;
@@ -331,6 +333,7 @@ function createImaController(video, options) {
331
333
  try {
332
334
  const willAutoPlay = !video.paused || video.autoplay;
333
335
  adsRequest.setAdWillAutoPlay(willAutoPlay);
336
+ console.log(`[IMA] Ad will autoplay: ${willAutoPlay}`);
334
337
  } catch (error) {
335
338
  console.warn("[IMA] Failed to call setAdWillAutoPlay:", error);
336
339
  }
@@ -339,13 +342,17 @@ function createImaController(video, options) {
339
342
  try {
340
343
  const willPlayMuted = video.muted || video.volume === 0;
341
344
  adsRequest.setAdWillPlayMuted(willPlayMuted);
345
+ console.log(`[IMA] Ad will play muted: ${willPlayMuted}`);
342
346
  } catch (error) {
343
347
  console.warn("[IMA] Failed to call setAdWillPlayMuted:", error);
344
348
  }
345
349
  }
346
350
  adsRequest.vastLoadTimeout = 5e3;
347
- console.log(`[IMA] Ads request dimensions: ${videoWidth}x${videoHeight}`);
351
+ console.log(`[IMA] \u{1F4D0} Ads request dimensions: ${videoWidth}x${videoHeight}`);
352
+ console.log("[IMA] \u23F1\uFE0F VAST load timeout: 5000ms");
353
+ console.log("[IMA] \u{1F680} Calling adsLoader.requestAds()...");
348
354
  adsLoader.requestAds(adsRequest);
355
+ console.log("[IMA] \u23F3 Waiting for ADS_MANAGER_LOADED or AD_ERROR event...");
349
356
  if (preloadedResponse) {
350
357
  preloadedVast.delete(vastTagUrl);
351
358
  }
@@ -423,22 +430,24 @@ function createImaController(video, options) {
423
430
  });
424
431
  },
425
432
  async requestAds(vastTagUrl) {
426
- console.log("[IMA] Requesting ads:", vastTagUrl);
433
+ console.log("[IMA] \u{1F4E1} === requestAds() called ===");
434
+ console.log("[IMA] VAST URL:", vastTagUrl);
435
+ console.log("[IMA] This will fetch the ad from the server - no visual change yet");
427
436
  if (!vastTagUrl || vastTagUrl.trim() === "") {
428
437
  const error = new Error("VAST tag URL is empty or undefined");
429
- console.warn("[IMA]", error.message);
438
+ console.warn("[IMA] \u274C", error.message);
430
439
  return Promise.reject(error);
431
440
  }
432
441
  try {
433
442
  new URL(vastTagUrl);
434
443
  } catch (e) {
435
444
  const error = new Error(`Invalid VAST tag URL format: ${vastTagUrl}`);
436
- console.warn("[IMA]", error.message);
445
+ console.warn("[IMA] \u274C", error.message);
437
446
  return Promise.reject(error);
438
447
  }
439
448
  if (adPlaying) {
440
449
  console.warn(
441
- "[IMA] Cannot request new ads while an ad is playing. Call stop() first."
450
+ "[IMA] \u26A0\uFE0F Cannot request new ads while an ad is playing. Call stop() first."
442
451
  );
443
452
  return Promise.reject(
444
453
  new Error("Ad already playing - cannot request new ads")
@@ -528,20 +537,85 @@ function createImaController(video, options) {
528
537
  adsLoader.addEventListener(
529
538
  google.ima.AdsManagerLoadedEvent.Type.ADS_MANAGER_LOADED,
530
539
  (evt) => {
531
- console.log(
532
- "[IMA] Ads manager loaded - enabling preloading for continuous playback"
533
- );
540
+ console.log("[IMA] \u2705 ADS_MANAGER_LOADED - Ads fetched successfully!");
541
+ console.log("[IMA] Setting up ads manager with preloading enabled");
542
+ console.log("[IMA] ========================================");
543
+ console.log("[IMA] EXPECTED EVENT FLOW:");
544
+ console.log("[IMA] 1. requestAds() \u2192 fetch VAST");
545
+ console.log("[IMA] 2. ADS_MANAGER_LOADED \u2192 ads ready");
546
+ console.log("[IMA] 3. play() \u2192 start playback");
547
+ console.log("[IMA] 4. CONTENT_PAUSE_REQUESTED \u2192 show ad layer \u2728");
548
+ console.log("[IMA] 5. STARTED \u2192 ad is playing");
549
+ console.log("[IMA] 6. CONTENT_RESUME_REQUESTED \u2192 ad done");
550
+ console.log("[IMA] 7. ALL_ADS_COMPLETED \u2192 hide ad layer");
551
+ console.log("[IMA] ========================================");
534
552
  try {
535
553
  const adsRenderingSettings = new google.ima.AdsRenderingSettings();
536
554
  adsRenderingSettings.enablePreloading = true;
537
555
  adsManager = evt.getAdsManager(video, adsRenderingSettings);
538
556
  const AdEvent = google.ima.AdEvent.Type;
539
557
  const AdErrorEvent = google.ima.AdErrorEvent.Type;
558
+ console.log("[IMA] ========== IMA EVENT LOGGING ENABLED ==========");
559
+ console.log("[IMA] All IMA SDK events will be logged below");
560
+ const allAdEvents = [
561
+ "AD_BREAK_READY",
562
+ "AD_METADATA",
563
+ "ALL_ADS_COMPLETED",
564
+ "CLICK",
565
+ "COMPLETE",
566
+ "CONTENT_PAUSE_REQUESTED",
567
+ "CONTENT_RESUME_REQUESTED",
568
+ "DURATION_CHANGE",
569
+ "FIRST_QUARTILE",
570
+ "IMPRESSION",
571
+ "INTERACTION",
572
+ "LINEAR_CHANGED",
573
+ "LOADED",
574
+ "LOG",
575
+ "MIDPOINT",
576
+ "PAUSED",
577
+ "RESUMED",
578
+ "SKIPPABLE_STATE_CHANGED",
579
+ "SKIPPED",
580
+ "STARTED",
581
+ "THIRD_QUARTILE",
582
+ "USER_CLOSE",
583
+ "VOLUME_CHANGED",
584
+ "VOLUME_MUTED"
585
+ ];
586
+ allAdEvents.forEach((eventType) => {
587
+ if (AdEvent[eventType]) {
588
+ adsManager.addEventListener(AdEvent[eventType], (e) => {
589
+ var _a, _b, _c, _d, _e, _f;
590
+ const ad = (_a = e.getAd) == null ? void 0 : _a.call(e);
591
+ const adData = ad ? {
592
+ adId: (_b = ad.getAdId) == null ? void 0 : _b.call(ad),
593
+ title: (_c = ad.getTitle) == null ? void 0 : _c.call(ad),
594
+ duration: (_d = ad.getDuration) == null ? void 0 : _d.call(ad),
595
+ isLinear: (_e = ad.isLinear) == null ? void 0 : _e.call(ad),
596
+ contentType: (_f = ad.getContentType) == null ? void 0 : _f.call(ad)
597
+ } : null;
598
+ console.log(`[IMA EVENT] ${eventType}`, {
599
+ eventType,
600
+ timestamp: (/* @__PURE__ */ new Date()).toISOString(),
601
+ adData
602
+ });
603
+ });
604
+ }
605
+ });
606
+ console.log("[IMA] ========== EVENT LISTENERS ATTACHED ==========");
540
607
  adsManager.addEventListener(
541
608
  AdErrorEvent.AD_ERROR,
542
609
  (errorEvent) => {
543
- var _a;
544
- console.error("[IMA] Ad error:", errorEvent.getError());
610
+ var _a, _b, _c, _d, _e, _f;
611
+ const error = errorEvent.getError();
612
+ console.error("[IMA] \u274C AD_ERROR Event:", {
613
+ message: (_a = error.getMessage) == null ? void 0 : _a.call(error),
614
+ errorCode: (_b = error.getErrorCode) == null ? void 0 : _b.call(error),
615
+ type: (_c = error.getType) == null ? void 0 : _c.call(error),
616
+ vastErrorCode: (_d = error.getVastErrorCode) == null ? void 0 : _d.call(error),
617
+ innerError: (_e = error.getInnerError) == null ? void 0 : _e.call(error)
618
+ });
545
619
  destroyAdsManager();
546
620
  adPlaying = false;
547
621
  setAdPlayingFlag(false);
@@ -583,7 +657,7 @@ function createImaController(video, options) {
583
657
  console.log(
584
658
  "[IMA] Resuming paused video after ad error"
585
659
  );
586
- (_a = video.play()) == null ? void 0 : _a.catch(() => {
660
+ (_f = video.play()) == null ? void 0 : _f.catch(() => {
587
661
  });
588
662
  }
589
663
  }
@@ -593,7 +667,8 @@ function createImaController(video, options) {
593
667
  adsManager.addEventListener(
594
668
  AdEvent.CONTENT_PAUSE_REQUESTED,
595
669
  () => {
596
- console.log("[IMA] Content pause requested");
670
+ console.log("[IMA] \u2705 CONTENT_PAUSE_REQUESTED - Ad is ready to play!");
671
+ console.log("[IMA] This is the event that triggers the ad layer to appear");
597
672
  if (!(options == null ? void 0 : options.continueLiveStreamDuringAds)) {
598
673
  video.pause();
599
674
  console.log("[IMA] Content video paused (VOD mode)");
@@ -602,13 +677,23 @@ function createImaController(video, options) {
602
677
  "[IMA] Content video continues in background (Live mode)"
603
678
  );
604
679
  }
680
+ hideContentVideo();
681
+ if (adContainerEl) {
682
+ adContainerEl.style.pointerEvents = "auto";
683
+ adContainerEl.style.display = "flex";
684
+ adContainerEl.style.backgroundColor = "#000";
685
+ adContainerEl.offsetHeight;
686
+ adContainerEl.style.opacity = "1";
687
+ console.log("[IMA] \u2728 Ad container NOW VISIBLE (after content pause)");
688
+ }
605
689
  adPlaying = true;
606
690
  setAdPlayingFlag(true);
691
+ console.log("[IMA] Emitting 'content_pause' event to player");
607
692
  emit("content_pause");
608
693
  }
609
694
  );
610
695
  adsManager.addEventListener(AdEvent.STARTED, () => {
611
- console.log("[IMA] Ad started - showing ad video");
696
+ console.log("[IMA] \u25B6\uFE0F STARTED - Ad playback has begun");
612
697
  setAdPlayingFlag(true);
613
698
  hideContentVideo();
614
699
  if (adVideoElement) {
@@ -624,20 +709,21 @@ function createImaController(video, options) {
624
709
  adContainerEl.style.backgroundColor = "#000";
625
710
  adContainerEl.offsetHeight;
626
711
  adContainerEl.style.opacity = "1";
627
- console.log("[IMA] Ad container now visible");
712
+ console.log("[IMA] Ad container now visible (STARTED event)");
628
713
  }
629
714
  });
630
715
  adsManager.addEventListener(
631
716
  AdEvent.CONTENT_RESUME_REQUESTED,
632
717
  () => {
633
- console.log("[IMA] Content resume requested");
718
+ console.log("[IMA] \u23F8\uFE0F CONTENT_RESUME_REQUESTED - Single ad completed");
634
719
  adPlaying = false;
635
720
  setAdPlayingFlag(false);
721
+ console.log("[IMA] Emitting 'content_resume' event to player");
636
722
  emit("content_resume");
637
723
  }
638
724
  );
639
725
  adsManager.addEventListener(AdEvent.ALL_ADS_COMPLETED, () => {
640
- console.log("[IMA] All ads completed - restoring content");
726
+ console.log("[IMA] \u{1F3C1} ALL_ADS_COMPLETED - All ads in break finished");
641
727
  adPlaying = false;
642
728
  setAdPlayingFlag(false);
643
729
  if (adContainerEl) {
@@ -647,7 +733,7 @@ function createImaController(video, options) {
647
733
  if (adContainerEl) {
648
734
  adContainerEl.style.pointerEvents = "none";
649
735
  adContainerEl.style.display = "none";
650
- console.log("[IMA] Ad container hidden");
736
+ console.log("[IMA] \u{1F648} Ad container hidden (ALL_ADS_COMPLETED)");
651
737
  }
652
738
  }, 300);
653
739
  }
@@ -658,6 +744,7 @@ function createImaController(video, options) {
658
744
  console.warn("[IMA] Failed to resume content video:", e);
659
745
  });
660
746
  }
747
+ console.log("[IMA] Emitting 'all_ads_completed' event to player");
661
748
  emit("all_ads_completed");
662
749
  });
663
750
  console.log("[IMA] Ads manager event listeners attached");
@@ -706,7 +793,17 @@ function createImaController(video, options) {
706
793
  adsLoader.addEventListener(
707
794
  google.ima.AdErrorEvent.Type.AD_ERROR,
708
795
  (adErrorEvent) => {
709
- console.error("[IMA] Ads loader error:", adErrorEvent.getError());
796
+ var _a, _b, _c, _d;
797
+ const error = adErrorEvent.getError();
798
+ console.error("[IMA] \u274C ADS_LOADER ERROR - Ad request failed!", {
799
+ message: (_a = error.getMessage) == null ? void 0 : _a.call(error),
800
+ errorCode: (_b = error.getErrorCode) == null ? void 0 : _b.call(error),
801
+ type: (_c = error.getType) == null ? void 0 : _c.call(error),
802
+ vastErrorCode: (_d = error.getVastErrorCode) == null ? void 0 : _d.call(error)
803
+ });
804
+ console.error("[IMA] This means the ad server didn't return valid ads");
805
+ console.error("[IMA] Ad layer will NOT appear (no flicker)");
806
+ console.error("[IMA] Full error object:", adErrorEvent.getError());
710
807
  adPlaying = false;
711
808
  setAdPlayingFlag(false);
712
809
  if (adContainerEl) {
@@ -738,8 +835,10 @@ function createImaController(video, options) {
738
835
  false
739
836
  );
740
837
  }
741
- console.log("[IMA] Making ads request");
838
+ console.log("[IMA] \u{1F680} Making ads request to IMA SDK");
839
+ console.log("[IMA] Waiting for IMA SDK response (LOADED or ERROR event)...");
742
840
  makeAdsRequest(google, vastTagUrl);
841
+ console.log("[IMA] \u23F3 Returning promise that will resolve when ads are loaded");
743
842
  return adsLoadedPromise;
744
843
  } catch (error) {
745
844
  console.error("[IMA] Failed to request ads:", error);
@@ -777,20 +876,23 @@ function createImaController(video, options) {
777
876
  },
778
877
  async play() {
779
878
  var _a, _b;
879
+ console.log("[IMA] \u25B6\uFE0F === play() called ===");
880
+ console.log("[IMA] This initializes and starts the ad");
881
+ console.log("[IMA] Ad layer will appear when CONTENT_PAUSE_REQUESTED fires");
780
882
  if (!((_a = window.google) == null ? void 0 : _a.ima) || !adDisplayContainer) {
781
883
  console.warn(
782
- "[IMA] Cannot play ad: IMA SDK or ad container not available"
884
+ "[IMA] \u274C Cannot play ad: IMA SDK or ad container not available"
783
885
  );
784
886
  return Promise.reject(new Error("IMA SDK not available"));
785
887
  }
786
888
  if (!adsManager) {
787
- console.warn("[IMA] Cannot play ad: No ads manager available");
889
+ console.warn("[IMA] \u274C Cannot play ad: No ads manager available");
788
890
  return Promise.reject(new Error("No ads manager"));
789
891
  }
790
892
  try {
791
893
  const width = video.clientWidth || 640;
792
894
  const height = video.clientHeight || 360;
793
- console.log(`[IMA] Initializing ads manager (${width}x${height})`);
895
+ console.log(`[IMA] \u{1F3AC} Initializing ads manager (${width}x${height})`);
794
896
  adsManager.init(width, height, window.google.ima.ViewMode.NORMAL);
795
897
  adPlaying = true;
796
898
  const adVolume = originalMutedState ? 0 : originalVolume;
@@ -798,7 +900,7 @@ function createImaController(video, options) {
798
900
  adVideoElement.volume = adVolume;
799
901
  adVideoElement.muted = originalMutedState;
800
902
  console.log(
801
- `[IMA] Set dedicated ad video volume to ${adVolume}, muted: ${originalMutedState}`
903
+ `[IMA] \u{1F50A} Set dedicated ad video volume to ${adVolume}, muted: ${originalMutedState}`
802
904
  );
803
905
  }
804
906
  try {
@@ -807,11 +909,13 @@ function createImaController(video, options) {
807
909
  } catch (error) {
808
910
  console.warn("[IMA] Failed to set IMA manager volume:", error);
809
911
  }
810
- console.log("[IMA] Starting ad playback");
912
+ console.log("[IMA] \u{1F3AF} Calling adsManager.start()");
913
+ console.log("[IMA] If successful, IMA will fire CONTENT_PAUSE_REQUESTED");
811
914
  adsManager.start();
915
+ console.log("[IMA] \u2705 play() completed successfully");
812
916
  return Promise.resolve();
813
917
  } catch (error) {
814
- console.error("[IMA] Error starting ad playback:", error);
918
+ console.error("[IMA] \u274C Error starting ad playback:", error);
815
919
  adPlaying = false;
816
920
  setAdPlayingFlag(false);
817
921
  if (!(options == null ? void 0 : options.continueLiveStreamDuringAds)) {
@@ -1 +1 @@
1
- {"version":3,"sources":["../../src/sdk/ima.ts","../../src/utils/browserCompat.ts"],"sourcesContent":["import type { ImaController } from \"../types\";\nimport { supportsGoogleIMA } from \"../utils/browserCompat\";\n\ndeclare global {\n interface Window {\n google?: any;\n }\n}\n\nexport function createImaController(\n video: HTMLVideoElement,\n options?: { continueLiveStreamDuringAds?: boolean }\n): ImaController {\n let adPlaying = false;\n let contentVideoHidden = false;\n let originalMutedState = false;\n let originalVolume =\n typeof video.volume === \"number\" && !Number.isNaN(video.volume)\n ? Math.max(0, Math.min(1, video.volume))\n : 1;\n const listeners = new Map<string, Set<(payload?: any) => void>>();\n const preloadedVast = new Map<string, string>();\n const preloadingVast = new Map<string, Promise<void>>();\n let adVideoElement: HTMLVideoElement | undefined;\n\n function setAdPlayingFlag(isPlaying: boolean): void {\n if (isPlaying) {\n video.dataset.stormcloudAdPlaying = \"true\";\n } else {\n delete video.dataset.stormcloudAdPlaying;\n }\n }\n\n function hideContentVideo(): void {\n if (!contentVideoHidden) {\n video.style.transition = \"opacity 0.3s ease-in-out\";\n video.style.opacity = \"0\";\n setTimeout(() => {\n video.style.visibility = \"hidden\";\n }, 300);\n video.muted = true;\n video.volume = 0;\n contentVideoHidden = true;\n console.log(\"[IMA] Content video hidden and muted\");\n }\n }\n\n function showContentVideo(): void {\n if (contentVideoHidden) {\n video.style.visibility = \"visible\";\n video.style.transition = \"opacity 0.3s ease-in-out\";\n video.offsetHeight;\n video.style.opacity = \"1\";\n video.muted = originalMutedState;\n video.volume = originalVolume;\n contentVideoHidden = false;\n console.log(\n `[IMA] Content video restored (muted: ${originalMutedState}, volume: ${originalVolume})`\n );\n }\n }\n\n function createAdVideoElement(): HTMLVideoElement {\n const adVideo = document.createElement(\"video\");\n adVideo.style.position = \"absolute\";\n adVideo.style.top = \"0\";\n adVideo.style.left = \"0\";\n adVideo.style.width = \"100%\";\n adVideo.style.height = \"100%\";\n adVideo.style.objectFit = \"contain\";\n adVideo.style.backgroundColor = \"transparent\";\n adVideo.style.zIndex = \"15\";\n adVideo.playsInline = true;\n adVideo.muted = false;\n adVideo.volume = originalMutedState ? 0 : originalVolume;\n\n adVideo.style.opacity = \"0\";\n adVideo.addEventListener(\n \"canplay\",\n () => {\n adVideo.style.opacity = \"1\";\n console.log(\"[IMA] Ad video ready to play\");\n },\n { once: true }\n );\n\n console.log(\n `[IMA] Created dedicated ad video element with volume: ${adVideo.volume}, muted: ${adVideo.muted}`\n );\n return adVideo;\n }\n\n function emit(event: string, payload?: any): void {\n const set = listeners.get(event);\n if (!set) return;\n for (const fn of Array.from(set)) {\n try {\n fn(payload);\n } catch {}\n }\n }\n\n function ensureImaLoaded(): Promise<void> {\n if (!supportsGoogleIMA()) {\n console.warn(\n \"[IMA] Google IMA SDK is not supported on this browser. Please use HLS ad player instead.\"\n );\n return Promise.reject(\n new Error(\"Google IMA SDK not supported on this browser\")\n );\n }\n\n try {\n const frameEl = window.frameElement as HTMLIFrameElement | null;\n const sandboxAttr = frameEl?.getAttribute?.(\"sandbox\") || \"\";\n if (sandboxAttr) {\n const tokens = new Set(\n sandboxAttr\n .split(/\\s+/)\n .map((t) => t.trim())\n .filter((t) => t.length > 0)\n );\n const allowsScripts = tokens.has(\"allow-scripts\");\n if (!allowsScripts) {\n // eslint-disable-next-line no-console\n console.error(\n \"StormcloudVideoPlayer: The host page is inside a sandboxed iframe without 'allow-scripts'. Google IMA cannot run ads within sandboxed frames. Remove the sandbox attribute or include 'allow-scripts allow-same-origin'.\"\n );\n }\n }\n } catch {}\n\n if (typeof window !== \"undefined\" && window.google?.ima)\n return Promise.resolve();\n const existing = document.querySelector(\n 'script[data-ima=\"true\"]'\n ) as HTMLScriptElement | null;\n if (existing) {\n if (window.google?.ima) {\n return Promise.resolve();\n }\n return new Promise((resolve, reject) => {\n const timeout = setTimeout(() => {\n reject(new Error(\"IMA SDK load timeout\"));\n }, 10000);\n existing.addEventListener(\"load\", () => {\n clearTimeout(timeout);\n resolve();\n });\n existing.addEventListener(\"error\", () => {\n clearTimeout(timeout);\n reject(new Error(\"IMA SDK load failed\"));\n });\n });\n }\n return new Promise((resolve, reject) => {\n const script = document.createElement(\"script\");\n script.src = \"https://imasdk.googleapis.com/js/sdkloader/ima3.js\";\n script.async = true;\n script.defer = true;\n script.setAttribute(\"data-ima\", \"true\");\n script.onload = () => resolve();\n script.onerror = () => reject(new Error(\"IMA SDK load failed\"));\n document.head.appendChild(script);\n });\n }\n\n let adsManager: any | undefined;\n let adsLoader: any | undefined;\n let adDisplayContainer: any | undefined;\n let adContainerEl: HTMLDivElement | undefined;\n let lastAdTagUrl: string | undefined;\n let retryAttempts = 0;\n const maxRetries = 2;\n const backoffBaseMs = 500;\n let adsLoadedPromise: Promise<void> | undefined;\n let adsLoadedResolve: (() => void) | undefined;\n let adsLoadedReject: ((error: Error) => void) | undefined;\n\n function makeAdsRequest(google: any, vastTagUrl: string) {\n const adsRequest = new google.ima.AdsRequest();\n const preloadedResponse = preloadedVast.get(vastTagUrl);\n\n if (preloadedResponse) {\n adsRequest.adsResponse = preloadedResponse;\n console.log(\n \"[IMA] Using preloaded VAST response for immediate ad request\"\n );\n } else {\n adsRequest.adTagUrl = vastTagUrl;\n }\n\n const videoWidth = video.offsetWidth || video.clientWidth || 640;\n const videoHeight = video.offsetHeight || video.clientHeight || 360;\n\n adsRequest.linearAdSlotWidth = videoWidth;\n adsRequest.linearAdSlotHeight = videoHeight;\n adsRequest.nonLinearAdSlotWidth = videoWidth;\n adsRequest.nonLinearAdSlotHeight = videoHeight;\n\n if (typeof adsRequest.setAdWillAutoPlay === \"function\") {\n try {\n const willAutoPlay = !video.paused || video.autoplay;\n adsRequest.setAdWillAutoPlay(willAutoPlay);\n } catch (error) {\n console.warn(\"[IMA] Failed to call setAdWillAutoPlay:\", error);\n }\n }\n\n if (typeof adsRequest.setAdWillPlayMuted === \"function\") {\n try {\n const willPlayMuted = video.muted || video.volume === 0;\n adsRequest.setAdWillPlayMuted(willPlayMuted);\n } catch (error) {\n console.warn(\"[IMA] Failed to call setAdWillPlayMuted:\", error);\n }\n }\n\n adsRequest.vastLoadTimeout = 5000;\n\n console.log(`[IMA] Ads request dimensions: ${videoWidth}x${videoHeight}`);\n\n adsLoader.requestAds(adsRequest);\n\n if (preloadedResponse) {\n preloadedVast.delete(vastTagUrl);\n }\n }\n\n function ensurePlaceholderContainer(): void {\n if (adContainerEl) {\n return;\n }\n\n const container = document.createElement(\"div\");\n container.style.position = \"absolute\";\n container.style.left = \"0\";\n container.style.top = \"0\";\n container.style.right = \"0\";\n container.style.bottom = \"0\";\n container.style.display = \"none\";\n container.style.alignItems = \"center\";\n container.style.justifyContent = \"center\";\n container.style.pointerEvents = \"none\";\n container.style.zIndex = \"10\";\n container.style.backgroundColor = \"transparent\";\n container.style.transition =\n \"opacity 0.3s ease-in-out, background-color 0.3s ease-in-out\";\n container.style.opacity = \"0\";\n\n video.parentElement?.appendChild(container);\n adContainerEl = container;\n }\n\n async function fetchVastDocument(vastTagUrl: string): Promise<string> {\n const response = await fetch(vastTagUrl, { mode: \"cors\" });\n if (!response.ok) {\n throw new Error(`Failed to preload VAST: ${response.status}`);\n }\n return response.text();\n }\n\n function destroyAdsManager() {\n if (adsManager) {\n try {\n console.log(\"[IMA] Destroying existing ads manager\");\n adsManager.destroy();\n } catch (error) {\n console.warn(\"[IMA] Error destroying ads manager:\", error);\n }\n adsManager = undefined;\n }\n\n if (adVideoElement) {\n adVideoElement.style.opacity = \"0\";\n }\n }\n\n return {\n initialize() {\n ensureImaLoaded()\n .then(() => {\n const google = window.google;\n ensurePlaceholderContainer();\n\n if (!adDisplayContainer && adContainerEl) {\n if (!adVideoElement) {\n adVideoElement = createAdVideoElement();\n adContainerEl.appendChild(adVideoElement);\n console.log(\n \"[IMA] Dedicated ad video element added to container\"\n );\n }\n\n adDisplayContainer = new google.ima.AdDisplayContainer(\n adContainerEl,\n adVideoElement\n );\n try {\n adDisplayContainer.initialize?.();\n console.log(\n \"[IMA] AdDisplayContainer initialized with dedicated ad video\"\n );\n } catch {}\n }\n })\n .catch(() => {});\n },\n async requestAds(vastTagUrl: string) {\n console.log(\"[IMA] Requesting ads:\", vastTagUrl);\n\n if (!vastTagUrl || vastTagUrl.trim() === \"\") {\n const error = new Error(\"VAST tag URL is empty or undefined\");\n console.warn(\"[IMA]\", error.message);\n return Promise.reject(error);\n }\n\n try {\n new URL(vastTagUrl);\n } catch (e) {\n const error = new Error(`Invalid VAST tag URL format: ${vastTagUrl}`);\n console.warn(\"[IMA]\", error.message);\n return Promise.reject(error);\n }\n\n if (adPlaying) {\n console.warn(\n \"[IMA] Cannot request new ads while an ad is playing. Call stop() first.\"\n );\n return Promise.reject(\n new Error(\"Ad already playing - cannot request new ads\")\n );\n }\n\n destroyAdsManager();\n\n adsLoadedReject = undefined;\n adsLoadedResolve = undefined;\n\n let currentReject: ((error: Error) => void) | undefined;\n adsLoadedPromise = new Promise<void>((resolve, reject) => {\n adsLoadedResolve = resolve;\n adsLoadedReject = reject;\n currentReject = reject;\n\n setTimeout(() => {\n if (adsLoadedReject) {\n adsLoadedReject(new Error(\"Ad request timeout\"));\n adsLoadedReject = undefined;\n adsLoadedResolve = undefined;\n }\n }, 10000);\n });\n\n try {\n await ensureImaLoaded();\n const google = window.google;\n lastAdTagUrl = vastTagUrl;\n retryAttempts = 0;\n\n if (!adDisplayContainer) {\n console.log(\"[IMA] Creating ad display container\");\n const container = document.createElement(\"div\");\n container.style.position = \"absolute\";\n container.style.left = \"0\";\n container.style.top = \"0\";\n container.style.right = \"0\";\n container.style.bottom = \"0\";\n container.style.display = \"none\";\n container.style.alignItems = \"center\";\n container.style.justifyContent = \"center\";\n container.style.pointerEvents = \"none\";\n container.style.zIndex = \"10\";\n container.style.backgroundColor = \"transparent\";\n container.style.transition =\n \"opacity 0.3s ease-in-out, background-color 0.3s ease-in-out\";\n container.style.opacity = \"0\";\n\n if (!video.parentElement) {\n throw new Error(\"Video element has no parent for ad container\");\n }\n\n video.parentElement.appendChild(container);\n adContainerEl = container;\n\n if (!adVideoElement) {\n adVideoElement = createAdVideoElement();\n adContainerEl.appendChild(adVideoElement);\n console.log(\n \"[IMA] Dedicated ad video element created and added to container\"\n );\n }\n\n adDisplayContainer = new google.ima.AdDisplayContainer(\n container,\n adVideoElement\n );\n\n try {\n adDisplayContainer.initialize();\n console.log(\n \"[IMA] Ad display container initialized with dedicated ad video\"\n );\n } catch (error) {\n console.warn(\n \"[IMA] Failed to initialize ad display container:\",\n error\n );\n }\n }\n\n const videoWidth = video.offsetWidth || video.clientWidth;\n const videoHeight = video.offsetHeight || video.clientHeight;\n\n if (\n !videoWidth ||\n !videoHeight ||\n videoWidth === 0 ||\n videoHeight === 0\n ) {\n const error = new Error(\n `Invalid video dimensions: ${videoWidth}x${videoHeight}. Cannot initialize ads.`\n );\n console.warn(\"[IMA]\", error.message);\n currentReject?.(error);\n adsLoadedReject = undefined;\n adsLoadedResolve = undefined;\n return Promise.reject(error);\n }\n\n if (!adsLoader) {\n console.log(\"[IMA] Creating ads loader\");\n const adsLoaderCls = new google.ima.AdsLoader(adDisplayContainer);\n adsLoader = adsLoaderCls;\n\n adsLoader.addEventListener(\n google.ima.AdsManagerLoadedEvent.Type.ADS_MANAGER_LOADED,\n (evt: any) => {\n console.log(\n \"[IMA] Ads manager loaded - enabling preloading for continuous playback\"\n );\n try {\n const adsRenderingSettings =\n new google.ima.AdsRenderingSettings();\n adsRenderingSettings.enablePreloading = true;\n adsManager = evt.getAdsManager(video, adsRenderingSettings);\n const AdEvent = google.ima.AdEvent.Type;\n const AdErrorEvent = google.ima.AdErrorEvent.Type;\n\n adsManager.addEventListener(\n AdErrorEvent.AD_ERROR,\n (errorEvent: any) => {\n console.error(\"[IMA] Ad error:\", errorEvent.getError());\n\n destroyAdsManager();\n\n adPlaying = false;\n setAdPlayingFlag(false);\n\n if (adContainerEl) {\n adContainerEl.style.opacity = \"0\";\n adContainerEl.style.backgroundColor = \"transparent\";\n setTimeout(() => {\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"none\";\n adContainerEl.style.display = \"none\";\n console.log(\"[IMA] Ad container hidden after error\");\n }\n }, 300);\n }\n\n showContentVideo();\n\n if (adsLoadedReject) {\n adsLoadedReject(new Error(\"Ad playback error\"));\n adsLoadedReject = undefined;\n adsLoadedResolve = undefined;\n }\n\n if (lastAdTagUrl && retryAttempts < maxRetries) {\n const delay =\n backoffBaseMs * Math.pow(2, retryAttempts++);\n console.log(\n `[IMA] Retrying ad request in ${delay}ms (attempt ${retryAttempts})`\n );\n window.setTimeout(() => {\n try {\n makeAdsRequest(google, lastAdTagUrl!);\n } catch {}\n }, delay);\n } else {\n console.log(\n \"[IMA] Max retries reached, emitting ad_error\"\n );\n emit(\"ad_error\");\n\n if (!options?.continueLiveStreamDuringAds) {\n if (video.paused) {\n console.log(\n \"[IMA] Resuming paused video after ad error\"\n );\n video.play()?.catch(() => {});\n }\n }\n }\n }\n );\n\n adsManager.addEventListener(\n AdEvent.CONTENT_PAUSE_REQUESTED,\n () => {\n console.log(\"[IMA] Content pause requested\");\n\n if (!options?.continueLiveStreamDuringAds) {\n video.pause();\n console.log(\"[IMA] Content video paused (VOD mode)\");\n } else {\n console.log(\n \"[IMA] Content video continues in background (Live mode)\"\n );\n }\n\n adPlaying = true;\n setAdPlayingFlag(true);\n emit(\"content_pause\");\n }\n );\n\n adsManager.addEventListener(AdEvent.STARTED, () => {\n console.log(\"[IMA] Ad started - showing ad video\");\n setAdPlayingFlag(true);\n\n hideContentVideo();\n\n if (adVideoElement) {\n adVideoElement.volume = originalMutedState\n ? 0\n : originalVolume;\n adVideoElement.muted = originalMutedState;\n console.log(\n `[IMA] Ad video volume: ${adVideoElement.volume}, muted: ${adVideoElement.muted}`\n );\n }\n\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"auto\";\n adContainerEl.style.display = \"flex\";\n adContainerEl.style.backgroundColor = \"#000\";\n adContainerEl.offsetHeight;\n adContainerEl.style.opacity = \"1\";\n console.log(\"[IMA] Ad container now visible\");\n }\n });\n\n adsManager.addEventListener(\n AdEvent.CONTENT_RESUME_REQUESTED,\n () => {\n console.log(\"[IMA] Content resume requested\");\n adPlaying = false;\n setAdPlayingFlag(false);\n emit(\"content_resume\");\n }\n );\n\n adsManager.addEventListener(AdEvent.ALL_ADS_COMPLETED, () => {\n console.log(\"[IMA] All ads completed - restoring content\");\n adPlaying = false;\n setAdPlayingFlag(false);\n\n if (adContainerEl) {\n adContainerEl.style.opacity = \"0\";\n adContainerEl.style.backgroundColor = \"transparent\";\n setTimeout(() => {\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"none\";\n adContainerEl.style.display = \"none\";\n console.log(\"[IMA] Ad container hidden\");\n }\n }, 300);\n }\n\n showContentVideo();\n\n if (!options?.continueLiveStreamDuringAds && video.paused) {\n console.log(\"[IMA] Resuming content video playback\");\n video.play().catch((e) => {\n console.warn(\"[IMA] Failed to resume content video:\", e);\n });\n }\n\n emit(\"all_ads_completed\");\n });\n\n console.log(\"[IMA] Ads manager event listeners attached\");\n\n if (adsLoadedResolve) {\n adsLoadedResolve();\n adsLoadedResolve = undefined;\n adsLoadedReject = undefined;\n }\n } catch (e) {\n console.error(\"[IMA] Error setting up ads manager:\", e);\n adPlaying = false;\n setAdPlayingFlag(false);\n if (adContainerEl) {\n adContainerEl.style.opacity = \"0\";\n adContainerEl.style.backgroundColor = \"transparent\";\n setTimeout(() => {\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"none\";\n adContainerEl.style.display = \"none\";\n console.log(\n \"[IMA] Ad container hidden after setup error\"\n );\n }\n }, 300);\n }\n showContentVideo();\n\n if (!options?.continueLiveStreamDuringAds) {\n if (video.paused) {\n console.log(\n \"[IMA] Resuming paused video after setup error\"\n );\n video.play().catch(() => {});\n }\n }\n\n if (adsLoadedReject) {\n adsLoadedReject(new Error(\"Failed to setup ads manager\"));\n adsLoadedReject = undefined;\n adsLoadedResolve = undefined;\n }\n emit(\"ad_error\");\n }\n },\n false\n );\n\n adsLoader.addEventListener(\n google.ima.AdErrorEvent.Type.AD_ERROR,\n (adErrorEvent: any) => {\n console.error(\"[IMA] Ads loader error:\", adErrorEvent.getError());\n\n adPlaying = false;\n setAdPlayingFlag(false);\n\n if (adContainerEl) {\n adContainerEl.style.opacity = \"0\";\n adContainerEl.style.backgroundColor = \"transparent\";\n setTimeout(() => {\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"none\";\n adContainerEl.style.display = \"none\";\n console.log(\"[IMA] Ad container hidden after loader error\");\n }\n }, 300);\n }\n\n showContentVideo();\n\n if (!options?.continueLiveStreamDuringAds) {\n if (video.paused) {\n console.log(\"[IMA] Resuming paused video after loader error\");\n video.play().catch(() => {});\n }\n }\n\n if (adsLoadedReject) {\n adsLoadedReject(new Error(\"Ads loader error\"));\n adsLoadedReject = undefined;\n adsLoadedResolve = undefined;\n }\n emit(\"ad_error\");\n },\n false\n );\n }\n\n console.log(\"[IMA] Making ads request\");\n makeAdsRequest(google, vastTagUrl);\n\n return adsLoadedPromise;\n } catch (error) {\n console.error(\"[IMA] Failed to request ads:\", error);\n\n currentReject?.(error as Error);\n adsLoadedReject = undefined;\n adsLoadedResolve = undefined;\n return Promise.reject(error);\n }\n },\n async preloadAds(vastTagUrl: string) {\n if (!vastTagUrl || vastTagUrl.trim() === \"\") {\n return Promise.resolve();\n }\n\n if (preloadedVast.has(vastTagUrl)) {\n return Promise.resolve();\n }\n\n const inflight = preloadingVast.get(vastTagUrl);\n if (inflight) {\n return inflight;\n }\n\n const preloadPromise = fetchVastDocument(vastTagUrl)\n .then((xml) => {\n preloadedVast.set(vastTagUrl, xml);\n console.log(\"[IMA] Cached VAST response for preloading:\", vastTagUrl);\n })\n .catch((error) => {\n console.warn(\"[IMA] Failed to preload VAST response:\", error);\n preloadedVast.delete(vastTagUrl);\n })\n .finally(() => {\n preloadingVast.delete(vastTagUrl);\n });\n\n preloadingVast.set(vastTagUrl, preloadPromise);\n return preloadPromise;\n },\n hasPreloadedAd(vastTagUrl: string) {\n return preloadedVast.has(vastTagUrl);\n },\n async play() {\n if (!window.google?.ima || !adDisplayContainer) {\n console.warn(\n \"[IMA] Cannot play ad: IMA SDK or ad container not available\"\n );\n return Promise.reject(new Error(\"IMA SDK not available\"));\n }\n\n if (!adsManager) {\n console.warn(\"[IMA] Cannot play ad: No ads manager available\");\n return Promise.reject(new Error(\"No ads manager\"));\n }\n\n try {\n const width = video.clientWidth || 640;\n const height = video.clientHeight || 360;\n\n console.log(`[IMA] Initializing ads manager (${width}x${height})`);\n adsManager.init(width, height, window.google.ima.ViewMode.NORMAL);\n\n adPlaying = true;\n\n const adVolume = originalMutedState ? 0 : originalVolume;\n if (adVideoElement) {\n adVideoElement.volume = adVolume;\n adVideoElement.muted = originalMutedState;\n console.log(\n `[IMA] Set dedicated ad video volume to ${adVolume}, muted: ${originalMutedState}`\n );\n }\n\n try {\n adsManager.setVolume(adVolume);\n console.log(`[IMA] Set IMA manager volume to ${adVolume}`);\n } catch (error) {\n console.warn(\"[IMA] Failed to set IMA manager volume:\", error);\n }\n\n console.log(\"[IMA] Starting ad playback\");\n adsManager.start();\n\n return Promise.resolve();\n } catch (error) {\n console.error(\"[IMA] Error starting ad playback:\", error);\n adPlaying = false;\n setAdPlayingFlag(false);\n\n if (!options?.continueLiveStreamDuringAds) {\n video.play()?.catch(() => {});\n }\n return Promise.reject(error);\n }\n },\n async stop() {\n console.log(\"[IMA] Stopping ad playback\");\n adPlaying = false;\n setAdPlayingFlag(false);\n\n if (adContainerEl) {\n adContainerEl.style.opacity = \"0\";\n adContainerEl.style.backgroundColor = \"transparent\";\n setTimeout(() => {\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"none\";\n adContainerEl.style.display = \"none\";\n console.log(\"[IMA] Ad container hidden after stop\");\n }\n }, 300);\n }\n\n showContentVideo();\n\n try {\n adsManager?.stop?.();\n } catch {}\n\n destroyAdsManager();\n },\n destroy() {\n destroyAdsManager();\n\n adPlaying = false;\n setAdPlayingFlag(false);\n\n if (adContainerEl) {\n adContainerEl.style.opacity = \"0\";\n adContainerEl.style.backgroundColor = \"transparent\";\n setTimeout(() => {\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"none\";\n adContainerEl.style.display = \"none\";\n\n if (adContainerEl.parentElement) {\n adContainerEl.parentElement.removeChild(adContainerEl);\n }\n\n adContainerEl = undefined;\n adVideoElement = undefined;\n }\n }, 300);\n }\n\n showContentVideo();\n\n try {\n adsLoader?.destroy?.();\n } catch {}\n\n adDisplayContainer = undefined;\n adsLoader = undefined;\n contentVideoHidden = false;\n preloadedVast.clear();\n preloadingVast.clear();\n },\n isAdPlaying() {\n return adPlaying;\n },\n resize(width: number, height: number) {\n if (!adsManager || !window.google?.ima) {\n console.warn(\n \"[IMA] Cannot resize: No ads manager or IMA SDK available\"\n );\n return;\n }\n\n try {\n console.log(`[IMA] Resizing ads manager to ${width}x${height}`);\n adsManager.resize(width, height, window.google.ima.ViewMode.NORMAL);\n } catch (error) {\n console.warn(\"[IMA] Error resizing ads manager:\", error);\n }\n },\n on(event: string, listener: (payload?: any) => void) {\n if (!listeners.has(event)) listeners.set(event, new Set());\n listeners.get(event)!.add(listener);\n },\n off(event: string, listener: (payload?: any) => void) {\n listeners.get(event)?.delete(listener);\n },\n updateOriginalMutedState(muted: boolean, volume?: number) {\n const nextVolume =\n typeof volume === \"number\" && !Number.isNaN(volume)\n ? Math.max(0, Math.min(1, volume))\n : originalVolume;\n console.log(\n `[IMA] updateOriginalMutedState called: { muted: ${originalMutedState} -> ${muted}, volume: ${originalVolume} -> ${nextVolume} }`\n );\n originalMutedState = muted;\n originalVolume = nextVolume;\n },\n getOriginalMutedState() {\n return originalMutedState;\n },\n getOriginalVolume() {\n return originalVolume;\n },\n setAdVolume(volume: number) {\n const clampedVolume = Math.max(0, Math.min(1, volume));\n\n if (adVideoElement && adPlaying) {\n adVideoElement.volume = clampedVolume;\n adVideoElement.muted = clampedVolume === 0;\n console.log(\n `[IMA] Set dedicated ad video volume to ${clampedVolume}, muted: ${\n clampedVolume === 0\n }`\n );\n }\n\n if (adsManager && adPlaying) {\n try {\n adsManager.setVolume(clampedVolume);\n } catch (error) {\n console.warn(\"[IMA] Failed to set IMA manager volume:\", error);\n }\n }\n },\n getAdVolume(): number {\n if (adVideoElement && adPlaying) {\n return adVideoElement.volume;\n }\n\n if (adsManager && adPlaying) {\n try {\n return adsManager.getVolume();\n } catch (error) {\n console.warn(\"[IMA] Failed to get ad volume:\", error);\n return 1;\n }\n }\n return 1;\n },\n showPlaceholder() {\n ensurePlaceholderContainer();\n if (adContainerEl) {\n adContainerEl.style.display = \"flex\";\n adContainerEl.style.backgroundColor = \"#000\";\n // Force reflow\n adContainerEl.offsetHeight;\n adContainerEl.style.opacity = \"1\";\n adContainerEl.style.pointerEvents = \"auto\";\n }\n },\n hidePlaceholder() {\n if (adContainerEl) {\n adContainerEl.style.opacity = \"0\";\n adContainerEl.style.backgroundColor = \"transparent\";\n setTimeout(() => {\n if (adContainerEl) {\n adContainerEl.style.display = \"none\";\n adContainerEl.style.pointerEvents = \"none\";\n }\n }, 300);\n }\n },\n };\n}\n","interface NavigatorUAData {\n platform?: string;\n brands?: Array<{ brand: string; version: string }>;\n mobile?: boolean;\n}\n\ndeclare global {\n interface Navigator {\n userAgentData?: NavigatorUAData;\n }\n}\n\nexport interface BrowserInfo {\n name: string;\n version: string;\n majorVersion: number;\n isSmartTV: boolean;\n isLegacyTV: boolean;\n platform: string;\n supportsIMA: boolean;\n supportsModernJS: boolean;\n recommendedAdPlayer: 'ima' | 'hls';\n}\n\nfunction getChromeVersion(ua: string): number {\n const match = ua.match(/Chrome\\/(\\d+)/);\n return match && match[1] ? parseInt(match[1], 10) : 0;\n}\n\nfunction getWebKitVersion(ua: string): number {\n const match = ua.match(/AppleWebKit\\/(\\d+)/);\n return match && match[1] ? parseInt(match[1], 10) : 0;\n}\n\nfunction getPlatform(): string {\n if ('userAgentData' in navigator && navigator.userAgentData?.platform) {\n return navigator.userAgentData.platform;\n }\n\n const ua = navigator.userAgent;\n if (/Mac|iPhone|iPad|iPod/i.test(ua)) {\n return /iPhone|iPad|iPod/i.test(ua) ? 'iPhone' : 'MacIntel';\n }\n if (/Win/i.test(ua)) {\n return 'Win32';\n }\n if (/Linux/i.test(ua)) {\n return /Android/i.test(ua) ? 'Linux armv8l' : 'Linux x86_64';\n }\n if (/CrOS/i.test(ua)) {\n return 'CrOS';\n }\n\n // eslint-disable-next-line deprecation/deprecation\n return (navigator as any).platform || 'Unknown';\n}\n\nexport function detectBrowser(): BrowserInfo {\n const ua = navigator.userAgent;\n const platform = getPlatform();\n\n let name = 'Unknown';\n let version = '0';\n let majorVersion = 0;\n let isSmartTV = false;\n let isLegacyTV = false;\n let supportsIMA = true;\n let supportsModernJS = true;\n let recommendedAdPlayer: 'ima' | 'hls' = 'ima';\n\n if (/Web0S|webOS/i.test(ua)) {\n name = 'LG WebOS';\n isSmartTV = true;\n const match = ua.match(/Web0S[/\\s]*([\\d.]+)/i);\n version = match && match[1] ? match[1] : 'Unknown';\n if (version !== 'Unknown') {\n const parts = version.split('.');\n majorVersion = parts[0] ? parseInt(parts[0], 10) : 0;\n }\n } else if (/Tizen/i.test(ua)) {\n name = 'Samsung Tizen';\n isSmartTV = true;\n const match = ua.match(/Tizen[/\\s]*([\\d.]+)/i);\n version = match && match[1] ? match[1] : 'Unknown';\n if (version !== 'Unknown') {\n const parts = version.split('.');\n majorVersion = parts[0] ? parseInt(parts[0], 10) : 0;\n }\n } else if (/SMART-TV|SmartTV/i.test(ua)) {\n name = 'Smart TV';\n isSmartTV = true;\n } else if (/NetCast/i.test(ua)) {\n name = 'LG NetCast';\n isSmartTV = true;\n isLegacyTV = true;\n } else if (/BRAVIA/i.test(ua)) {\n name = 'Sony BRAVIA';\n isSmartTV = true;\n }\n\n const chromeVersion = getChromeVersion(ua);\n const webkitVersion = getWebKitVersion(ua);\n\n if (chromeVersion > 0) {\n if (!isSmartTV) {\n name = 'Chrome';\n version = chromeVersion.toString();\n majorVersion = chromeVersion;\n }\n\n if (chromeVersion < 50) {\n supportsIMA = false;\n supportsModernJS = false;\n isLegacyTV = true;\n recommendedAdPlayer = 'hls';\n }\n }\n\n if (webkitVersion > 0 && webkitVersion < 600) {\n supportsModernJS = false;\n if (isSmartTV) {\n isLegacyTV = true;\n supportsIMA = false;\n recommendedAdPlayer = 'hls';\n }\n }\n\n if (typeof Promise === 'undefined' ||\n typeof Map === 'undefined' ||\n typeof Set === 'undefined') {\n supportsModernJS = false;\n supportsIMA = false;\n recommendedAdPlayer = 'hls';\n }\n\n if (typeof URLSearchParams === 'undefined') {\n supportsModernJS = false;\n }\n\n return {\n name,\n version,\n majorVersion,\n isSmartTV,\n isLegacyTV,\n platform,\n supportsIMA,\n supportsModernJS,\n recommendedAdPlayer,\n };\n}\n\nexport function supportsGoogleIMA(): boolean {\n const browser = detectBrowser();\n\n if (browser.isLegacyTV) {\n return false;\n }\n\n if (typeof document === 'undefined' ||\n typeof document.createElement !== 'function') {\n return false;\n }\n\n try {\n const video = document.createElement('video');\n if (!video) {\n return false;\n }\n } catch (e) {\n return false;\n }\n\n if (typeof Promise === 'undefined') {\n return false;\n }\n\n return browser.supportsIMA;\n}\n\nexport function getRecommendedAdPlayer(): 'ima' | 'hls' {\n const browser = detectBrowser();\n return browser.recommendedAdPlayer;\n}\n\nexport function supportsModernJS(): boolean {\n try {\n return (\n typeof Promise !== 'undefined' &&\n typeof Map !== 'undefined' &&\n typeof Set !== 'undefined' &&\n typeof Array.from !== 'undefined' &&\n typeof Object.assign !== 'undefined' &&\n typeof Array.prototype.forEach !== 'undefined' &&\n typeof String.prototype.includes !== 'undefined'\n );\n } catch (e) {\n return false;\n }\n}\n\nexport function logBrowserInfo(debug: boolean = false): void {\n if (!debug) return;\n\n const browser = detectBrowser();\n const imaSupport = supportsGoogleIMA();\n\n console.log('[StormcloudVideoPlayer] Browser Compatibility Info:', {\n browser: `${browser.name} ${browser.version}`,\n platform: browser.platform,\n isSmartTV: browser.isSmartTV,\n isLegacyTV: browser.isLegacyTV,\n supportsIMA: imaSupport,\n supportsModernJS: browser.supportsModernJS,\n recommendedAdPlayer: browser.recommendedAdPlayer,\n userAgent: navigator.userAgent,\n });\n}\n\nexport function getBrowserConfigOverrides(): {\n adPlayerType?: 'ima' | 'hls';\n allowNativeHls?: boolean;\n} {\n const browser = detectBrowser();\n const overrides: any = {};\n\n if (browser.isLegacyTV || !browser.supportsIMA) {\n overrides.adPlayerType = 'hls';\n }\n\n if (browser.isSmartTV) {\n overrides.allowNativeHls = true;\n }\n\n return overrides;\n}\n\nexport function supportsFeature(feature: string): boolean {\n switch (feature) {\n case 'ima':\n return supportsGoogleIMA();\n case 'urlsearchparams':\n return typeof URLSearchParams !== 'undefined';\n case 'textencoder':\n return typeof TextEncoder !== 'undefined';\n case 'promises':\n return typeof Promise !== 'undefined';\n case 'fetch':\n return typeof fetch !== 'undefined';\n case 'crypto':\n return typeof crypto !== 'undefined' && typeof crypto.subtle !== 'undefined';\n default:\n return false;\n }\n}\n\n"],"mappings":"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","names":[]}
1
+ {"version":3,"sources":["../../src/sdk/ima.ts","../../src/utils/browserCompat.ts"],"sourcesContent":["import type { ImaController } from \"../types\";\nimport { supportsGoogleIMA } from \"../utils/browserCompat\";\n\ndeclare global {\n interface Window {\n google?: any;\n }\n}\n\nexport function createImaController(\n video: HTMLVideoElement,\n options?: { continueLiveStreamDuringAds?: boolean }\n): ImaController {\n let adPlaying = false;\n let contentVideoHidden = false;\n let originalMutedState = false;\n let originalVolume =\n typeof video.volume === \"number\" && !Number.isNaN(video.volume)\n ? Math.max(0, Math.min(1, video.volume))\n : 1;\n const listeners = new Map<string, Set<(payload?: any) => void>>();\n const preloadedVast = new Map<string, string>();\n const preloadingVast = new Map<string, Promise<void>>();\n let adVideoElement: HTMLVideoElement | undefined;\n\n function setAdPlayingFlag(isPlaying: boolean): void {\n if (isPlaying) {\n video.dataset.stormcloudAdPlaying = \"true\";\n } else {\n delete video.dataset.stormcloudAdPlaying;\n }\n }\n\n function hideContentVideo(): void {\n if (!contentVideoHidden) {\n video.style.transition = \"opacity 0.3s ease-in-out\";\n video.style.opacity = \"0\";\n setTimeout(() => {\n video.style.visibility = \"hidden\";\n }, 300);\n video.muted = true;\n video.volume = 0;\n contentVideoHidden = true;\n console.log(\"[IMA] Content video hidden and muted\");\n }\n }\n\n function showContentVideo(): void {\n if (contentVideoHidden) {\n video.style.visibility = \"visible\";\n video.style.transition = \"opacity 0.3s ease-in-out\";\n video.offsetHeight;\n video.style.opacity = \"1\";\n video.muted = originalMutedState;\n video.volume = originalVolume;\n contentVideoHidden = false;\n console.log(\n `[IMA] Content video restored (muted: ${originalMutedState}, volume: ${originalVolume})`\n );\n }\n }\n\n function createAdVideoElement(): HTMLVideoElement {\n const adVideo = document.createElement(\"video\");\n adVideo.style.position = \"absolute\";\n adVideo.style.top = \"0\";\n adVideo.style.left = \"0\";\n adVideo.style.width = \"100%\";\n adVideo.style.height = \"100%\";\n adVideo.style.objectFit = \"contain\";\n adVideo.style.backgroundColor = \"transparent\";\n adVideo.style.zIndex = \"15\";\n adVideo.playsInline = true;\n adVideo.muted = false;\n adVideo.volume = originalMutedState ? 0 : originalVolume;\n\n adVideo.style.opacity = \"0\";\n adVideo.addEventListener(\n \"canplay\",\n () => {\n adVideo.style.opacity = \"1\";\n console.log(\"[IMA] Ad video ready to play\");\n },\n { once: true }\n );\n\n console.log(\n `[IMA] Created dedicated ad video element with volume: ${adVideo.volume}, muted: ${adVideo.muted}`\n );\n return adVideo;\n }\n\n function emit(event: string, payload?: any): void {\n const set = listeners.get(event);\n if (!set) return;\n for (const fn of Array.from(set)) {\n try {\n fn(payload);\n } catch {}\n }\n }\n\n function ensureImaLoaded(): Promise<void> {\n if (!supportsGoogleIMA()) {\n console.warn(\n \"[IMA] Google IMA SDK is not supported on this browser. Please use HLS ad player instead.\"\n );\n return Promise.reject(\n new Error(\"Google IMA SDK not supported on this browser\")\n );\n }\n\n try {\n const frameEl = window.frameElement as HTMLIFrameElement | null;\n const sandboxAttr = frameEl?.getAttribute?.(\"sandbox\") || \"\";\n if (sandboxAttr) {\n const tokens = new Set(\n sandboxAttr\n .split(/\\s+/)\n .map((t) => t.trim())\n .filter((t) => t.length > 0)\n );\n const allowsScripts = tokens.has(\"allow-scripts\");\n if (!allowsScripts) {\n // eslint-disable-next-line no-console\n console.error(\n \"StormcloudVideoPlayer: The host page is inside a sandboxed iframe without 'allow-scripts'. Google IMA cannot run ads within sandboxed frames. Remove the sandbox attribute or include 'allow-scripts allow-same-origin'.\"\n );\n }\n }\n } catch {}\n\n if (typeof window !== \"undefined\" && window.google?.ima)\n return Promise.resolve();\n const existing = document.querySelector(\n 'script[data-ima=\"true\"]'\n ) as HTMLScriptElement | null;\n if (existing) {\n if (window.google?.ima) {\n return Promise.resolve();\n }\n return new Promise((resolve, reject) => {\n const timeout = setTimeout(() => {\n reject(new Error(\"IMA SDK load timeout\"));\n }, 10000);\n existing.addEventListener(\"load\", () => {\n clearTimeout(timeout);\n resolve();\n });\n existing.addEventListener(\"error\", () => {\n clearTimeout(timeout);\n reject(new Error(\"IMA SDK load failed\"));\n });\n });\n }\n return new Promise((resolve, reject) => {\n const script = document.createElement(\"script\");\n script.src = \"https://imasdk.googleapis.com/js/sdkloader/ima3.js\";\n script.async = true;\n script.defer = true;\n script.setAttribute(\"data-ima\", \"true\");\n script.onload = () => resolve();\n script.onerror = () => reject(new Error(\"IMA SDK load failed\"));\n document.head.appendChild(script);\n });\n }\n\n let adsManager: any | undefined;\n let adsLoader: any | undefined;\n let adDisplayContainer: any | undefined;\n let adContainerEl: HTMLDivElement | undefined;\n let lastAdTagUrl: string | undefined;\n let retryAttempts = 0;\n const maxRetries = 2;\n const backoffBaseMs = 500;\n let adsLoadedPromise: Promise<void> | undefined;\n let adsLoadedResolve: (() => void) | undefined;\n let adsLoadedReject: ((error: Error) => void) | undefined;\n\n function makeAdsRequest(google: any, vastTagUrl: string) {\n console.log(\"[IMA] πŸ“‹ === makeAdsRequest() - Building IMA request ===\");\n \n const adsRequest = new google.ima.AdsRequest();\n const preloadedResponse = preloadedVast.get(vastTagUrl);\n\n if (preloadedResponse) {\n adsRequest.adsResponse = preloadedResponse;\n console.log(\n \"[IMA] ⚑ Using preloaded VAST response for immediate ad request\"\n );\n } else {\n adsRequest.adTagUrl = vastTagUrl;\n console.log(\"[IMA] 🌐 Will fetch VAST from URL:\", vastTagUrl);\n }\n\n const videoWidth = video.offsetWidth || video.clientWidth || 640;\n const videoHeight = video.offsetHeight || video.clientHeight || 360;\n\n adsRequest.linearAdSlotWidth = videoWidth;\n adsRequest.linearAdSlotHeight = videoHeight;\n adsRequest.nonLinearAdSlotWidth = videoWidth;\n adsRequest.nonLinearAdSlotHeight = videoHeight;\n\n if (typeof adsRequest.setAdWillAutoPlay === \"function\") {\n try {\n const willAutoPlay = !video.paused || video.autoplay;\n adsRequest.setAdWillAutoPlay(willAutoPlay);\n console.log(`[IMA] Ad will autoplay: ${willAutoPlay}`);\n } catch (error) {\n console.warn(\"[IMA] Failed to call setAdWillAutoPlay:\", error);\n }\n }\n\n if (typeof adsRequest.setAdWillPlayMuted === \"function\") {\n try {\n const willPlayMuted = video.muted || video.volume === 0;\n adsRequest.setAdWillPlayMuted(willPlayMuted);\n console.log(`[IMA] Ad will play muted: ${willPlayMuted}`);\n } catch (error) {\n console.warn(\"[IMA] Failed to call setAdWillPlayMuted:\", error);\n }\n }\n\n adsRequest.vastLoadTimeout = 5000;\n\n console.log(`[IMA] πŸ“ Ads request dimensions: ${videoWidth}x${videoHeight}`);\n console.log(\"[IMA] ⏱️ VAST load timeout: 5000ms\");\n console.log(\"[IMA] πŸš€ Calling adsLoader.requestAds()...\");\n\n adsLoader.requestAds(adsRequest);\n\n console.log(\"[IMA] ⏳ Waiting for ADS_MANAGER_LOADED or AD_ERROR event...\");\n\n if (preloadedResponse) {\n preloadedVast.delete(vastTagUrl);\n }\n }\n\n function ensurePlaceholderContainer(): void {\n if (adContainerEl) {\n return;\n }\n\n const container = document.createElement(\"div\");\n container.style.position = \"absolute\";\n container.style.left = \"0\";\n container.style.top = \"0\";\n container.style.right = \"0\";\n container.style.bottom = \"0\";\n container.style.display = \"none\";\n container.style.alignItems = \"center\";\n container.style.justifyContent = \"center\";\n container.style.pointerEvents = \"none\";\n container.style.zIndex = \"10\";\n container.style.backgroundColor = \"transparent\";\n container.style.transition =\n \"opacity 0.3s ease-in-out, background-color 0.3s ease-in-out\";\n container.style.opacity = \"0\";\n\n video.parentElement?.appendChild(container);\n adContainerEl = container;\n }\n\n async function fetchVastDocument(vastTagUrl: string): Promise<string> {\n const response = await fetch(vastTagUrl, { mode: \"cors\" });\n if (!response.ok) {\n throw new Error(`Failed to preload VAST: ${response.status}`);\n }\n return response.text();\n }\n\n function destroyAdsManager() {\n if (adsManager) {\n try {\n console.log(\"[IMA] Destroying existing ads manager\");\n adsManager.destroy();\n } catch (error) {\n console.warn(\"[IMA] Error destroying ads manager:\", error);\n }\n adsManager = undefined;\n }\n\n if (adVideoElement) {\n adVideoElement.style.opacity = \"0\";\n }\n }\n\n return {\n initialize() {\n ensureImaLoaded()\n .then(() => {\n const google = window.google;\n ensurePlaceholderContainer();\n\n if (!adDisplayContainer && adContainerEl) {\n if (!adVideoElement) {\n adVideoElement = createAdVideoElement();\n adContainerEl.appendChild(adVideoElement);\n console.log(\n \"[IMA] Dedicated ad video element added to container\"\n );\n }\n\n adDisplayContainer = new google.ima.AdDisplayContainer(\n adContainerEl,\n adVideoElement\n );\n try {\n adDisplayContainer.initialize?.();\n console.log(\n \"[IMA] AdDisplayContainer initialized with dedicated ad video\"\n );\n } catch {}\n }\n })\n .catch(() => {});\n },\n async requestAds(vastTagUrl: string) {\n console.log(\"[IMA] πŸ“‘ === requestAds() called ===\");\n console.log(\"[IMA] VAST URL:\", vastTagUrl);\n console.log(\"[IMA] This will fetch the ad from the server - no visual change yet\");\n\n if (!vastTagUrl || vastTagUrl.trim() === \"\") {\n const error = new Error(\"VAST tag URL is empty or undefined\");\n console.warn(\"[IMA] ❌\", error.message);\n return Promise.reject(error);\n }\n\n try {\n new URL(vastTagUrl);\n } catch (e) {\n const error = new Error(`Invalid VAST tag URL format: ${vastTagUrl}`);\n console.warn(\"[IMA] ❌\", error.message);\n return Promise.reject(error);\n }\n\n if (adPlaying) {\n console.warn(\n \"[IMA] ⚠️ Cannot request new ads while an ad is playing. Call stop() first.\"\n );\n return Promise.reject(\n new Error(\"Ad already playing - cannot request new ads\")\n );\n }\n\n destroyAdsManager();\n\n adsLoadedReject = undefined;\n adsLoadedResolve = undefined;\n\n let currentReject: ((error: Error) => void) | undefined;\n adsLoadedPromise = new Promise<void>((resolve, reject) => {\n adsLoadedResolve = resolve;\n adsLoadedReject = reject;\n currentReject = reject;\n\n setTimeout(() => {\n if (adsLoadedReject) {\n adsLoadedReject(new Error(\"Ad request timeout\"));\n adsLoadedReject = undefined;\n adsLoadedResolve = undefined;\n }\n }, 10000);\n });\n\n try {\n await ensureImaLoaded();\n const google = window.google;\n lastAdTagUrl = vastTagUrl;\n retryAttempts = 0;\n\n if (!adDisplayContainer) {\n console.log(\"[IMA] Creating ad display container\");\n const container = document.createElement(\"div\");\n container.style.position = \"absolute\";\n container.style.left = \"0\";\n container.style.top = \"0\";\n container.style.right = \"0\";\n container.style.bottom = \"0\";\n container.style.display = \"none\";\n container.style.alignItems = \"center\";\n container.style.justifyContent = \"center\";\n container.style.pointerEvents = \"none\";\n container.style.zIndex = \"10\";\n container.style.backgroundColor = \"transparent\";\n container.style.transition =\n \"opacity 0.3s ease-in-out, background-color 0.3s ease-in-out\";\n container.style.opacity = \"0\";\n\n if (!video.parentElement) {\n throw new Error(\"Video element has no parent for ad container\");\n }\n\n video.parentElement.appendChild(container);\n adContainerEl = container;\n\n if (!adVideoElement) {\n adVideoElement = createAdVideoElement();\n adContainerEl.appendChild(adVideoElement);\n console.log(\n \"[IMA] Dedicated ad video element created and added to container\"\n );\n }\n\n adDisplayContainer = new google.ima.AdDisplayContainer(\n container,\n adVideoElement\n );\n\n try {\n adDisplayContainer.initialize();\n console.log(\n \"[IMA] Ad display container initialized with dedicated ad video\"\n );\n } catch (error) {\n console.warn(\n \"[IMA] Failed to initialize ad display container:\",\n error\n );\n }\n }\n\n const videoWidth = video.offsetWidth || video.clientWidth;\n const videoHeight = video.offsetHeight || video.clientHeight;\n\n if (\n !videoWidth ||\n !videoHeight ||\n videoWidth === 0 ||\n videoHeight === 0\n ) {\n const error = new Error(\n `Invalid video dimensions: ${videoWidth}x${videoHeight}. Cannot initialize ads.`\n );\n console.warn(\"[IMA]\", error.message);\n currentReject?.(error);\n adsLoadedReject = undefined;\n adsLoadedResolve = undefined;\n return Promise.reject(error);\n }\n\n if (!adsLoader) {\n console.log(\"[IMA] Creating ads loader\");\n const adsLoaderCls = new google.ima.AdsLoader(adDisplayContainer);\n adsLoader = adsLoaderCls;\n\n adsLoader.addEventListener(\n google.ima.AdsManagerLoadedEvent.Type.ADS_MANAGER_LOADED,\n (evt: any) => {\n console.log(\"[IMA] βœ… ADS_MANAGER_LOADED - Ads fetched successfully!\");\n console.log(\"[IMA] Setting up ads manager with preloading enabled\");\n console.log(\"[IMA] ========================================\");\n console.log(\"[IMA] EXPECTED EVENT FLOW:\");\n console.log(\"[IMA] 1. requestAds() β†’ fetch VAST\");\n console.log(\"[IMA] 2. ADS_MANAGER_LOADED β†’ ads ready\");\n console.log(\"[IMA] 3. play() β†’ start playback\");\n console.log(\"[IMA] 4. CONTENT_PAUSE_REQUESTED β†’ show ad layer ✨\");\n console.log(\"[IMA] 5. STARTED β†’ ad is playing\");\n console.log(\"[IMA] 6. CONTENT_RESUME_REQUESTED β†’ ad done\");\n console.log(\"[IMA] 7. ALL_ADS_COMPLETED β†’ hide ad layer\");\n console.log(\"[IMA] ========================================\");\n try {\n const adsRenderingSettings =\n new google.ima.AdsRenderingSettings();\n adsRenderingSettings.enablePreloading = true;\n adsManager = evt.getAdsManager(video, adsRenderingSettings);\n const AdEvent = google.ima.AdEvent.Type;\n const AdErrorEvent = google.ima.AdErrorEvent.Type;\n\n console.log(\"[IMA] ========== IMA EVENT LOGGING ENABLED ==========\");\n console.log(\"[IMA] All IMA SDK events will be logged below\");\n\n // Log ALL IMA events for comprehensive debugging\n const allAdEvents = [\n 'AD_BREAK_READY',\n 'AD_METADATA',\n 'ALL_ADS_COMPLETED',\n 'CLICK',\n 'COMPLETE',\n 'CONTENT_PAUSE_REQUESTED',\n 'CONTENT_RESUME_REQUESTED',\n 'DURATION_CHANGE',\n 'FIRST_QUARTILE',\n 'IMPRESSION',\n 'INTERACTION',\n 'LINEAR_CHANGED',\n 'LOADED',\n 'LOG',\n 'MIDPOINT',\n 'PAUSED',\n 'RESUMED',\n 'SKIPPABLE_STATE_CHANGED',\n 'SKIPPED',\n 'STARTED',\n 'THIRD_QUARTILE',\n 'USER_CLOSE',\n 'VOLUME_CHANGED',\n 'VOLUME_MUTED',\n ];\n\n allAdEvents.forEach((eventType) => {\n if (AdEvent[eventType]) {\n adsManager.addEventListener(AdEvent[eventType], (e: any) => {\n const ad = e.getAd?.();\n const adData = ad ? {\n adId: ad.getAdId?.(),\n title: ad.getTitle?.(),\n duration: ad.getDuration?.(),\n isLinear: ad.isLinear?.(),\n contentType: ad.getContentType?.(),\n } : null;\n console.log(`[IMA EVENT] ${eventType}`, {\n eventType,\n timestamp: new Date().toISOString(),\n adData,\n });\n });\n }\n });\n\n console.log(\"[IMA] ========== EVENT LISTENERS ATTACHED ==========\");\n\n adsManager.addEventListener(\n AdErrorEvent.AD_ERROR,\n (errorEvent: any) => {\n const error = errorEvent.getError();\n console.error(\"[IMA] ❌ AD_ERROR Event:\", {\n message: error.getMessage?.(),\n errorCode: error.getErrorCode?.(),\n type: error.getType?.(),\n vastErrorCode: error.getVastErrorCode?.(),\n innerError: error.getInnerError?.(),\n });\n\n destroyAdsManager();\n\n adPlaying = false;\n setAdPlayingFlag(false);\n\n if (adContainerEl) {\n adContainerEl.style.opacity = \"0\";\n adContainerEl.style.backgroundColor = \"transparent\";\n setTimeout(() => {\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"none\";\n adContainerEl.style.display = \"none\";\n console.log(\"[IMA] Ad container hidden after error\");\n }\n }, 300);\n }\n\n showContentVideo();\n\n if (adsLoadedReject) {\n adsLoadedReject(new Error(\"Ad playback error\"));\n adsLoadedReject = undefined;\n adsLoadedResolve = undefined;\n }\n\n if (lastAdTagUrl && retryAttempts < maxRetries) {\n const delay =\n backoffBaseMs * Math.pow(2, retryAttempts++);\n console.log(\n `[IMA] Retrying ad request in ${delay}ms (attempt ${retryAttempts})`\n );\n window.setTimeout(() => {\n try {\n makeAdsRequest(google, lastAdTagUrl!);\n } catch {}\n }, delay);\n } else {\n console.log(\n \"[IMA] Max retries reached, emitting ad_error\"\n );\n emit(\"ad_error\");\n\n if (!options?.continueLiveStreamDuringAds) {\n if (video.paused) {\n console.log(\n \"[IMA] Resuming paused video after ad error\"\n );\n video.play()?.catch(() => {});\n }\n }\n }\n }\n );\n\n adsManager.addEventListener(\n AdEvent.CONTENT_PAUSE_REQUESTED,\n () => {\n console.log(\"[IMA] βœ… CONTENT_PAUSE_REQUESTED - Ad is ready to play!\");\n console.log(\"[IMA] This is the event that triggers the ad layer to appear\");\n\n if (!options?.continueLiveStreamDuringAds) {\n video.pause();\n console.log(\"[IMA] Content video paused (VOD mode)\");\n } else {\n console.log(\n \"[IMA] Content video continues in background (Live mode)\"\n );\n }\n\n hideContentVideo();\n\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"auto\";\n adContainerEl.style.display = \"flex\";\n adContainerEl.style.backgroundColor = \"#000\";\n adContainerEl.offsetHeight;\n adContainerEl.style.opacity = \"1\";\n console.log(\"[IMA] ✨ Ad container NOW VISIBLE (after content pause)\");\n }\n\n adPlaying = true;\n setAdPlayingFlag(true);\n \n console.log(\"[IMA] Emitting 'content_pause' event to player\");\n emit(\"content_pause\");\n }\n );\n\n adsManager.addEventListener(AdEvent.STARTED, () => {\n console.log(\"[IMA] ▢️ STARTED - Ad playback has begun\");\n setAdPlayingFlag(true);\n\n hideContentVideo();\n\n if (adVideoElement) {\n adVideoElement.volume = originalMutedState\n ? 0\n : originalVolume;\n adVideoElement.muted = originalMutedState;\n console.log(\n `[IMA] Ad video volume: ${adVideoElement.volume}, muted: ${adVideoElement.muted}`\n );\n }\n\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"auto\";\n adContainerEl.style.display = \"flex\";\n adContainerEl.style.backgroundColor = \"#000\";\n adContainerEl.offsetHeight;\n adContainerEl.style.opacity = \"1\";\n console.log(\"[IMA] Ad container now visible (STARTED event)\");\n }\n });\n\n adsManager.addEventListener(\n AdEvent.CONTENT_RESUME_REQUESTED,\n () => {\n console.log(\"[IMA] ⏸️ CONTENT_RESUME_REQUESTED - Single ad completed\");\n adPlaying = false;\n setAdPlayingFlag(false);\n console.log(\"[IMA] Emitting 'content_resume' event to player\");\n emit(\"content_resume\");\n }\n );\n\n adsManager.addEventListener(AdEvent.ALL_ADS_COMPLETED, () => {\n console.log(\"[IMA] 🏁 ALL_ADS_COMPLETED - All ads in break finished\");\n adPlaying = false;\n setAdPlayingFlag(false);\n\n if (adContainerEl) {\n adContainerEl.style.opacity = \"0\";\n adContainerEl.style.backgroundColor = \"transparent\";\n setTimeout(() => {\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"none\";\n adContainerEl.style.display = \"none\";\n console.log(\"[IMA] πŸ™ˆ Ad container hidden (ALL_ADS_COMPLETED)\");\n }\n }, 300);\n }\n\n showContentVideo();\n\n if (!options?.continueLiveStreamDuringAds && video.paused) {\n console.log(\"[IMA] Resuming content video playback\");\n video.play().catch((e) => {\n console.warn(\"[IMA] Failed to resume content video:\", e);\n });\n }\n\n console.log(\"[IMA] Emitting 'all_ads_completed' event to player\");\n emit(\"all_ads_completed\");\n });\n\n console.log(\"[IMA] Ads manager event listeners attached\");\n\n if (adsLoadedResolve) {\n adsLoadedResolve();\n adsLoadedResolve = undefined;\n adsLoadedReject = undefined;\n }\n } catch (e) {\n console.error(\"[IMA] Error setting up ads manager:\", e);\n adPlaying = false;\n setAdPlayingFlag(false);\n if (adContainerEl) {\n adContainerEl.style.opacity = \"0\";\n adContainerEl.style.backgroundColor = \"transparent\";\n setTimeout(() => {\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"none\";\n adContainerEl.style.display = \"none\";\n console.log(\n \"[IMA] Ad container hidden after setup error\"\n );\n }\n }, 300);\n }\n showContentVideo();\n\n if (!options?.continueLiveStreamDuringAds) {\n if (video.paused) {\n console.log(\n \"[IMA] Resuming paused video after setup error\"\n );\n video.play().catch(() => {});\n }\n }\n\n if (adsLoadedReject) {\n adsLoadedReject(new Error(\"Failed to setup ads manager\"));\n adsLoadedReject = undefined;\n adsLoadedResolve = undefined;\n }\n emit(\"ad_error\");\n }\n },\n false\n );\n\n adsLoader.addEventListener(\n google.ima.AdErrorEvent.Type.AD_ERROR,\n (adErrorEvent: any) => {\n const error = adErrorEvent.getError();\n console.error(\"[IMA] ❌ ADS_LOADER ERROR - Ad request failed!\", {\n message: error.getMessage?.(),\n errorCode: error.getErrorCode?.(),\n type: error.getType?.(),\n vastErrorCode: error.getVastErrorCode?.(),\n });\n console.error(\"[IMA] This means the ad server didn't return valid ads\");\n console.error(\"[IMA] Ad layer will NOT appear (no flicker)\");\n console.error(\"[IMA] Full error object:\", adErrorEvent.getError());\n\n adPlaying = false;\n setAdPlayingFlag(false);\n\n if (adContainerEl) {\n adContainerEl.style.opacity = \"0\";\n adContainerEl.style.backgroundColor = \"transparent\";\n setTimeout(() => {\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"none\";\n adContainerEl.style.display = \"none\";\n console.log(\"[IMA] Ad container hidden after loader error\");\n }\n }, 300);\n }\n\n showContentVideo();\n\n if (!options?.continueLiveStreamDuringAds) {\n if (video.paused) {\n console.log(\"[IMA] Resuming paused video after loader error\");\n video.play().catch(() => {});\n }\n }\n\n if (adsLoadedReject) {\n adsLoadedReject(new Error(\"Ads loader error\"));\n adsLoadedReject = undefined;\n adsLoadedResolve = undefined;\n }\n emit(\"ad_error\");\n },\n false\n );\n }\n\n console.log(\"[IMA] πŸš€ Making ads request to IMA SDK\");\n console.log(\"[IMA] Waiting for IMA SDK response (LOADED or ERROR event)...\");\n makeAdsRequest(google, vastTagUrl);\n\n console.log(\"[IMA] ⏳ Returning promise that will resolve when ads are loaded\");\n return adsLoadedPromise;\n } catch (error) {\n console.error(\"[IMA] Failed to request ads:\", error);\n\n currentReject?.(error as Error);\n adsLoadedReject = undefined;\n adsLoadedResolve = undefined;\n return Promise.reject(error);\n }\n },\n async preloadAds(vastTagUrl: string) {\n if (!vastTagUrl || vastTagUrl.trim() === \"\") {\n return Promise.resolve();\n }\n\n if (preloadedVast.has(vastTagUrl)) {\n return Promise.resolve();\n }\n\n const inflight = preloadingVast.get(vastTagUrl);\n if (inflight) {\n return inflight;\n }\n\n const preloadPromise = fetchVastDocument(vastTagUrl)\n .then((xml) => {\n preloadedVast.set(vastTagUrl, xml);\n console.log(\"[IMA] Cached VAST response for preloading:\", vastTagUrl);\n })\n .catch((error) => {\n console.warn(\"[IMA] Failed to preload VAST response:\", error);\n preloadedVast.delete(vastTagUrl);\n })\n .finally(() => {\n preloadingVast.delete(vastTagUrl);\n });\n\n preloadingVast.set(vastTagUrl, preloadPromise);\n return preloadPromise;\n },\n hasPreloadedAd(vastTagUrl: string) {\n return preloadedVast.has(vastTagUrl);\n },\n async play() {\n console.log(\"[IMA] ▢️ === play() called ===\");\n console.log(\"[IMA] This initializes and starts the ad\");\n console.log(\"[IMA] Ad layer will appear when CONTENT_PAUSE_REQUESTED fires\");\n\n if (!window.google?.ima || !adDisplayContainer) {\n console.warn(\n \"[IMA] ❌ Cannot play ad: IMA SDK or ad container not available\"\n );\n return Promise.reject(new Error(\"IMA SDK not available\"));\n }\n\n if (!adsManager) {\n console.warn(\"[IMA] ❌ Cannot play ad: No ads manager available\");\n return Promise.reject(new Error(\"No ads manager\"));\n }\n\n try {\n const width = video.clientWidth || 640;\n const height = video.clientHeight || 360;\n\n console.log(`[IMA] 🎬 Initializing ads manager (${width}x${height})`);\n adsManager.init(width, height, window.google.ima.ViewMode.NORMAL);\n\n adPlaying = true;\n\n const adVolume = originalMutedState ? 0 : originalVolume;\n if (adVideoElement) {\n adVideoElement.volume = adVolume;\n adVideoElement.muted = originalMutedState;\n console.log(\n `[IMA] πŸ”Š Set dedicated ad video volume to ${adVolume}, muted: ${originalMutedState}`\n );\n }\n\n try {\n adsManager.setVolume(adVolume);\n console.log(`[IMA] Set IMA manager volume to ${adVolume}`);\n } catch (error) {\n console.warn(\"[IMA] Failed to set IMA manager volume:\", error);\n }\n\n console.log(\"[IMA] 🎯 Calling adsManager.start()\");\n console.log(\"[IMA] If successful, IMA will fire CONTENT_PAUSE_REQUESTED\");\n adsManager.start();\n\n console.log(\"[IMA] βœ… play() completed successfully\");\n return Promise.resolve();\n } catch (error) {\n console.error(\"[IMA] ❌ Error starting ad playback:\", error);\n adPlaying = false;\n setAdPlayingFlag(false);\n\n if (!options?.continueLiveStreamDuringAds) {\n video.play()?.catch(() => {});\n }\n return Promise.reject(error);\n }\n },\n async stop() {\n console.log(\"[IMA] Stopping ad playback\");\n adPlaying = false;\n setAdPlayingFlag(false);\n\n if (adContainerEl) {\n adContainerEl.style.opacity = \"0\";\n adContainerEl.style.backgroundColor = \"transparent\";\n setTimeout(() => {\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"none\";\n adContainerEl.style.display = \"none\";\n console.log(\"[IMA] Ad container hidden after stop\");\n }\n }, 300);\n }\n\n showContentVideo();\n\n try {\n adsManager?.stop?.();\n } catch {}\n\n destroyAdsManager();\n },\n destroy() {\n destroyAdsManager();\n\n adPlaying = false;\n setAdPlayingFlag(false);\n\n if (adContainerEl) {\n adContainerEl.style.opacity = \"0\";\n adContainerEl.style.backgroundColor = \"transparent\";\n setTimeout(() => {\n if (adContainerEl) {\n adContainerEl.style.pointerEvents = \"none\";\n adContainerEl.style.display = \"none\";\n\n if (adContainerEl.parentElement) {\n adContainerEl.parentElement.removeChild(adContainerEl);\n }\n\n adContainerEl = undefined;\n adVideoElement = undefined;\n }\n }, 300);\n }\n\n showContentVideo();\n\n try {\n adsLoader?.destroy?.();\n } catch {}\n\n adDisplayContainer = undefined;\n adsLoader = undefined;\n contentVideoHidden = false;\n preloadedVast.clear();\n preloadingVast.clear();\n },\n isAdPlaying() {\n return adPlaying;\n },\n resize(width: number, height: number) {\n if (!adsManager || !window.google?.ima) {\n console.warn(\n \"[IMA] Cannot resize: No ads manager or IMA SDK available\"\n );\n return;\n }\n\n try {\n console.log(`[IMA] Resizing ads manager to ${width}x${height}`);\n adsManager.resize(width, height, window.google.ima.ViewMode.NORMAL);\n } catch (error) {\n console.warn(\"[IMA] Error resizing ads manager:\", error);\n }\n },\n on(event: string, listener: (payload?: any) => void) {\n if (!listeners.has(event)) listeners.set(event, new Set());\n listeners.get(event)!.add(listener);\n },\n off(event: string, listener: (payload?: any) => void) {\n listeners.get(event)?.delete(listener);\n },\n updateOriginalMutedState(muted: boolean, volume?: number) {\n const nextVolume =\n typeof volume === \"number\" && !Number.isNaN(volume)\n ? Math.max(0, Math.min(1, volume))\n : originalVolume;\n console.log(\n `[IMA] updateOriginalMutedState called: { muted: ${originalMutedState} -> ${muted}, volume: ${originalVolume} -> ${nextVolume} }`\n );\n originalMutedState = muted;\n originalVolume = nextVolume;\n },\n getOriginalMutedState() {\n return originalMutedState;\n },\n getOriginalVolume() {\n return originalVolume;\n },\n setAdVolume(volume: number) {\n const clampedVolume = Math.max(0, Math.min(1, volume));\n\n if (adVideoElement && adPlaying) {\n adVideoElement.volume = clampedVolume;\n adVideoElement.muted = clampedVolume === 0;\n console.log(\n `[IMA] Set dedicated ad video volume to ${clampedVolume}, muted: ${\n clampedVolume === 0\n }`\n );\n }\n\n if (adsManager && adPlaying) {\n try {\n adsManager.setVolume(clampedVolume);\n } catch (error) {\n console.warn(\"[IMA] Failed to set IMA manager volume:\", error);\n }\n }\n },\n getAdVolume(): number {\n if (adVideoElement && adPlaying) {\n return adVideoElement.volume;\n }\n\n if (adsManager && adPlaying) {\n try {\n return adsManager.getVolume();\n } catch (error) {\n console.warn(\"[IMA] Failed to get ad volume:\", error);\n return 1;\n }\n }\n return 1;\n },\n showPlaceholder() {\n ensurePlaceholderContainer();\n if (adContainerEl) {\n adContainerEl.style.display = \"flex\";\n adContainerEl.style.backgroundColor = \"#000\";\n // Force reflow\n adContainerEl.offsetHeight;\n adContainerEl.style.opacity = \"1\";\n adContainerEl.style.pointerEvents = \"auto\";\n }\n },\n hidePlaceholder() {\n if (adContainerEl) {\n adContainerEl.style.opacity = \"0\";\n adContainerEl.style.backgroundColor = \"transparent\";\n setTimeout(() => {\n if (adContainerEl) {\n adContainerEl.style.display = \"none\";\n adContainerEl.style.pointerEvents = \"none\";\n }\n }, 300);\n }\n },\n };\n}\n","interface NavigatorUAData {\n platform?: string;\n brands?: Array<{ brand: string; version: string }>;\n mobile?: boolean;\n}\n\ndeclare global {\n interface Navigator {\n userAgentData?: NavigatorUAData;\n }\n}\n\nexport interface BrowserInfo {\n name: string;\n version: string;\n majorVersion: number;\n isSmartTV: boolean;\n isLegacyTV: boolean;\n platform: string;\n supportsIMA: boolean;\n supportsModernJS: boolean;\n recommendedAdPlayer: 'ima' | 'hls';\n}\n\nfunction getChromeVersion(ua: string): number {\n const match = ua.match(/Chrome\\/(\\d+)/);\n return match && match[1] ? parseInt(match[1], 10) : 0;\n}\n\nfunction getWebKitVersion(ua: string): number {\n const match = ua.match(/AppleWebKit\\/(\\d+)/);\n return match && match[1] ? parseInt(match[1], 10) : 0;\n}\n\nfunction getPlatform(): string {\n if ('userAgentData' in navigator && navigator.userAgentData?.platform) {\n return navigator.userAgentData.platform;\n }\n\n const ua = navigator.userAgent;\n if (/Mac|iPhone|iPad|iPod/i.test(ua)) {\n return /iPhone|iPad|iPod/i.test(ua) ? 'iPhone' : 'MacIntel';\n }\n if (/Win/i.test(ua)) {\n return 'Win32';\n }\n if (/Linux/i.test(ua)) {\n return /Android/i.test(ua) ? 'Linux armv8l' : 'Linux x86_64';\n }\n if (/CrOS/i.test(ua)) {\n return 'CrOS';\n }\n\n // eslint-disable-next-line deprecation/deprecation\n return (navigator as any).platform || 'Unknown';\n}\n\nexport function detectBrowser(): BrowserInfo {\n const ua = navigator.userAgent;\n const platform = getPlatform();\n\n let name = 'Unknown';\n let version = '0';\n let majorVersion = 0;\n let isSmartTV = false;\n let isLegacyTV = false;\n let supportsIMA = true;\n let supportsModernJS = true;\n let recommendedAdPlayer: 'ima' | 'hls' = 'ima';\n\n if (/Web0S|webOS/i.test(ua)) {\n name = 'LG WebOS';\n isSmartTV = true;\n const match = ua.match(/Web0S[/\\s]*([\\d.]+)/i);\n version = match && match[1] ? match[1] : 'Unknown';\n if (version !== 'Unknown') {\n const parts = version.split('.');\n majorVersion = parts[0] ? parseInt(parts[0], 10) : 0;\n }\n } else if (/Tizen/i.test(ua)) {\n name = 'Samsung Tizen';\n isSmartTV = true;\n const match = ua.match(/Tizen[/\\s]*([\\d.]+)/i);\n version = match && match[1] ? match[1] : 'Unknown';\n if (version !== 'Unknown') {\n const parts = version.split('.');\n majorVersion = parts[0] ? parseInt(parts[0], 10) : 0;\n }\n } else if (/SMART-TV|SmartTV/i.test(ua)) {\n name = 'Smart TV';\n isSmartTV = true;\n } else if (/NetCast/i.test(ua)) {\n name = 'LG NetCast';\n isSmartTV = true;\n isLegacyTV = true;\n } else if (/BRAVIA/i.test(ua)) {\n name = 'Sony BRAVIA';\n isSmartTV = true;\n }\n\n const chromeVersion = getChromeVersion(ua);\n const webkitVersion = getWebKitVersion(ua);\n\n if (chromeVersion > 0) {\n if (!isSmartTV) {\n name = 'Chrome';\n version = chromeVersion.toString();\n majorVersion = chromeVersion;\n }\n\n if (chromeVersion < 50) {\n supportsIMA = false;\n supportsModernJS = false;\n isLegacyTV = true;\n recommendedAdPlayer = 'hls';\n }\n }\n\n if (webkitVersion > 0 && webkitVersion < 600) {\n supportsModernJS = false;\n if (isSmartTV) {\n isLegacyTV = true;\n supportsIMA = false;\n recommendedAdPlayer = 'hls';\n }\n }\n\n if (typeof Promise === 'undefined' ||\n typeof Map === 'undefined' ||\n typeof Set === 'undefined') {\n supportsModernJS = false;\n supportsIMA = false;\n recommendedAdPlayer = 'hls';\n }\n\n if (typeof URLSearchParams === 'undefined') {\n supportsModernJS = false;\n }\n\n return {\n name,\n version,\n majorVersion,\n isSmartTV,\n isLegacyTV,\n platform,\n supportsIMA,\n supportsModernJS,\n recommendedAdPlayer,\n };\n}\n\nexport function supportsGoogleIMA(): boolean {\n const browser = detectBrowser();\n\n if (browser.isLegacyTV) {\n return false;\n }\n\n if (typeof document === 'undefined' ||\n typeof document.createElement !== 'function') {\n return false;\n }\n\n try {\n const video = document.createElement('video');\n if (!video) {\n return false;\n }\n } catch (e) {\n return false;\n }\n\n if (typeof Promise === 'undefined') {\n return false;\n }\n\n return browser.supportsIMA;\n}\n\nexport function getRecommendedAdPlayer(): 'ima' | 'hls' {\n const browser = detectBrowser();\n return browser.recommendedAdPlayer;\n}\n\nexport function supportsModernJS(): boolean {\n try {\n return (\n typeof Promise !== 'undefined' &&\n typeof Map !== 'undefined' &&\n typeof Set !== 'undefined' &&\n typeof Array.from !== 'undefined' &&\n typeof Object.assign !== 'undefined' &&\n typeof Array.prototype.forEach !== 'undefined' &&\n typeof String.prototype.includes !== 'undefined'\n );\n } catch (e) {\n return false;\n }\n}\n\nexport function logBrowserInfo(debug: boolean = false): void {\n if (!debug) return;\n\n const browser = detectBrowser();\n const imaSupport = supportsGoogleIMA();\n\n console.log('[StormcloudVideoPlayer] Browser Compatibility Info:', {\n browser: `${browser.name} ${browser.version}`,\n platform: browser.platform,\n isSmartTV: browser.isSmartTV,\n isLegacyTV: browser.isLegacyTV,\n supportsIMA: imaSupport,\n supportsModernJS: browser.supportsModernJS,\n recommendedAdPlayer: browser.recommendedAdPlayer,\n userAgent: navigator.userAgent,\n });\n}\n\nexport function getBrowserConfigOverrides(): {\n adPlayerType?: 'ima' | 'hls';\n allowNativeHls?: boolean;\n} {\n const browser = detectBrowser();\n const overrides: any = {};\n\n if (browser.isLegacyTV || !browser.supportsIMA) {\n overrides.adPlayerType = 'hls';\n }\n\n if (browser.isSmartTV) {\n overrides.allowNativeHls = true;\n }\n\n return overrides;\n}\n\nexport function supportsFeature(feature: string): boolean {\n switch (feature) {\n case 'ima':\n return supportsGoogleIMA();\n case 'urlsearchparams':\n return typeof URLSearchParams !== 'undefined';\n case 'textencoder':\n return typeof TextEncoder !== 'undefined';\n case 'promises':\n return typeof Promise !== 'undefined';\n case 'fetch':\n return typeof fetch !== 'undefined';\n case 'crypto':\n return typeof crypto !== 'undefined' && typeof crypto.subtle !== 'undefined';\n default:\n return false;\n }\n}\n\n"],"mappings":"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","names":[]}