spactureai-mobile-player 1.0.32 → 1.0.34

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.
@@ -11,18 +11,53 @@ import Foundation
11
11
  import MobileVLCKit
12
12
  import NitroModules
13
13
 
14
- // MARK: - HLS / network tuning (conservative defaults; override via source headers if needed)
14
+ // MARK: - HLS / network tuning (libvlc `network-caching` / `live-caching`)
15
15
 
16
+ /// libvlc `network-caching` is a **single** input-side budget (ms). Setting it
17
+ /// to many minutes makes VLC stay in `opening` / `buffering` for a long time
18
+ /// before first frame — the default must stay small for CCTV/HLS. Opt into a
19
+ /// larger window only via `VideoConfig.bufferConfig` (forward + back sum).
16
20
  private enum VLCHLSDefaults {
17
- /// Milliseconds of media to prefetch before playback resumes.
18
- /// VLC sits buffering for at least this long after every seek, so we
19
- /// keep it small for VOD HLS (recordings) where the user expects scrub
20
- /// to land near-instantly. Bump back up if you see frequent stutter.
21
- static let networkCachingMs = 300
22
- /// Same as above but only used when libvlc tags the stream as live; our
23
- /// MediaMTX recordings are VOD, so this almost never applies. Keep it
24
- /// low so the rare live tail doesn't add seconds of pre-roll.
25
- static let liveCachingMs = 300
21
+ static let floorMs = 300
22
+ /// Default total when JS omits `bufferConfig` prioritises time-to-first-frame.
23
+ static let defaultRemoteTotalMs = 4_000
24
+ /// Per-side fallback when `bufferConfig` is present but a field is nil (1 min).
25
+ static let bufferConfigSideFallbackMs = 60_000
26
+ static let hardCapMs = 2 * 3600 * 1_000
27
+ /// First-frame watchdog: if we never leave loading, surface `error` to JS.
28
+ static let firstFrameTimeoutSeconds: TimeInterval = 45
29
+
30
+ static func networkCachingMs(for config: NativeVideoConfig, sourceURL: URL) -> Int {
31
+ let scheme = sourceURL.scheme?.lowercased() ?? ""
32
+ let isRemote =
33
+ scheme == "http" || scheme == "https" || scheme == "rtsp" || scheme == "rtsps"
34
+ guard isRemote else { return floorMs }
35
+
36
+ guard let b = config.bufferConfig else {
37
+ return min(max(floorMs, defaultRemoteTotalMs), hardCapMs)
38
+ }
39
+
40
+ let side = Double(bufferConfigSideFallbackMs)
41
+ let forward = Int(b.preferredForwardBufferDurationMs ?? b.maxBufferMs ?? side)
42
+ let back = Int(b.backBufferDurationMs ?? b.minBufferMs ?? side)
43
+ let total = max(floorMs, forward + back)
44
+ return min(total, hardCapMs)
45
+ }
46
+
47
+ static func liveCachingMs(for config: NativeVideoConfig, networkCachingMs: Int) -> Int {
48
+ if let target = config.bufferConfig?.livePlayback?.targetOffsetMs, target > 0 {
49
+ return max(floorMs, min(Int(target), networkCachingMs))
50
+ }
51
+ return networkCachingMs
52
+ }
53
+
54
+ #if DEBUG
55
+ static func log(_ message: String) {
56
+ print("[UnifiedPlayer/VLC] \(message)")
57
+ }
58
+ #else
59
+ static func log(_ message: String) {}
60
+ #endif
26
61
  }
27
62
 
