@stream-io/video-client 0.3.35 → 0.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.es.js CHANGED
@@ -867,6 +867,10 @@ var ErrorCode;
867
867
  * @generated from protobuf enum value: ERROR_CODE_SFU_SHUTTING_DOWN = 600;
868
868
  */
869
869
  ErrorCode[ErrorCode["SFU_SHUTTING_DOWN"] = 600] = "SFU_SHUTTING_DOWN";
870
+ /**
871
+ * @generated from protobuf enum value: ERROR_CODE_SFU_FULL = 700;
872
+ */
873
+ ErrorCode[ErrorCode["SFU_FULL"] = 700] = "SFU_FULL";
870
874
  })(ErrorCode || (ErrorCode = {}));
871
875
  /**
872
876
  * @generated from protobuf enum stream.video.sfu.models.SdkType
@@ -901,6 +905,10 @@ var SdkType;
901
905
  * @generated from protobuf enum value: SDK_TYPE_REACT_NATIVE = 6;
902
906
  */
903
907
  SdkType[SdkType["REACT_NATIVE"] = 6] = "REACT_NATIVE";
908
+ /**
909
+ * @generated from protobuf enum value: SDK_TYPE_UNITY = 7;
910
+ */
911
+ SdkType[SdkType["UNITY"] = 7] = "UNITY";
904
912
  })(SdkType || (SdkType = {}));
905
913
  /**
906
914
  * @generated from protobuf enum stream.video.sfu.models.TrackUnpublishReason
@@ -5328,6 +5336,12 @@ class VideoLayerSetting$Type extends MessageType {
5328
5336
  ],
5329
5337
  },
5330
5338
  { no: 6, name: 'codec', kind: 'message', T: () => Codec },
5339
+ {
5340
+ no: 7,
5341
+ name: 'max_framerate',
5342
+ kind: 'scalar',
5343
+ T: 13 /*ScalarType.UINT32*/,
5344
+ },
5331
5345
  ]);
5332
5346
  }