28
63
  final class HybridVideoPlayer: HybridVideoPlayerSpec, VLCPlaybackDelegateOwner {
@@ -60,6 +95,8 @@ final class HybridVideoPlayer: HybridVideoPlayerSpec, VLCPlaybackDelegateOwner {
60
95
  /// from `VideoComponentView` when the surface attaches.
61
96
  private var wantsPlaybackWhenDrawableReady: Bool = false
62
97
 
98
+ private var loadTimeoutWorkItem: DispatchWorkItem?
99
+
63
100
  /// Marshal a closure onto the main thread, executing inline if we're
64
101
  /// already there. VLC's renderer (`VLCOpenGLES2VideoView`) reaches into
65
102
  /// `CAEAGLLayer` to manage its OpenGL renderbuffer when the active
@@ -219,6 +256,7 @@ final class HybridVideoPlayer: HybridVideoPlayerSpec, VLCPlaybackDelegateOwner {
219
256
  }
220
257
 
221
258
  func release() {
259
+ cancelLoadTimeout()
222
260
  invalidateStallWatchdog()
223
261
 
224
262
  // Capture the VLC objects so they survive past `self` being
@@ -300,10 +338,14 @@ final class HybridVideoPlayer: HybridVideoPlayerSpec, VLCPlaybackDelegateOwner {
300
338
 
301
339
  /// Called from `VideoComponentView` after `mediaPlayer.drawable` is set.
302
340
  func notifyVideoHostViewAttached() {
341
+ VLCHLSDefaults.log(
342
+ "drawable attached; wantsPlayback=\(wantsPlaybackWhenDrawableReady) state=\(String(describing: mediaPlayer.state))"
343
+ )
303
344
  if wantsPlaybackWhenDrawableReady, media != nil {
304
345
  mediaPlayer.play()
305
346
  }
306
347
  maybeFireOnLoad()
348
+ emitPlaybackState()
307
349
  }
308
350
 
309
351
  func seekBy(time: Double) throws {
@@ -339,6 +381,7 @@ final class HybridVideoPlayer: HybridVideoPlayerSpec, VLCPlaybackDelegateOwner {
339
381
  promise.resolve(withResult: ())
340
382
  case .second(let newSource):
341
383
  wantsPlaybackWhenDrawableReady = false
384
+ cancelLoadTimeout()
342
385
  invalidateStallWatchdog()
343
386
 
344
387
  // Tear down the previous VLC media on main — same reasoning as
@@ -467,7 +510,11 @@ final class HybridVideoPlayer: HybridVideoPlayerSpec, VLCPlaybackDelegateOwner {
467
510
 
468
511
  let media = VLCMedia(url: mediaURL)
469
512
 
470
- applyHlsNetworkOptions(to: media)
513
+ applyHlsNetworkOptions(
514
+ to: media,
515
+ sourceURL: hybridSource.url,
516
+ videoConfig: hybridSource.config
517
+ )
471
518
 
472
519
  for (key, value) in residualHeaders {
473
520
  switch key.lowercased() {
@@ -512,6 +559,8 @@ final class HybridVideoPlayer: HybridVideoPlayerSpec, VLCPlaybackDelegateOwner {
512
559
  status = .loading
513
560
  setBuffering(true)
514
561
  hasEmittedEndForCurrentItem = false
562
+ emitPlaybackState()
563
+ scheduleLoadTimeout()
515
564
  }
516
565
 
517
566
  /// Rewrite an http(s) URL to point at the local auth proxy on
@@ -529,11 +578,68 @@ final class HybridVideoPlayer: HybridVideoPlayerSpec, VLCPlaybackDelegateOwner {
529
578
  return components.url
530
579
  }
531
580
 
532
- private func applyHlsNetworkOptions(to media: VLCMedia) {
533
- media.addOption(":network-caching=\(VLCHLSDefaults.networkCachingMs)")
534
- media.addOption(":live-caching=\(VLCHLSDefaults.liveCachingMs)")
581
+ private func applyHlsNetworkOptions(
582
+ to media: VLCMedia,
583
+ sourceURL: URL,
584
+ videoConfig: NativeVideoConfig
585
+ ) {
586
+ let scheme = sourceURL.scheme?.lowercased() ?? ""
587
+ let networkMs = VLCHLSDefaults.networkCachingMs(for: videoConfig, sourceURL: sourceURL)
588
+ let liveMs = VLCHLSDefaults.liveCachingMs(for: videoConfig, networkCachingMs: networkMs)
589
+ media.addOption(":network-caching=\(networkMs)")
590
+ media.addOption(":live-caching=\(liveMs)")
535
591
  // HLS over HTTP benefits from reconnect; harmless for file URLs.
536
592
  media.addOption(":http-reconnect=true")
593
+
594
+ // RTSP: UDP can be blocked on cellular / Wi‑Fi guest; TCP interleaved is
595
+ // the reliable default for CCTV / NVR streams.
596
+ if scheme == "rtsp" || scheme == "rtsps" {
597
+ media.addOption(":rtsp-tcp")
598
+ }
599
+
600
+ // HLS: libvlc may issue many small GETs (master + variant index.m3u8).
601
+ // Keep-alive amortizes TLS/TCP handshakes. Parallel segment threads help
602
+ // time-to-first-frame once a variant is selected. (Master still lists
603
+ // every variant; fastest fix for huge masters is pointing the URI at a
604
+ // single media playlist from the app.)
605
+ let path = sourceURL.absoluteString.lowercased()
606
+ if path.contains(".m3u8") {
607
+ media.addOption(":http-keep-alive=true")
608
+ media.addOption(":hls-segment-threads=2")
609
+ }
610
+
611
+ VLCHLSDefaults.log(
612
+ "options url=\(sourceURL.absoluteString) scheme=\(scheme) network-caching=\(networkMs) live-caching=\(liveMs)"
613
+ )
614
+ }
615
+
616
+ private func scheduleLoadTimeout() {
617
+ cancelLoadTimeout()
618
+ let item = DispatchWorkItem { [weak self] in
619
+ guard let self else { return }
620
+ guard self.media != nil else { return }
621
+ guard !self.hasFiredOnLoad else { return }
622
+ let vlcState = self.mediaPlayer.state
623
+ if vlcState == .playing || vlcState == .paused {
624
+ return
625
+ }
626
+ VLCHLSDefaults.log(
627
+ "first-frame timeout (state=\(String(describing: vlcState)) isPlaying=\(self.mediaPlayer.isPlaying))"
628
+ )
629
+ self.setBuffering(false)
630
+ self.status = .error
631
+ self.emitPlaybackState()
632
+ }
633
+ loadTimeoutWorkItem = item
634
+ DispatchQueue.main.asyncAfter(
635
+ deadline: .now() + VLCHLSDefaults.firstFrameTimeoutSeconds,
636
+ execute: item
637
+ )
638
+ }
639
+
640
+ private func cancelLoadTimeout() {
641
+ loadTimeoutWorkItem?.cancel()
642
+ loadTimeoutWorkItem = nil
537
643
  }
538
644
 
539
645
  /// Resets stall-watchdog liveness so a long seek / buffer gap is not mistaken for a dead stream.
@@ -571,6 +677,7 @@ final class HybridVideoPlayer: HybridVideoPlayerSpec, VLCPlaybackDelegateOwner {
571
677
 
572
678
  private func handleStateChange() {
573
679
  let state = mediaPlayer.state
680
+ VLCHLSDefaults.log("stateChange -> \(String(describing: state))")
574
681
  switch state {
575
682
  case .opening:
576
683
  status = .loading
@@ -584,6 +691,7 @@ final class HybridVideoPlayer: HybridVideoPlayerSpec, VLCPlaybackDelegateOwner {
584
691
  }
585
692
 
586
693
  case .playing:
694
+ cancelLoadTimeout()
587
695
  setBuffering(false)
588
696
  status = .readytoplay
589
697
  maybeFireOnLoad()
@@ -594,6 +702,7 @@ final class HybridVideoPlayer: HybridVideoPlayerSpec, VLCPlaybackDelegateOwner {
594
702
  case .paused:
595
703
  setBuffering(false)
596
704
  if status == .loading { status = .readytoplay }
705
+ maybeFireOnLoad()
597
706
  VideoManager.shared.requestAudioSessionUpdate()
598
707
 
599
708
  case .stopped, .ended:
@@ -609,6 +718,7 @@ final class HybridVideoPlayer: HybridVideoPlayerSpec, VLCPlaybackDelegateOwner {
609
718
  }
610
719
 
611
720
  case .error:
721
+ cancelLoadTimeout()
612
722
  setBuffering(false)
613
723
  status = .error
614
724
  // JS layer maps `error` status → `onError` (see VideoPlayer.ts).
@@ -661,13 +771,22 @@ final class HybridVideoPlayer: HybridVideoPlayerSpec, VLCPlaybackDelegateOwner {
661
771
  let hasDuration = dur.isFinite && dur > 0
662
772
  let size = mediaPlayer.videoSize
663
773
  let hasVideo = size.width > 0 && size.height > 0
774
+ let state = mediaPlayer.state
664
775
  // VOD HLS from MediaMTX may keep length at 0 until the playlist is fully
665
776
  // parsed; still emit onLoad once we are playing or have decoded dimensions
666
777
  // so JS overlays (e.g. preroll spinner) can clear.
667
- if !hasDuration && !mediaPlayer.isPlaying && !hasVideo {
778
+ let hasBasicReadiness =
779
+ hasDuration || mediaPlayer.isPlaying || hasVideo
780
+ // First paint: VLC can report 0×0 video size and unknown duration while
781
+ // already past demux (paused autoplay, or drawable attached a frame late).
782
+ let demuxPastOpen =
783
+ state == .playing || state == .paused || state == .buffering
784
+ let relaxedReadiness = (media?.isParsed == true) && demuxPastOpen
785
+ if !hasBasicReadiness && !relaxedReadiness {
668
786
  return
669
787
  }
670
788
  hasFiredOnLoad = true
789
+ cancelLoadTimeout()
671
790
  let width = Double(size.width)
672
791
  let height = Double(size.height)
673
792
  let orientation: VideoOrientation =
@@ -1,10 +1,11 @@
1
1
  "use strict";
2
2
 
3
3
  import * as React from 'react';
4
+ import { ActivityIndicator, StyleSheet, View } from 'react-native';
4
5
  import { NitroModules } from 'react-native-nitro-modules';
5
6
  import { tryParseNativeVideoError, VideoComponentError, VideoError } from "../types/VideoError.js";
6
7
  import { NativeVideoView } from './NativeVideoView';
7
- import { jsx as _jsx } from "react/jsx-runtime";
8
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
8
9
  let nitroIdCounter = 1;
9
10
  const VideoViewViewManagerFactory = NitroModules.createHybridObject('VideoViewViewManagerFactory');
10
11
  const wrapNativeViewManagerFunction = (manager, func) => {
@@ -50,6 +51,8 @@ const VideoView = /*#__PURE__*/React.forwardRef(({
50
51
  fullscreen = false,
51
52
  paused,
52
53
  speed,
54
+ showLoadingIndicator = false,
55
+ loadingIndicatorColor,
53
56
  onPictureInPictureChange,
54
57
  onFullscreenChange,
55
58
  willEnterFullscreen,
@@ -61,6 +64,37 @@ const VideoView = /*#__PURE__*/React.forwardRef(({
61
64
  const nitroId = React.useMemo(() => nitroIdCounter++, []);
62
65
  const nitroViewManager = React.useRef(null);
63
66
  const [isManagerReady, setIsManagerReady] = React.useState(false);
67
+ const [hasLoadedMedia, setHasLoadedMedia] = React.useState(false);
68
+ const [isBuffering, setIsBuffering] = React.useState(false);
69
+ const [playerStatus, setPlayerStatus] = React.useState(player.status);
70
+ React.useEffect(() => {
71
+ if (!showLoadingIndicator) {
72
+ return;
73
+ }
74
+ setPlayerStatus(player.status);
75
+ setHasLoadedMedia(player.status === 'readyToPlay');
76
+ const onLoadStart = () => {
77
+ setHasLoadedMedia(false);
78
+ setIsBuffering(true);
79
+ };
80
+ const onLoad = () => {
81
+ setHasLoadedMedia(true);
82
+ setIsBuffering(false);
83
+ };
84
+ const onBuffer = buffering => setIsBuffering(buffering);
85
+ const onStatus = status => setPlayerStatus(status);
86
+ const subLoadStart = player.addEventListener('onLoadStart', onLoadStart);
87
+ const subLoad = player.addEventListener('onLoad', onLoad);
88
+ const subBuffer = player.addEventListener('onBuffer', onBuffer);
89
+ const subStatus = player.addEventListener('onStatusChange', onStatus);
90
+ return () => {
91
+ subLoadStart.remove();
92
+ subLoad.remove();
93
+ subBuffer.remove();
94
+ subStatus.remove();
95
+ };
96
+ }, [player, showLoadingIndicator]);
97
+ const showNativeSpinner = showLoadingIndicator && playerStatus !== 'error' && playerStatus !== 'idle' && (!hasLoadedMedia || isBuffering);
64
98
  const setupViewManager = React.useCallback(id => {
65
99
  try {
66
100
  if (nitroViewManager.current === null) {
@@ -250,12 +284,38 @@ const VideoView = /*#__PURE__*/React.forwardRef(({
250
284
  console.warn('[UnifiedPlayer] Failed to change fullscreen state:', error);
251
285
  }
252
286
  }, [fullscreen, isManagerReady]);
253
- return /*#__PURE__*/_jsx(NativeVideoView, {
254
- nitroId: nitroId,
255
- onNitroIdChange: onNitroIdChange,
256
- ...props
287
+ if (!showLoadingIndicator) {
288
+ return /*#__PURE__*/_jsx(NativeVideoView, {
289
+ nitroId: nitroId,
290
+ onNitroIdChange: onNitroIdChange,
291
+ ...props
292
+ });
293
+ }
294
+ return /*#__PURE__*/_jsxs(View, {
295
+ style: props.style,
296
+ collapsable: false,
297
+ children: [/*#__PURE__*/_jsx(NativeVideoView, {
298
+ nitroId: nitroId,
299
+ onNitroIdChange: onNitroIdChange,
300
+ ...props,
301
+ style: StyleSheet.absoluteFill
302
+ }), showNativeSpinner ? /*#__PURE__*/_jsx(View, {
303
+ style: styles.loadingOverlay,
304
+ pointerEvents: "none",
305
+ children: /*#__PURE__*/_jsx(ActivityIndicator, {
306
+ size: "large",
307
+ color: loadingIndicatorColor
308
+ })
309
+ }) : null]
257
310
  });
258
311
  });
312
+ const styles = StyleSheet.create({
313
+ loadingOverlay: {
314
+ ...StyleSheet.absoluteFillObject,
315
+ alignItems: 'center',
316
+ justifyContent: 'center'
317
+ }
318
+ });
259
319
  VideoView.displayName = 'VideoView';
260
320
  export default /*#__PURE__*/React.memo(VideoView);
261
321
  //# sourceMappingURL=VideoView.js.map
@@ -1 +1 @@
1
- {"version":3,"names":["React","NitroModules","tryParseNativeVideoError","VideoComponentError","VideoError","NativeVideoView","jsx","_jsx","nitroIdCounter","VideoViewViewManagerFactory","createHybridObject","wrapNativeViewManagerFunction","manager","func","error","updateProps","props","player","__getNativePlayer","controls","pictureInPicture","autoEnterPictureInPicture","resizeMode","keepScreenAwake","surfaceType","VideoView","forwardRef","autoplay","fullscreen","paused","speed","onPictureInPictureChange","onFullscreenChange","willEnterFullscreen","willExitFullscreen","willEnterPictureInPicture","willExitPictureInPicture","ref","nitroId","useMemo","nitroViewManager","useRef","isManagerReady","setIsManagerReady","useState","setupViewManager","useCallback","id","current","createViewManager","parsedError","code","console","warn","onNitroIdChange","event","nativeEvent","useImperativeHandle","enterFullscreen","exitFullscreen","enterPictureInPicture","exitPictureInPicture","canEnterPictureInPicture","addEventListener","callback","addOnPictureInPictureChangeListener","addOnFullscreenChangeListener","addWillEnterFullscreenListener","addWillExitFullscreenListener","addWillEnterPictureInPictureListener","addWillExitPictureInPictureListener","Error","useEffect","clearAllListeners","subscriptions","push","forEach","sub","remove","undefined","pause","play","rate","hasAutoplayedRef","prevFullscreenRef","prev","displayName","memo"],"sourceRoot":"../../../../src","sources":["core/video-view/VideoView.tsx"],"mappings":"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","ignoreList":[]}
1
+ {"version":3,"names":["React","ActivityIndicator","StyleSheet","View","NitroModules","tryParseNativeVideoError","VideoComponentError","VideoError","NativeVideoView","jsx","_jsx","jsxs","_jsxs","nitroIdCounter","VideoViewViewManagerFactory","createHybridObject","wrapNativeViewManagerFunction","manager","func","error","updateProps","props","player","__getNativePlayer","controls","pictureInPicture","autoEnterPictureInPicture","resizeMode","keepScreenAwake","surfaceType","VideoView","forwardRef","autoplay","fullscreen","paused","speed","showLoadingIndicator","loadingIndicatorColor","onPictureInPictureChange","onFullscreenChange","willEnterFullscreen","willExitFullscreen","willEnterPictureInPicture","willExitPictureInPicture","ref","nitroId","useMemo","nitroViewManager","useRef","isManagerReady","setIsManagerReady","useState","hasLoadedMedia","setHasLoadedMedia","isBuffering","setIsBuffering","playerStatus","setPlayerStatus","status","useEffect","onLoadStart","onLoad","onBuffer","buffering","onStatus","subLoadStart","addEventListener","subLoad","subBuffer","subStatus","remove","showNativeSpinner","setupViewManager","useCallback","id","current","createViewManager","parsedError","code","console","warn","onNitroIdChange","event","nativeEvent","useImperativeHandle","enterFullscreen","exitFullscreen","enterPictureInPicture","exitPictureInPicture","canEnterPictureInPicture","callback","addOnPictureInPictureChangeListener","addOnFullscreenChangeListener","addWillEnterFullscreenListener","addWillExitFullscreenListener","addWillEnterPictureInPictureListener","addWillExitPictureInPictureListener","Error","clearAllListeners","subscriptions","push","forEach","sub","undefined","pause","play","rate","hasAutoplayedRef","prevFullscreenRef","prev","style","collapsable","children","absoluteFill","styles","loadingOverlay","pointerEvents","size","color","create","absoluteFillObject","alignItems","justifyContent","displayName","memo"],"sourceRoot":"../../../../src","sources":["core/video-view/VideoView.tsx"],"mappings":"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","ignoreList":[]}
@@ -38,12 +38,17 @@ export interface BufferConfig {
38
38
  * Minimum duration (ms) the player will attempt to keep buffered.
39
39
  * @default 5000
40
40
  * @platform android
41
+ * @platform ios (VLC) Back portion of `network-caching` when set; if omitted
42
+ * alongside the other buffer fields, defaults to 60s for that side. Large
43
+ * values delay first frame — prefer explicit tuning over huge defaults.
41
44
  */
42
45
  minBufferMs?: number;
43
46
  /**
44
47
  * Maximum duration (ms) the player will attempt to keep buffered.
45
48
  * @default 10000
46
49
  * @platform android
50
+ * @platform ios (VLC) Fallback for the **forward** half when
51
+ * `preferredForwardBufferDurationMs` is omitted.
47
52
  */
48
53
  maxBufferMs?: number;
49
54
  /**
@@ -61,11 +66,16 @@ export interface BufferConfig {
61
66
  /**
62
67
  * Duration (ms) of media that must be buffered before it can be played from the back buffer.
63
68
  * @platform android
69
+ * @platform ios (VLC) Back portion of libvlc `network-caching`; if omitted
70
+ * defaults to 60s when any `bufferConfig` field is set.
64
71
  */
65
72
  backBufferDurationMs?: number;
66
73
  /**
67
74
  * The preferred duration (ms) of media that the player will attempt to retain in the buffer.
68
- * @platform ios, visionOS, tvOS
75
+ * @platform ios, visionOS, tvOS — AVKit semantics where applicable.
76
+ * @platform ios (VLC / unified-player) Forward portion of libvlc `network-caching`
77
+ * (combined with `backBufferDurationMs` / `minBufferMs`). Omit all fields to use
78
+ * a small default (~4s total) for fast first frame.
69
79
  */
70
80
  preferredForwardBufferDurationMs?: number;
71
81
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"BufferConfig.d.ts","sourceRoot":"","sources":["../../../../../src/core/types/BufferConfig.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,kBAAkB;IACjC;;;OAGG;IACH,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B;;;OAGG;IACH,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B;;;OAGG;IACH,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB;;;OAGG;IACH,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB;;;OAGG;IACH,cAAc,CAAC,EAAE,MAAM,CAAC;CACzB;AAED,UAAU,UAAU;IAClB,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,YAAY;IAC3B;;OAEG;IACH,YAAY,CAAC,EAAE,kBAAkB,CAAC;IAIlC;;;;OAIG;IACH,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB;;;;OAIG;IACH,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB;;;;OAIG;IACH,mBAAmB,CAAC,EAAE,MAAM,CAAC;IAC7B;;;;OAIG;IACH,gCAAgC,CAAC,EAAE,MAAM,CAAC;IAC1C;;;OAGG;IACH,oBAAoB,CAAC,EAAE,MAAM,CAAC;IAI9B;;;OAGG;IACH,gCAAgC,CAAC,EAAE,MAAM,CAAC;IAC1C;;;;;OAKG;IACH,oBAAoB,CAAC,EAAE,MAAM,CAAC;IAC9B;;;;;OAKG;IACH,0BAA0B,CAAC,EAAE,UAAU,CAAC;IACxC;;;OAGG;IACH,wCAAwC,CAAC,EAAE,MAAM,CAAC;IAClD;;;OAGG;IACH,8CAA8C,CAAC,EAAE,UAAU,CAAC;CAC7D"}
1
+ {"version":3,"file":"BufferConfig.d.ts","sourceRoot":"","sources":["../../../../../src/core/types/BufferConfig.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,kBAAkB;IACjC;;;OAGG;IACH,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B;;;OAGG;IACH,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B;;;OAGG;IACH,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB;;;OAGG;IACH,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB;;;OAGG;IACH,cAAc,CAAC,EAAE,MAAM,CAAC;CACzB;AAED,UAAU,UAAU;IAClB,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,YAAY;IAC3B;;OAEG;IACH,YAAY,CAAC,EAAE,kBAAkB,CAAC;IAIlC;;;;;;;OAOG;IACH,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB;;;;;;OAMG;IACH,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB;;;;OAIG;IACH,mBAAmB,CAAC,EAAE,MAAM,CAAC;IAC7B;;;;OAIG;IACH,gCAAgC,CAAC,EAAE,MAAM,CAAC;IAC1C;;;;;OAKG;IACH,oBAAoB,CAAC,EAAE,MAAM,CAAC;IAI9B;;;;;;OAMG;IACH,gCAAgC,CAAC,EAAE,MAAM,CAAC;IAC1C;;;;;OAKG;IACH,oBAAoB,CAAC,EAAE,MAAM,CAAC;IAC9B;;;;;OAKG;IACH,0BAA0B,CAAC,EAAE,UAAU,CAAC;IACxC;;;OAGG;IACH,wCAAwC,CAAC,EAAE,MAAM,CAAC;IAClD;;;OAGG;IACH,8CAA8C,CAAC,EAAE,UAAU,CAAC;CAC7D"}
@@ -68,6 +68,16 @@ export interface VideoViewProps extends Partial<VideoViewEvents>, ViewProps {
68
68
  * The playback speed of the video. Defaults to 1.0.
69
69
  */
70
70
  speed?: number;
71
+ /**
72
+ * When true, shows a centered activity indicator while the source is
73
+ * loading or the native player reports buffering (initial load and rebuffer).
74
+ * @default false
75
+ */
76
+ showLoadingIndicator?: boolean;
77
+ /**
78
+ * @platform ios
79
+ */
80
+ loadingIndicatorColor?: string;
71
81
  }
72
82
  export interface VideoViewRef {
73
83
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"VideoView.d.ts","sourceRoot":"","sources":["../../../../../src/core/video-view/VideoView.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAC/B,OAAO,KAAK,EAAE,SAAS,EAAE,SAAS,EAAE,MAAM,cAAc,CAAC;AAEzD,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,gDAAgD,CAAC;AAC3F,OAAO,KAAK,EACV,WAAW,EAGZ,MAAM,6CAA6C,CAAC;AACrD,OAAO,EAAE,KAAK,eAAe,EAAE,MAAM,iBAAiB,CAAC;AACvD,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,qBAAqB,CAAC;AAMtD,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,gBAAgB,CAAC;AAGlD,MAAM,WAAW,cAAe,SAAQ,OAAO,CAAC,eAAe,CAAC,EAAE,SAAS;IACzE;;OAEG;IACH,MAAM,EAAE,WAAW,CAAC;IACpB;;OAEG;IACH,KAAK,CAAC,EAAE,SAAS,CAAC;IAClB;;OAEG;IACH,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB;;OAEG;IACH,gBAAgB,CAAC,EAAE,OAAO,CAAC;IAC3B;;OAEG;IACH,yBAAyB,CAAC,EAAE,OAAO,CAAC;IACpC;;;;;;OAMG;IACH,UAAU,CAAC,EAAE,UAAU,CAAC;IACxB;;OAEG;IACH,eAAe,CAAC,EAAE,OAAO,CAAC;IAE1B;;;;;;;;;OASG;IACH,WAAW,CAAC,EAAE,WAAW,CAAC;IAC1B;;OAEG;IACH,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB;;;OAGG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB;;;;OAIG;IACH,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB;;OAEG;IACH,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,YAAY;IAC3B;;OAEG;IACH,eAAe,EAAE,MAAM,IAAI,CAAC;IAC5B;;OAEG;IACH,cAAc,EAAE,MAAM,IAAI,CAAC;IAC3B;;OAEG;IACH,qBAAqB,EAAE,MAAM,IAAI,CAAC;IAClC;;OAEG;IACH,oBAAoB,EAAE,MAAM,IAAI,CAAC;IACjC;;;OAGG;IACH,wBAAwB,EAAE,MAAM,OAAO,CAAC;IACxC;;;;;OAKG;IACH,gBAAgB,EAAE,CAAC,KAAK,SAAS,MAAM,eAAe,EACpD,KAAK,EAAE,KAAK,EACZ,QAAQ,EAAE,eAAe,CAAC,KAAK,CAAC,KAC7B,oBAAoB,CAAC;CAC3B;;AAsXD,wBAAqC"}
1
+ {"version":3,"file":"VideoView.d.ts","sourceRoot":"","sources":["../../../../../src/core/video-view/VideoView.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAC/B,OAAO,KAAK,EAAE,SAAS,EAAE,SAAS,EAAE,MAAM,cAAc,CAAC;AAGzD,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,gDAAgD,CAAC;AAC3F,OAAO,KAAK,EACV,WAAW,EAGZ,MAAM,6CAA6C,CAAC;AACrD,OAAO,EAAE,KAAK,eAAe,EAAE,MAAM,iBAAiB,CAAC;AACvD,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,qBAAqB,CAAC;AAOtD,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,gBAAgB,CAAC;AAGlD,MAAM,WAAW,cAAe,SAAQ,OAAO,CAAC,eAAe,CAAC,EAAE,SAAS;IACzE;;OAEG;IACH,MAAM,EAAE,WAAW,CAAC;IACpB;;OAEG;IACH,KAAK,CAAC,EAAE,SAAS,CAAC;IAClB;;OAEG;IACH,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB;;OAEG;IACH,gBAAgB,CAAC,EAAE,OAAO,CAAC;IAC3B;;OAEG;IACH,yBAAyB,CAAC,EAAE,OAAO,CAAC;IACpC;;;;;;OAMG;IACH,UAAU,CAAC,EAAE,UAAU,CAAC;IACxB;;OAEG;IACH,eAAe,CAAC,EAAE,OAAO,CAAC;IAE1B;;;;;;;;;OASG;IACH,WAAW,CAAC,EAAE,WAAW,CAAC;IAC1B;;OAEG;IACH,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB;;;OAGG;IACH,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB;;;;OAIG;IACH,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB;;OAEG;IACH,KAAK,CAAC,EAAE,MAAM,CAAC;IACf;;;;OAIG;IACH,oBAAoB,CAAC,EAAE,OAAO,CAAC;IAC/B;;OAEG;IACH,qBAAqB,CAAC,EAAE,MAAM,CAAC;CAChC;AAED,MAAM,WAAW,YAAY;IAC3B;;OAEG;IACH,eAAe,EAAE,MAAM,IAAI,CAAC;IAC5B;;OAEG;IACH,cAAc,EAAE,MAAM,IAAI,CAAC;IAC3B;;OAEG;IACH,qBAAqB,EAAE,MAAM,IAAI,CAAC;IAClC;;OAEG;IACH,oBAAoB,EAAE,MAAM,IAAI,CAAC;IACjC;;;OAGG;IACH,wBAAwB,EAAE,MAAM,OAAO,CAAC;IACxC;;;;;OAKG;IACH,gBAAgB,EAAE,CAAC,KAAK,SAAS,MAAM,eAAe,EACpD,KAAK,EAAE,KAAK,EACZ,QAAQ,EAAE,eAAe,CAAC,KAAK,CAAC,KAC7B,oBAAoB,CAAC;CAC3B;;AA4bD,wBAAqC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "spactureai-mobile-player",
3
- "version": "1.0.32",
3
+ "version": "1.0.34",
4
4
  "description": "Spacture AI Mobile Player",
5
5
  "source": "./src/index.tsx",
6
6
  "main": "./lib/module/index.js",
@@ -43,12 +43,17 @@ export interface BufferConfig {
43
43
  * Minimum duration (ms) the player will attempt to keep buffered.
44
44
  * @default 5000
45
45
  * @platform android
46
+ * @platform ios (VLC) Back portion of `network-caching` when set; if omitted
47
+ * alongside the other buffer fields, defaults to 60s for that side. Large
48
+ * values delay first frame — prefer explicit tuning over huge defaults.
46
49
  */
47
50
  minBufferMs?: number;
48
51
  /**
49
52
  * Maximum duration (ms) the player will attempt to keep buffered.
50
53
  * @default 10000
51
54
  * @platform android
55
+ * @platform ios (VLC) Fallback for the **forward** half when
56
+ * `preferredForwardBufferDurationMs` is omitted.
52
57
  */
53
58
  maxBufferMs?: number;
54
59
  /**
@@ -66,6 +71,8 @@ export interface BufferConfig {
66
71
  /**
67
72
  * Duration (ms) of media that must be buffered before it can be played from the back buffer.
68
73
  * @platform android
74
+ * @platform ios (VLC) Back portion of libvlc `network-caching`; if omitted
75
+ * defaults to 60s when any `bufferConfig` field is set.
69
76
  */
70
77
  backBufferDurationMs?: number;
71
78
 
@@ -73,7 +80,10 @@ export interface BufferConfig {
73
80
 
74
81
  /**
75
82
  * The preferred duration (ms) of media that the player will attempt to retain in the buffer.
76
- * @platform ios, visionOS, tvOS
83
+ * @platform ios, visionOS, tvOS — AVKit semantics where applicable.
84
+ * @platform ios (VLC / unified-player) Forward portion of libvlc `network-caching`
85
+ * (combined with `backBufferDurationMs` / `minBufferMs`). Omit all fields to use
86
+ * a small default (~4s total) for fast first frame.
77
87
  */
78
88
  preferredForwardBufferDurationMs?: number;
79
89
  /**
@@ -1,5 +1,6 @@
1
1
  import * as React from 'react';
2
2
  import type { ViewProps, ViewStyle } from 'react-native';
3
+ import { ActivityIndicator, StyleSheet, View } from 'react-native';
3
4
  import { NitroModules } from 'react-native-nitro-modules';
4
5
  import type { ListenerSubscription } from '../../spec/nitro/VideoPlayerEventEmitter.nitro';
5
6
  import type {
@@ -14,6 +15,7 @@ import {
14
15
  VideoComponentError,
15
16
  VideoError,
16
17
  } from '../types/VideoError';
18
+ import type { VideoPlayerStatus } from '../types/VideoPlayerStatus';
17
19
  import type { VideoPlayer } from '../VideoPlayer';
18
20
  import { NativeVideoView } from './NativeVideoView';
19
21
 
@@ -81,6 +83,16 @@ export interface VideoViewProps extends Partial<VideoViewEvents>, ViewProps {
81
83
  * The playback speed of the video. Defaults to 1.0.
82
84
  */
83
85
  speed?: number;
86
+ /**
87
+ * When true, shows a centered activity indicator while the source is
88
+ * loading or the native player reports buffering (initial load and rebuffer).
89
+ * @default false
90
+ */
91
+ showLoadingIndicator?: boolean;
92
+ /**
93
+ * @platform ios
94
+ */
95
+ loadingIndicatorColor?: string;
84
96
  }
85
97
 
86
98
  export interface VideoViewRef {
@@ -173,6 +185,8 @@ const VideoView = React.forwardRef<VideoViewRef, VideoViewProps>(
173
185
  fullscreen = false,
174
186
  paused,
175
187
  speed,
188
+ showLoadingIndicator = false,
189
+ loadingIndicatorColor,
176
190
  onPictureInPictureChange,
177
191
  onFullscreenChange,
178
192
  willEnterFullscreen,
@@ -187,6 +201,48 @@ const VideoView = React.forwardRef<VideoViewRef, VideoViewProps>(
187
201
  const nitroViewManager = React.useRef<VideoViewViewManager | null>(null);
188
202
  const [isManagerReady, setIsManagerReady] = React.useState(false);
189
203
 
204
+ const [hasLoadedMedia, setHasLoadedMedia] = React.useState(false);
205
+ const [isBuffering, setIsBuffering] = React.useState(false);
206
+ const [playerStatus, setPlayerStatus] = React.useState<VideoPlayerStatus>(
207
+ player.status
208
+ );
209
+
210
+ React.useEffect(() => {
211
+ if (!showLoadingIndicator) {
212
+ return;
213
+ }
214
+ setPlayerStatus(player.status);
215
+ setHasLoadedMedia(player.status === 'readyToPlay');
216
+ const onLoadStart = () => {
217
+ setHasLoadedMedia(false);
218
+ setIsBuffering(true);
219
+ };
220
+ const onLoad = () => {
221
+ setHasLoadedMedia(true);
222
+ setIsBuffering(false);
223
+ };
224
+ const onBuffer = (buffering: boolean) => setIsBuffering(buffering);
225
+ const onStatus = (status: VideoPlayerStatus) => setPlayerStatus(status);
226
+
227
+ const subLoadStart = player.addEventListener('onLoadStart', onLoadStart);
228
+ const subLoad = player.addEventListener('onLoad', onLoad);
229
+ const subBuffer = player.addEventListener('onBuffer', onBuffer);
230
+ const subStatus = player.addEventListener('onStatusChange', onStatus);
231
+
232
+ return () => {
233
+ subLoadStart.remove();
234
+ subLoad.remove();
235
+ subBuffer.remove();
236
+ subStatus.remove();
237
+ };
238
+ }, [player, showLoadingIndicator]);
239
+
240
+ const showNativeSpinner =
241
+ showLoadingIndicator &&
242
+ playerStatus !== 'error' &&
243
+ playerStatus !== 'idle' &&
244
+ (!hasLoadedMedia || isBuffering);
245
+
190
246
  const setupViewManager = React.useCallback(
191
247
  (id: number) => {
192
248
  try {
@@ -477,16 +533,42 @@ const VideoView = React.forwardRef<VideoViewRef, VideoViewProps>(
477
533
  }
478
534
  }, [fullscreen, isManagerReady]);
479
535
 
536
+ if (!showLoadingIndicator) {
537
+ return (
538
+ <NativeVideoView
539
+ nitroId={nitroId}
540
+ onNitroIdChange={onNitroIdChange}
541
+ {...props}
542
+ />
543
+ );
544
+ }
545
+
480
546
  return (
481
- <NativeVideoView
482
- nitroId={nitroId}
483
- onNitroIdChange={onNitroIdChange}
484
- {...props}
485
- />
547
+ <View style={props.style} collapsable={false}>
548
+ <NativeVideoView
549
+ nitroId={nitroId}
550
+ onNitroIdChange={onNitroIdChange}
551
+ {...props}
552
+ style={StyleSheet.absoluteFill}
553
+ />
554
+ {showNativeSpinner ? (
555
+ <View style={styles.loadingOverlay} pointerEvents="none">
556
+ <ActivityIndicator size="large" color={loadingIndicatorColor} />
557
+ </View>
558
+ ) : null}
559
+ </View>
486
560
  );
487
561
  }
488
562
  );
489
563
 
564
+ const styles = StyleSheet.create({
565
+ loadingOverlay: {
566
+ ...StyleSheet.absoluteFillObject,
567
+ alignItems: 'center',
568
+ justifyContent: 'center',
569
+ },
570
+ });
571
+
490
572
  VideoView.displayName = 'VideoView';
491
573
 
492
574
  export default React.memo(VideoView);