5333
5347
  create(value) {
@@ -5337,6 +5351,7 @@ class VideoLayerSetting$Type extends MessageType {
5337
5351
  maxBitrate: 0,
5338
5352
  scaleResolutionDownBy: 0,
5339
5353
  priority: 0,
5354
+ maxFramerate: 0,
5340
5355
  };
5341
5356
  globalThis.Object.defineProperty(message, MESSAGE_TYPE, {
5342
5357
  enumerable: false,
@@ -5369,6 +5384,9 @@ class VideoLayerSetting$Type extends MessageType {
5369
5384
  case /* stream.video.sfu.models.Codec codec */ 6:
5370
5385
  message.codec = Codec.internalBinaryRead(reader, reader.uint32(), options, message.codec);
5371
5386
  break;
5387
+ case /* uint32 max_framerate */ 7:
5388
+ message.maxFramerate = reader.uint32();
5389
+ break;
5372
5390
  default:
5373
5391
  let u = options.readUnknownField;
5374
5392
  if (u === 'throw')
@@ -5399,6 +5417,9 @@ class VideoLayerSetting$Type extends MessageType {
5399
5417
  /* stream.video.sfu.models.Codec codec = 6; */
5400
5418
  if (message.codec)
5401
5419
  Codec.internalBinaryWrite(message.codec, writer.tag(6, WireType.LengthDelimited).fork(), options).join();
5420
+ /* uint32 max_framerate = 7; */
5421
+ if (message.maxFramerate !== 0)
5422
+ writer.tag(7, WireType.Varint).uint32(message.maxFramerate);
5402
5423
  let u = options.writeUnknownFields;
5403
5424
  if (u !== false)
5404
5425
  (u == true ? UnknownFieldHandler.onWrite : u)(this.typeName, message, writer);
@@ -5718,9 +5739,6 @@ var DebounceType;
5718
5739
  DebounceType[DebounceType["MEDIUM"] = 600] = "MEDIUM";
5719
5740
  DebounceType[DebounceType["SLOW"] = 1200] = "SLOW";
5720
5741
  })(DebounceType || (DebounceType = {}));
5721
- const isStreamVideoLocalParticipant = (p) => {
5722
- return !!p.isLocalParticipant;
5723
- };
5724
5742
 
5725
5743
  /**
5726
5744
  * @generated from protobuf service stream.video.sfu.signal.SignalServer
@@ -6204,21 +6222,6 @@ const trackTypeToParticipantStreamKey = (trackType) => {
6204
6222
  throw new Error(`Unknown track type: ${exhaustiveTrackTypeCheck}`);
6205
6223
  }
6206
6224
  };
6207
- const trackTypeToDeviceIdKey = (trackType) => {
6208
- switch (trackType) {
6209
- case TrackType.AUDIO:
6210
- return 'audioDeviceId';
6211
- case TrackType.VIDEO:
6212
- return 'videoDeviceId';
6213
- case TrackType.SCREEN_SHARE:
6214
- case TrackType.SCREEN_SHARE_AUDIO:
6215
- case TrackType.UNSPECIFIED:
6216
- return undefined;
6217
- default:
6218
- const exhaustiveTrackTypeCheck = trackType;
6219
- throw new Error(`Unknown track type: ${exhaustiveTrackTypeCheck}`);
6220
- }
6221
- };
6222
6225
  const muteTypeToTrackType = (muteType) => {
6223
6226
  switch (muteType) {
6224
6227
  case 'audio':
@@ -6610,14 +6613,11 @@ class Publisher {
6610
6613
  }));
6611
6614
  }
6612
6615
  else {
6613
- const deviceId = track.getSettings().deviceId;
6614
- const audioOrVideoDeviceKey = trackTypeToDeviceIdKey(trackType);
6615
6616
  this.state.updateParticipant(this.sfuClient.sessionId, (p) => {
6616
6617
  return {
6617
6618
  publishedTracks: p.publishedTracks.includes(trackType)
6618
6619
  ? p.publishedTracks
6619
6620
  : [...p.publishedTracks, trackType],
6620
- ...(audioOrVideoDeviceKey && { [audioOrVideoDeviceKey]: deviceId }),
6621
6621
  [audioOrVideoOrScreenShareStream]: mediaStream,
6622
6622
  };
6623
6623
  });
@@ -6635,8 +6635,8 @@ class Publisher {
6635
6635
  }
6636
6636
  });
6637
6637
  };
6638
- this.updateVideoPublishQuality = async (enabledRids) => {
6639
- logger$3('info', 'Update publish quality, requested rids by SFU:', enabledRids);
6638
+ this.updateVideoPublishQuality = async (enabledLayers) => {
6639
+ logger$3('info', 'Update publish quality, requested layers by SFU:', enabledLayers);
6640
6640
  const videoSender = this.transceiverRegistry[TrackType.VIDEO]?.sender;
6641
6641
  if (!videoSender) {
6642
6642
  logger$3('warn', 'Update publish quality, no video sender found.');
@@ -6648,6 +6648,9 @@ class Publisher {
6648
6648
  return;
6649
6649
  }
6650
6650
  let changed = false;
6651
+ let enabledRids = enabledLayers
6652
+ .filter((ly) => ly.active)
6653
+ .map((ly) => ly.name);
6651
6654
  params.encodings.forEach((enc) => {
6652
6655
  // flip 'active' flag only when necessary
6653
6656
  const shouldEnable = enabledRids.includes(enc.rid);
@@ -6655,17 +6658,36 @@ class Publisher {
6655
6658
  enc.active = shouldEnable;
6656
6659
  changed = true;
6657
6660
  }
6661
+ if (shouldEnable) {
6662
+ let layer = enabledLayers.find((vls) => vls.name === enc.rid);
6663
+ if (layer !== undefined) {
6664
+ if (layer.scaleResolutionDownBy >= 1 &&
6665
+ layer.scaleResolutionDownBy !== enc.scaleResolutionDownBy) {
6666
+ logger$3('debug', '[dynascale]: setting scaleResolutionDownBy from server', 'layer', layer.name, 'scale-resolution-down-by', layer.scaleResolutionDownBy);
6667
+ enc.scaleResolutionDownBy = layer.scaleResolutionDownBy;
6668
+ changed = true;
6669
+ }
6670
+ if (layer.maxBitrate > 0 && layer.maxBitrate !== enc.maxBitrate) {
6671
+ logger$3('debug', '[dynascale] setting max-bitrate from the server', 'layer', layer.name, 'max-bitrate', layer.maxBitrate);
6672
+ enc.maxBitrate = layer.maxBitrate;
6673
+ changed = true;
6674
+ }
6675
+ if (layer.maxFramerate > 0 &&
6676
+ layer.maxFramerate !== enc.maxFramerate) {
6677
+ logger$3('debug', '[dynascale]: setting maxFramerate from server', 'layer', layer.name, 'max-framerate', layer.maxFramerate);
6678
+ enc.maxFramerate = layer.maxFramerate;
6679
+ changed = true;
6680
+ }
6681
+ }
6682
+ }
6658
6683
  });
6659
- const activeRids = params.encodings
6660
- .filter((e) => e.active)
6661
- .map((e) => e.rid)
6662
- .join(', ');
6684
+ const activeLayers = params.encodings.filter((e) => e.active);
6663
6685
  if (changed) {
6664
6686
  await videoSender.setParameters(params);
6665
- logger$3('info', `Update publish quality, enabled rids: ${activeRids}`);
6687
+ logger$3('info', `Update publish quality, enabled rids: `, activeLayers);
6666
6688
  }
6667
6689
  else {
6668
- logger$3('info', `Update publish quality, no change: ${activeRids}`);
6690
+ logger$3('info', `Update publish quality, no change: `, activeLayers);
6669
6691
  }
6670
6692
  };
6671
6693
  /**
@@ -8437,7 +8459,7 @@ class CallState {
8437
8459
  // maintain stable-sort by mutating the participants stored
8438
8460
  // in the original subject
8439
8461
  map$1((ps) => ps.sort(this.sortParticipantsBy)), shareReplay({ bufferSize: 1, refCount: true }));
8440
- this.localParticipant$ = this.participants$.pipe(map$1((participants) => participants.find(isStreamVideoLocalParticipant)), shareReplay({ bufferSize: 1, refCount: true }));
8462
+ this.localParticipant$ = this.participants$.pipe(map$1((participants) => participants.find((p) => p.isLocalParticipant)), shareReplay({ bufferSize: 1, refCount: true }));
8441
8463
  this.remoteParticipants$ = this.participants$.pipe(map$1((participants) => participants.filter((p) => !p.isLocalParticipant)), shareReplay({ bufferSize: 1, refCount: true }));
8442
8464
  this.pinnedParticipants$ = this.participants$.pipe(map$1((participants) => participants.filter((p) => !!p.pin)), shareReplay({ bufferSize: 1, refCount: true }));
8443
8465
  this.dominantSpeaker$ = this.participants$.pipe(map$1((participants) => participants.find((p) => p.isDominantSpeaker)), shareReplay({ bufferSize: 1, refCount: true }));
@@ -8801,7 +8823,7 @@ const watchChangePublishQuality = (dispatcher, call) => {
8801
8823
  const { videoSenders } = e.eventPayload.changePublishQuality;
8802
8824
  videoSenders.forEach((videoSender) => {
8803
8825
  const { layers } = videoSender;
8804
- call.updatePublishQuality(layers.filter((l) => l.active).map((l) => l.name));
8826
+ call.updatePublishQuality(layers.filter((l) => l.active));
8805
8827
  });
8806
8828
  });
8807
8829
  };
@@ -9172,14 +9194,7 @@ const reconcileParticipantLocalState = (target, source) => {
9172
9194
  if (!source)
9173
9195
  return target;
9174
9196
  // copy everything from source to target
9175
- Object.assign(target, source);
9176
- if (isStreamVideoLocalParticipant(source) &&
9177
- isStreamVideoLocalParticipant(target)) {
9178
- target.audioDeviceId = source.audioDeviceId;
9179
- target.videoDeviceId = source.videoDeviceId;
9180
- target.audioOutputDeviceId = source.audioOutputDeviceId;
9181
- }
9182
- return target;
9197
+ return Object.assign(target, source);
9183
9198
  };
9184
9199
 
9185
9200
  /**
@@ -9782,24 +9797,20 @@ class DynascaleManager {
9782
9797
  }
9783
9798
  });
9784
9799
  });
9785
- const sinkIdSubscription = combineLatest([
9786
- this.call.state.localParticipant$,
9787
- this.call.speaker.state.selectedDevice$,
9788
- ]).subscribe(([p, selectedDevice]) => {
9789
- const deviceId = getSdkInfo()?.type === SdkType.REACT
9790
- ? p?.audioOutputDeviceId
9791
- : selectedDevice;
9792
- if ('setSinkId' in audioElement && typeof deviceId === 'string') {
9793
- // @ts-expect-error setSinkId is not yet in the lib
9794
- audioElement.setSinkId(deviceId);
9795
- }
9796
- });
9800
+ const sinkIdSubscription = !('setSinkId' in audioElement)
9801
+ ? null
9802
+ : this.call.speaker.state.selectedDevice$.subscribe((deviceId) => {
9803
+ if (deviceId) {
9804
+ // @ts-expect-error setSinkId is not yet in the lib
9805
+ audioElement.setSinkId(deviceId);
9806
+ }
9807
+ });
9797
9808
  const volumeSubscription = this.call.speaker.state.volume$.subscribe((volume) => {
9798
9809
  audioElement.volume = volume;
9799
9810
  });
9800
9811
  audioElement.autoplay = true;
9801
9812
  return () => {
9802
- sinkIdSubscription.unsubscribe();
9813
+ sinkIdSubscription?.unsubscribe();
9803
9814
  volumeSubscription.unsubscribe();
9804
9815
  updateMediaStreamSubscription.unsubscribe();
9805
9816
  };
@@ -9848,11 +9859,12 @@ class PermissionsContext {
9848
9859
  * within the call.
9849
9860
  *
9850
9861
  * @param permission the permission to check for.
9862
+ * @param settings the call settings to check against (optional).
9851
9863
  */
9852
- this.canRequest = (permission) => {
9853
- if (!this.settings)
9864
+ this.canRequest = (permission, settings = this.settings) => {
9865
+ if (!settings)
9854
9866
  return false;
9855
- const { audio, video, screensharing } = this.settings;
9867
+ const { audio, video, screensharing } = settings;
9856
9868
  switch (permission) {
9857
9869
  case OwnCapability.SEND_AUDIO:
9858
9870
  return audio.access_request_enabled;
@@ -11091,7 +11103,7 @@ class Call {
11091
11103
  *
11092
11104
  * @param params.ring if set to true, a `call.ring` event will be sent to the call members.
11093
11105
  * @param params.notify if set to true, a `call.notification` event will be sent to the call members.
11094
- * @param params.members_limit the members limit.
11106
+ * @param params.members_limit the total number of members to return as part of the response.
11095
11107
  */
11096
11108
  this.get = async (params) => {
11097
11109
  const response = await this.streamClient.get(this.streamClientBasePath, params);
@@ -11455,15 +11467,12 @@ class Call {
11455
11467
  this.state.setServerSidePins(pins);
11456
11468
  this.reconnectAttempts = 0; // reset the reconnect attempts counter
11457
11469
  this.state.setCallingState(CallingState.JOINED);
11458
- // React uses a different device management for now
11459
- if (getSdkInfo()?.type !== SdkType.REACT) {
11460
- try {
11461
- await this.initCamera();
11462
- await this.initMic();
11463
- }
11464
- catch (error) {
11465
- this.logger('warn', 'Camera and/or mic init failed during join call');
11466
- }
11470
+ try {
11471
+ await this.initCamera();
11472
+ await this.initMic();
11473
+ }
11474
+ catch (error) {
11475
+ this.logger('warn', 'Camera and/or mic init failed during join call');
11467
11476
  }
11468
11477
  // 3. once we have the "joinResponse", and possibly reconciled the local state
11469
11478
  // we schedule a fast subscription update for all remote participants
@@ -11690,56 +11699,6 @@ class Call {
11690
11699
  this.stopReportingStatsFor = (sessionId) => {
11691
11700
  return this.statsReporter?.stopReportingStatsFor(sessionId);
11692
11701
  };
11693
- /**
11694
- * Sets the used audio output device (`audioOutputDeviceId` of the [`localParticipant$`](./StreamVideoClient.md/#readonlystatestore).
11695
- *
11696
- * This method only stores the selection, if you're using custom UI components, you'll have to implement the audio switching, for more information see: https://developer.mozilla.org/en-US/docs/Web/API/HTMLMediaElement/sinkId.
11697
- *
11698
- *
11699
- * @param deviceId the selected device, `undefined` means the user wants to use the system's default audio output
11700
- *
11701
- * @deprecated use `call.speaker` instead
11702
- */
11703
- this.setAudioOutputDevice = (deviceId) => {
11704
- if (!this.sfuClient)
11705
- return;
11706
- this.state.updateParticipant(this.sfuClient.sessionId, {
11707
- audioOutputDeviceId: deviceId,
11708
- });
11709
- };
11710
- /**
11711
- * Sets the `audioDeviceId` property of the [`localParticipant$`](./StreamVideoClient.md/#readonlystatestore)).
11712
- *
11713
- * This method only stores the selection, if you want to start publishing a media stream call the [`publishAudioStream` method](#publishaudiostream) that will set `audioDeviceId` as well.
11714
- *
11715
- *
11716
- * @param deviceId the selected device, pass `undefined` to clear the device selection
11717
- *
11718
- * @deprecated use call.microphone.select
11719
- */
11720
- this.setAudioDevice = (deviceId) => {
11721
- if (!this.sfuClient)
11722
- return;
11723
- this.state.updateParticipant(this.sfuClient.sessionId, {
11724
- audioDeviceId: deviceId,
11725
- });
11726
- };
11727
- /**
11728
- * Sets the `videoDeviceId` property of the [`localParticipant$`](./StreamVideoClient.md/#readonlystatestore).
11729
- *
11730
- * This method only stores the selection, if you want to start publishing a media stream call the [`publishVideoStream` method](#publishvideostream) that will set `videoDeviceId` as well.
11731
- *
11732
- * @param deviceId the selected device, pass `undefined` to clear the device selection
11733
- *
11734
- * @deprecated use call.camera.select
11735
- */
11736
- this.setVideoDevice = (deviceId) => {
11737
- if (!this.sfuClient)
11738
- return;
11739
- this.state.updateParticipant(this.sfuClient.sessionId, {
11740
- videoDeviceId: deviceId,
11741
- });
11742
- };
11743
11702
  /**
11744
11703
  * Resets the last sent reaction for the user holding the given `sessionId`. This is a local action, it won't reset the reaction on the backend.
11745
11704
  *
@@ -11763,8 +11722,8 @@ class Call {
11763
11722
  * @param enabledRids
11764
11723
  * @returns
11765
11724
  */
11766
- this.updatePublishQuality = async (enabledRids) => {
11767
- return this.publisher?.updateVideoPublishQuality(enabledRids);
11725
+ this.updatePublishQuality = async (enabledLayers) => {
11726
+ return this.publisher?.updateVideoPublishQuality(enabledLayers);
11768
11727
  };
11769
11728
  this.assertCallJoined = () => {
11770
11729
  return new Promise((resolve) => {
@@ -13976,7 +13935,7 @@ class StreamClient {
13976
13935
  });
13977
13936
  };
13978
13937
  this.getUserAgent = () => {
13979
- const version = "0.3.35" ;
13938
+ const version = "0.4.0" ;
13980
13939
  return (this.userAgent ||
13981
13940
  `stream-video-javascript-client-${this.node ? 'node' : 'browser'}-${version}`);
13982
13941
  };
@@ -14510,5 +14469,5 @@ class StreamVideoServerClient extends StreamVideoClient {
14510
14469
  }
14511
14470
  }
14512
14471
 
14513
- export { AudioSettingsDefaultDeviceEnum, AudioSettingsRequestDefaultDeviceEnum, browsers as Browsers, Call, CallState, CallType, CallTypes, CallingState, CameraManager, CameraManagerState, CreateDeviceRequestPushProviderEnum, DebounceType, DynascaleManager, ErrorFromResponse, InputMediaDeviceManager, InputMediaDeviceManagerState, LayoutSettingsNameEnum, LayoutSettingsRequestNameEnum, MicrophoneManager, MicrophoneManagerState, OwnCapability, RecordSettingsRequestModeEnum, RecordSettingsRequestQualityEnum, rxUtils as RxUtils, ScreenShareManager, ScreenShareState, events as SfuEvents, models as SfuModels, SpeakerManager, SpeakerState, StreamSfuClient, StreamVideoClient, StreamVideoReadOnlyStateStore, StreamVideoServerClient, StreamVideoWriteableStateStore, TranscriptionSettingsModeEnum, TranscriptionSettingsRequestModeEnum, VideoSettingsCameraFacingEnum, VideoSettingsRequestCameraFacingEnum, ViewportTracker, VisibilityState, checkIfAudioOutputChangeSupported, combineComparators, conditional, createSoundDetector, defaultSortPreset, descending, disposeOfMediaStream, dominantSpeaker, getAudioDevices, getAudioOutputDevices, getAudioStream, getClientDetails, getDeviceInfo, getLogger, getOSInfo, getScreenShareStream, getSdkInfo, getVideoDevices, getVideoStream, isStreamVideoLocalParticipant, livestreamOrAudioRoomSortPreset, logLevels, logToConsole, name, noopComparator, paginatedLayoutSortPreset, pinned, publishingAudio, publishingVideo, reactionType, role, screenSharing, setDeviceInfo, setLogLevel, setLogger, setOSInfo, setSdkInfo, speakerLayoutSortPreset, speaking, watchForAddedDefaultAudioDevice, watchForAddedDefaultAudioOutputDevice, watchForAddedDefaultVideoDevice, watchForDisconnectedAudioDevice, watchForDisconnectedAudioOutputDevice, watchForDisconnectedVideoDevice };
14472
+ export { AudioSettingsDefaultDeviceEnum, AudioSettingsRequestDefaultDeviceEnum, browsers as Browsers, Call, CallState, CallType, CallTypes, CallingState, CameraManager, CameraManagerState, CreateDeviceRequestPushProviderEnum, DebounceType, DynascaleManager, ErrorFromResponse, InputMediaDeviceManager, InputMediaDeviceManagerState, LayoutSettingsNameEnum, LayoutSettingsRequestNameEnum, MicrophoneManager, MicrophoneManagerState, OwnCapability, RecordSettingsRequestModeEnum, RecordSettingsRequestQualityEnum, rxUtils as RxUtils, ScreenShareManager, ScreenShareState, events as SfuEvents, models as SfuModels, SpeakerManager, SpeakerState, StreamSfuClient, StreamVideoClient, StreamVideoReadOnlyStateStore, StreamVideoServerClient, StreamVideoWriteableStateStore, TranscriptionSettingsModeEnum, TranscriptionSettingsRequestModeEnum, VideoSettingsCameraFacingEnum, VideoSettingsRequestCameraFacingEnum, ViewportTracker, VisibilityState, checkIfAudioOutputChangeSupported, combineComparators, conditional, createSoundDetector, defaultSortPreset, descending, disposeOfMediaStream, dominantSpeaker, getAudioDevices, getAudioOutputDevices, getAudioStream, getClientDetails, getDeviceInfo, getLogger, getOSInfo, getScreenShareStream, getSdkInfo, getVideoDevices, getVideoStream, livestreamOrAudioRoomSortPreset, logLevels, logToConsole, name, noopComparator, paginatedLayoutSortPreset, pinned, publishingAudio, publishingVideo, reactionType, role, screenSharing, setDeviceInfo, setLogLevel, setLogger, setOSInfo, setSdkInfo, speakerLayoutSortPreset, speaking, watchForAddedDefaultAudioDevice, watchForAddedDefaultAudioOutputDevice, watchForAddedDefaultVideoDevice, watchForDisconnectedAudioDevice, watchForDisconnectedAudioOutputDevice, watchForDisconnectedVideoDevice };
14514
14473
  //# sourceMappingURL=index.es.js.map