@stream-io/video-client 1.32.0 → 1.33.1
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/CHANGELOG.md +16 -0
- package/dist/index.browser.es.js +344 -91
- package/dist/index.browser.es.js.map +1 -1
- package/dist/index.cjs.js +345 -92
- package/dist/index.cjs.js.map +1 -1
- package/dist/index.es.js +344 -91
- package/dist/index.es.js.map +1 -1
- package/dist/src/Call.d.ts +3 -2
- package/dist/src/devices/AudioDeviceManager.d.ts +25 -0
- package/dist/src/devices/AudioDeviceManagerState.d.ts +24 -0
- package/dist/src/devices/CameraManager.d.ts +2 -2
- package/dist/src/devices/CameraManagerState.d.ts +3 -4
- package/dist/src/devices/{InputMediaDeviceManager.d.ts → DeviceManager.d.ts} +6 -6
- package/dist/src/devices/{InputMediaDeviceManagerState.d.ts → DeviceManagerState.d.ts} +4 -4
- package/dist/src/devices/MicrophoneManager.d.ts +5 -3
- package/dist/src/devices/MicrophoneManagerState.d.ts +6 -10
- package/dist/src/devices/ScreenShareManager.d.ts +4 -2
- package/dist/src/devices/ScreenShareState.d.ts +6 -2
- package/dist/src/devices/SpeakerState.d.ts +4 -4
- package/dist/src/devices/index.d.ts +2 -2
- package/dist/src/gen/coordinator/index.d.ts +169 -2
- package/dist/src/gen/video/sfu/models/models.d.ts +43 -0
- package/dist/src/rtc/BasePeerConnection.d.ts +2 -12
- package/dist/src/rtc/Publisher.d.ts +9 -6
- package/dist/src/rtc/Subscriber.d.ts +2 -1
- package/dist/src/rtc/TransceiverCache.d.ts +10 -11
- package/dist/src/rtc/index.d.ts +1 -1
- package/dist/src/rtc/{videoLayers.d.ts → layers.d.ts} +7 -1
- package/dist/src/rtc/types.d.ts +31 -0
- package/dist/src/sorting/participants.d.ts +5 -2
- package/package.json +3 -2
- package/src/Call.ts +13 -6
- package/src/__tests__/Call.publishing.test.ts +14 -3
- package/src/__tests__/StreamVideoClient.api.test.ts +1 -1
- package/src/devices/AudioDeviceManager.ts +61 -0
- package/src/devices/AudioDeviceManagerState.ts +44 -0
- package/src/devices/CameraManager.ts +4 -4
- package/src/devices/CameraManagerState.ts +9 -8
- package/src/devices/{InputMediaDeviceManager.ts → DeviceManager.ts} +11 -8
- package/src/devices/{InputMediaDeviceManagerState.ts → DeviceManagerState.ts} +7 -4
- package/src/devices/MicrophoneManager.ts +26 -6
- package/src/devices/MicrophoneManagerState.ts +18 -19
- package/src/devices/ScreenShareManager.ts +23 -4
- package/src/devices/ScreenShareState.ts +11 -3
- package/src/devices/SpeakerState.ts +6 -14
- package/src/devices/__tests__/CameraManager.test.ts +1 -0
- package/src/devices/__tests__/{InputMediaDeviceManager.test.ts → DeviceManager.test.ts} +4 -4
- package/src/devices/__tests__/{InputMediaDeviceManagerFilters.test.ts → DeviceManagerFilters.test.ts} +4 -4
- package/src/devices/__tests__/{InputMediaDeviceManagerState.test.ts → DeviceManagerState.test.ts} +2 -2
- package/src/devices/__tests__/MicrophoneManager.test.ts +41 -1
- package/src/devices/__tests__/NoiseCancellationStub.ts +3 -1
- package/src/devices/__tests__/ScreenShareManager.test.ts +5 -1
- package/src/devices/index.ts +2 -2
- package/src/events/__tests__/internal.test.ts +25 -11
- package/src/gen/coordinator/index.ts +169 -2
- package/src/gen/video/sfu/models/models.ts +65 -0
- package/src/rtc/BasePeerConnection.ts +1 -16
- package/src/rtc/Publisher.ts +74 -31
- package/src/rtc/Subscriber.ts +2 -4
- package/src/rtc/TransceiverCache.ts +23 -27
- package/src/rtc/__tests__/Publisher.test.ts +61 -29
- package/src/rtc/__tests__/{videoLayers.test.ts → layers.test.ts} +76 -1
- package/src/rtc/index.ts +2 -1
- package/src/rtc/{videoLayers.ts → layers.ts} +28 -7
- package/src/rtc/types.ts +44 -0
- package/src/sorting/__tests__/sorting.test.ts +106 -0
- package/src/sorting/participants.ts +30 -14
- package/src/sorting/presets.ts +16 -4
- package/src/store/CallState.ts +36 -10
- package/src/store/__tests__/CallState.test.ts +20 -2
|
@@ -86,6 +86,12 @@ export interface AudioSettingsRequest {
|
|
|
86
86
|
* @memberof AudioSettingsRequest
|
|
87
87
|
*/
|
|
88
88
|
default_device: AudioSettingsRequestDefaultDeviceEnum;
|
|
89
|
+
/**
|
|
90
|
+
*
|
|
91
|
+
* @type {boolean}
|
|
92
|
+
* @memberof AudioSettingsRequest
|
|
93
|
+
*/
|
|
94
|
+
hifi_audio_enabled?: boolean;
|
|
89
95
|
/**
|
|
90
96
|
*
|
|
91
97
|
* @type {boolean}
|
|
@@ -146,6 +152,12 @@ export interface AudioSettingsResponse {
|
|
|
146
152
|
* @memberof AudioSettingsResponse
|
|
147
153
|
*/
|
|
148
154
|
default_device: AudioSettingsResponseDefaultDeviceEnum;
|
|
155
|
+
/**
|
|
156
|
+
*
|
|
157
|
+
* @type {boolean}
|
|
158
|
+
* @memberof AudioSettingsResponse
|
|
159
|
+
*/
|
|
160
|
+
hifi_audio_enabled?: boolean;
|
|
149
161
|
/**
|
|
150
162
|
*
|
|
151
163
|
* @type {boolean}
|
|
@@ -408,6 +420,24 @@ export interface CallClosedCaption {
|
|
|
408
420
|
* @memberof CallClosedCaption
|
|
409
421
|
*/
|
|
410
422
|
end_time: string;
|
|
423
|
+
/**
|
|
424
|
+
*
|
|
425
|
+
* @type {string}
|
|
426
|
+
* @memberof CallClosedCaption
|
|
427
|
+
*/
|
|
428
|
+
id: string;
|
|
429
|
+
/**
|
|
430
|
+
*
|
|
431
|
+
* @type {string}
|
|
432
|
+
* @memberof CallClosedCaption
|
|
433
|
+
*/
|
|
434
|
+
language: string;
|
|
435
|
+
/**
|
|
436
|
+
*
|
|
437
|
+
* @type {string}
|
|
438
|
+
* @memberof CallClosedCaption
|
|
439
|
+
*/
|
|
440
|
+
service?: string;
|
|
411
441
|
/**
|
|
412
442
|
*
|
|
413
443
|
* @type {string}
|
|
@@ -426,6 +456,12 @@ export interface CallClosedCaption {
|
|
|
426
456
|
* @memberof CallClosedCaption
|
|
427
457
|
*/
|
|
428
458
|
text: string;
|
|
459
|
+
/**
|
|
460
|
+
*
|
|
461
|
+
* @type {boolean}
|
|
462
|
+
* @memberof CallClosedCaption
|
|
463
|
+
*/
|
|
464
|
+
translated: boolean;
|
|
429
465
|
/**
|
|
430
466
|
*
|
|
431
467
|
* @type {UserResponse}
|
|
@@ -917,6 +953,18 @@ export interface CallIngressResponse {
|
|
|
917
953
|
* @memberof CallIngressResponse
|
|
918
954
|
*/
|
|
919
955
|
rtmp: RTMPIngress;
|
|
956
|
+
/**
|
|
957
|
+
*
|
|
958
|
+
* @type {SRTIngress}
|
|
959
|
+
* @memberof CallIngressResponse
|
|
960
|
+
*/
|
|
961
|
+
srt: SRTIngress;
|
|
962
|
+
/**
|
|
963
|
+
*
|
|
964
|
+
* @type {WHIPIngress}
|
|
965
|
+
* @memberof CallIngressResponse
|
|
966
|
+
*/
|
|
967
|
+
whip: WHIPIngress;
|
|
920
968
|
}
|
|
921
969
|
/**
|
|
922
970
|
* This event is sent when a call is started. Clients receiving this event should start the call.
|
|
@@ -1791,6 +1839,12 @@ export interface CallResponse {
|
|
|
1791
1839
|
* @memberof CallResponse
|
|
1792
1840
|
*/
|
|
1793
1841
|
transcribing: boolean;
|
|
1842
|
+
/**
|
|
1843
|
+
*
|
|
1844
|
+
* @type {boolean}
|
|
1845
|
+
* @memberof CallResponse
|
|
1846
|
+
*/
|
|
1847
|
+
translating: boolean;
|
|
1794
1848
|
/**
|
|
1795
1849
|
* The type of call
|
|
1796
1850
|
* @type {string}
|
|
@@ -2099,6 +2153,12 @@ export interface CallSessionParticipantLeftEvent {
|
|
|
2099
2153
|
* @memberof CallSessionParticipantLeftEvent
|
|
2100
2154
|
*/
|
|
2101
2155
|
participant: CallParticipantResponse;
|
|
2156
|
+
/**
|
|
2157
|
+
* The reason why the participant left the session
|
|
2158
|
+
* @type {string}
|
|
2159
|
+
* @memberof CallSessionParticipantLeftEvent
|
|
2160
|
+
*/
|
|
2161
|
+
reason?: string;
|
|
2102
2162
|
/**
|
|
2103
2163
|
* Call session ID
|
|
2104
2164
|
* @type {string}
|
|
@@ -2732,7 +2792,7 @@ export interface CallUpdatedEvent {
|
|
|
2732
2792
|
*/
|
|
2733
2793
|
created_at: string;
|
|
2734
2794
|
/**
|
|
2735
|
-
* The type of event: "call.
|
|
2795
|
+
* The type of event: "call.updated" in this case
|
|
2736
2796
|
* @type {string}
|
|
2737
2797
|
* @memberof CallUpdatedEvent
|
|
2738
2798
|
*/
|
|
@@ -2835,6 +2895,12 @@ export interface CallUserMutedEvent {
|
|
|
2835
2895
|
* @memberof CallUserMutedEvent
|
|
2836
2896
|
*/
|
|
2837
2897
|
muted_user_ids: Array<string>;
|
|
2898
|
+
/**
|
|
2899
|
+
*
|
|
2900
|
+
* @type {string}
|
|
2901
|
+
* @memberof CallUserMutedEvent
|
|
2902
|
+
*/
|
|
2903
|
+
reason: string;
|
|
2838
2904
|
/**
|
|
2839
2905
|
* The type of event: "call.user_muted" in this case
|
|
2840
2906
|
* @type {string}
|
|
@@ -3787,6 +3853,12 @@ export interface GetCallReportResponse {
|
|
|
3787
3853
|
* @memberof GetCallReportResponse
|
|
3788
3854
|
*/
|
|
3789
3855
|
report: ReportResponse;
|
|
3856
|
+
/**
|
|
3857
|
+
*
|
|
3858
|
+
* @type {CallSessionResponse}
|
|
3859
|
+
* @memberof GetCallReportResponse
|
|
3860
|
+
*/
|
|
3861
|
+
session?: CallSessionResponse;
|
|
3790
3862
|
/**
|
|
3791
3863
|
*
|
|
3792
3864
|
* @type {string}
|
|
@@ -4928,6 +5000,7 @@ export const OwnCapability = {
|
|
|
4928
5000
|
REMOVE_CALL_MEMBER: 'remove-call-member',
|
|
4929
5001
|
SCREENSHARE: 'screenshare',
|
|
4930
5002
|
SEND_AUDIO: 'send-audio',
|
|
5003
|
+
SEND_CLOSED_CAPTIONS_CALL: 'send-closed-captions-call',
|
|
4931
5004
|
SEND_VIDEO: 'send-video',
|
|
4932
5005
|
START_BROADCAST_CALL: 'start-broadcast-call',
|
|
4933
5006
|
START_CLOSED_CAPTIONS_CALL: 'start-closed-captions-call',
|
|
@@ -6184,6 +6257,19 @@ export interface SFUResponse {
|
|
|
6184
6257
|
*/
|
|
6185
6258
|
ws_endpoint: string;
|
|
6186
6259
|
}
|
|
6260
|
+
/**
|
|
6261
|
+
*
|
|
6262
|
+
* @export
|
|
6263
|
+
* @interface SRTIngress
|
|
6264
|
+
*/
|
|
6265
|
+
export interface SRTIngress {
|
|
6266
|
+
/**
|
|
6267
|
+
*
|
|
6268
|
+
* @type {string}
|
|
6269
|
+
* @memberof SRTIngress
|
|
6270
|
+
*/
|
|
6271
|
+
address: string;
|
|
6272
|
+
}
|
|
6187
6273
|
/**
|
|
6188
6274
|
*
|
|
6189
6275
|
* @export
|
|
@@ -6349,6 +6435,25 @@ export interface SortParamRequest {
|
|
|
6349
6435
|
*/
|
|
6350
6436
|
field?: string;
|
|
6351
6437
|
}
|
|
6438
|
+
/**
|
|
6439
|
+
*
|
|
6440
|
+
* @export
|
|
6441
|
+
* @interface SpeechSegmentConfig
|
|
6442
|
+
*/
|
|
6443
|
+
export interface SpeechSegmentConfig {
|
|
6444
|
+
/**
|
|
6445
|
+
*
|
|
6446
|
+
* @type {number}
|
|
6447
|
+
* @memberof SpeechSegmentConfig
|
|
6448
|
+
*/
|
|
6449
|
+
max_speech_caption_ms?: number;
|
|
6450
|
+
/**
|
|
6451
|
+
*
|
|
6452
|
+
* @type {number}
|
|
6453
|
+
* @memberof SpeechSegmentConfig
|
|
6454
|
+
*/
|
|
6455
|
+
silence_duration_ms?: number;
|
|
6456
|
+
}
|
|
6352
6457
|
/**
|
|
6353
6458
|
*
|
|
6354
6459
|
* @export
|
|
@@ -6373,6 +6478,12 @@ export interface StartClosedCaptionsRequest {
|
|
|
6373
6478
|
* @memberof StartClosedCaptionsRequest
|
|
6374
6479
|
*/
|
|
6375
6480
|
language?: StartClosedCaptionsRequestLanguageEnum;
|
|
6481
|
+
/**
|
|
6482
|
+
*
|
|
6483
|
+
* @type {SpeechSegmentConfig}
|
|
6484
|
+
* @memberof StartClosedCaptionsRequest
|
|
6485
|
+
*/
|
|
6486
|
+
speech_segment_config?: SpeechSegmentConfig;
|
|
6376
6487
|
}
|
|
6377
6488
|
|
|
6378
6489
|
/**
|
|
@@ -6937,7 +7048,19 @@ export interface TranscriptionSettingsRequest {
|
|
|
6937
7048
|
* @type {string}
|
|
6938
7049
|
* @memberof TranscriptionSettingsRequest
|
|
6939
7050
|
*/
|
|
6940
|
-
mode
|
|
7051
|
+
mode?: TranscriptionSettingsRequestModeEnum;
|
|
7052
|
+
/**
|
|
7053
|
+
*
|
|
7054
|
+
* @type {SpeechSegmentConfig}
|
|
7055
|
+
* @memberof TranscriptionSettingsRequest
|
|
7056
|
+
*/
|
|
7057
|
+
speech_segment_config?: SpeechSegmentConfig;
|
|
7058
|
+
/**
|
|
7059
|
+
*
|
|
7060
|
+
* @type {TranslationSettings}
|
|
7061
|
+
* @memberof TranscriptionSettingsRequest
|
|
7062
|
+
*/
|
|
7063
|
+
translation?: TranslationSettings;
|
|
6941
7064
|
}
|
|
6942
7065
|
|
|
6943
7066
|
/**
|
|
@@ -7031,6 +7154,18 @@ export interface TranscriptionSettingsResponse {
|
|
|
7031
7154
|
* @memberof TranscriptionSettingsResponse
|
|
7032
7155
|
*/
|
|
7033
7156
|
mode: TranscriptionSettingsResponseModeEnum;
|
|
7157
|
+
/**
|
|
7158
|
+
*
|
|
7159
|
+
* @type {SpeechSegmentConfig}
|
|
7160
|
+
* @memberof TranscriptionSettingsResponse
|
|
7161
|
+
*/
|
|
7162
|
+
speech_segment_config?: SpeechSegmentConfig;
|
|
7163
|
+
/**
|
|
7164
|
+
*
|
|
7165
|
+
* @type {TranslationSettings}
|
|
7166
|
+
* @memberof TranscriptionSettingsResponse
|
|
7167
|
+
*/
|
|
7168
|
+
translation?: TranslationSettings;
|
|
7034
7169
|
}
|
|
7035
7170
|
|
|
7036
7171
|
/**
|
|
@@ -7100,6 +7235,25 @@ export const TranscriptionSettingsResponseModeEnum = {
|
|
|
7100
7235
|
export type TranscriptionSettingsResponseModeEnum =
|
|
7101
7236
|
(typeof TranscriptionSettingsResponseModeEnum)[keyof typeof TranscriptionSettingsResponseModeEnum];
|
|
7102
7237
|
|
|
7238
|
+
/**
|
|
7239
|
+
*
|
|
7240
|
+
* @export
|
|
7241
|
+
* @interface TranslationSettings
|
|
7242
|
+
*/
|
|
7243
|
+
export interface TranslationSettings {
|
|
7244
|
+
/**
|
|
7245
|
+
*
|
|
7246
|
+
* @type {boolean}
|
|
7247
|
+
* @memberof TranslationSettings
|
|
7248
|
+
*/
|
|
7249
|
+
enabled?: boolean;
|
|
7250
|
+
/**
|
|
7251
|
+
*
|
|
7252
|
+
* @type {Array<string>}
|
|
7253
|
+
* @memberof TranslationSettings
|
|
7254
|
+
*/
|
|
7255
|
+
languages?: Array<string>;
|
|
7256
|
+
}
|
|
7103
7257
|
/**
|
|
7104
7258
|
* UnblockUserRequest is the payload for unblocking a user.
|
|
7105
7259
|
* @export
|
|
@@ -7925,6 +8079,19 @@ export const VideoSettingsResponseCameraFacingEnum = {
|
|
|
7925
8079
|
export type VideoSettingsResponseCameraFacingEnum =
|
|
7926
8080
|
(typeof VideoSettingsResponseCameraFacingEnum)[keyof typeof VideoSettingsResponseCameraFacingEnum];
|
|
7927
8081
|
|
|
8082
|
+
/**
|
|
8083
|
+
*
|
|
8084
|
+
* @export
|
|
8085
|
+
* @interface WHIPIngress
|
|
8086
|
+
*/
|
|
8087
|
+
export interface WHIPIngress {
|
|
8088
|
+
/**
|
|
8089
|
+
* URL for a new whip input, every time a new link is created
|
|
8090
|
+
* @type {string}
|
|
8091
|
+
* @memberof WHIPIngress
|
|
8092
|
+
*/
|
|
8093
|
+
address: string;
|
|
8094
|
+
}
|
|
7928
8095
|
/**
|
|
7929
8096
|
* Websocket auth message
|
|
7930
8097
|
* @export
|
|
@@ -301,6 +301,12 @@ export interface PublishOption {
|
|
|
301
301
|
* @generated from protobuf field: bool use_single_layer = 9;
|
|
302
302
|
*/
|
|
303
303
|
useSingleLayer: boolean;
|
|
304
|
+
/**
|
|
305
|
+
* Audio bitrate profiles for different audio quality profiles.
|
|
306
|
+
*
|
|
307
|
+
* @generated from protobuf field: repeated stream.video.sfu.models.AudioBitrate audio_bitrate_profiles = 10;
|
|
308
|
+
*/
|
|
309
|
+
audioBitrateProfiles: AudioBitrate[];
|
|
304
310
|
}
|
|
305
311
|
/**
|
|
306
312
|
* @generated from protobuf message stream.video.sfu.models.Codec
|
|
@@ -344,6 +350,19 @@ export interface ICETrickle {
|
|
|
344
350
|
*/
|
|
345
351
|
sessionId: string;
|
|
346
352
|
}
|
|
353
|
+
/**
|
|
354
|
+
* @generated from protobuf message stream.video.sfu.models.AudioBitrate
|
|
355
|
+
*/
|
|
356
|
+
export interface AudioBitrate {
|
|
357
|
+
/**
|
|
358
|
+
* @generated from protobuf field: stream.video.sfu.models.AudioBitrateProfile profile = 1;
|
|
359
|
+
*/
|
|
360
|
+
profile: AudioBitrateProfile;
|
|
361
|
+
/**
|
|
362
|
+
* @generated from protobuf field: int32 bitrate = 2;
|
|
363
|
+
*/
|
|
364
|
+
bitrate: number;
|
|
365
|
+
}
|
|
347
366
|
/**
|
|
348
367
|
* @generated from protobuf message stream.video.sfu.models.TrackInfo
|
|
349
368
|
*/
|
|
@@ -794,6 +813,23 @@ export enum ParticipantSource {
|
|
|
794
813
|
*/
|
|
795
814
|
SRT = 5,
|
|
796
815
|
}
|
|
816
|
+
/**
|
|
817
|
+
* @generated from protobuf enum stream.video.sfu.models.AudioBitrateProfile
|
|
818
|
+
*/
|
|
819
|
+
export enum AudioBitrateProfile {
|
|
820
|
+
/**
|
|
821
|
+
* @generated from protobuf enum value: AUDIO_BITRATE_PROFILE_VOICE_STANDARD_UNSPECIFIED = 0;
|
|
822
|
+
*/
|
|
823
|
+
VOICE_STANDARD_UNSPECIFIED = 0,
|
|
824
|
+
/**
|
|
825
|
+
* @generated from protobuf enum value: AUDIO_BITRATE_PROFILE_VOICE_HIGH_QUALITY = 1;
|
|
826
|
+
*/
|
|
827
|
+
VOICE_HIGH_QUALITY = 1,
|
|
828
|
+
/**
|
|
829
|
+
* @generated from protobuf enum value: AUDIO_BITRATE_PROFILE_MUSIC_HIGH_QUALITY = 2;
|
|
830
|
+
*/
|
|
831
|
+
MUSIC_HIGH_QUALITY = 2,
|
|
832
|
+
}
|
|
797
833
|
/**
|
|
798
834
|
* @generated from protobuf enum stream.video.sfu.models.ErrorCode
|
|
799
835
|
*/
|
|
@@ -1398,6 +1434,13 @@ class PublishOption$Type extends MessageType<PublishOption> {
|
|
|
1398
1434
|
kind: 'scalar',
|
|
1399
1435
|
T: 8 /*ScalarType.BOOL*/,
|
|
1400
1436
|
},
|
|
1437
|
+
{
|
|
1438
|
+
no: 10,
|
|
1439
|
+
name: 'audio_bitrate_profiles',
|
|
1440
|
+
kind: 'message',
|
|
1441
|
+
repeat: 2 /*RepeatType.UNPACKED*/,
|
|
1442
|
+
T: () => AudioBitrate,
|
|
1443
|
+
},
|
|
1401
1444
|
]);
|
|
1402
1445
|
}
|
|
1403
1446
|
}
|
|
@@ -1461,6 +1504,28 @@ class ICETrickle$Type extends MessageType<ICETrickle> {
|
|
|
1461
1504
|
*/
|
|
1462
1505
|
export const ICETrickle = new ICETrickle$Type();
|
|
1463
1506
|
// @generated message type with reflection information, may provide speed optimized methods
|
|
1507
|
+
class AudioBitrate$Type extends MessageType<AudioBitrate> {
|
|
1508
|
+
constructor() {
|
|
1509
|
+
super('stream.video.sfu.models.AudioBitrate', [
|
|
1510
|
+
{
|
|
1511
|
+
no: 1,
|
|
1512
|
+
name: 'profile',
|
|
1513
|
+
kind: 'enum',
|
|
1514
|
+
T: () => [
|
|
1515
|
+
'stream.video.sfu.models.AudioBitrateProfile',
|
|
1516
|
+
AudioBitrateProfile,
|
|
1517
|
+
'AUDIO_BITRATE_PROFILE_',
|
|
1518
|
+
],
|
|
1519
|
+
},
|
|
1520
|
+
{ no: 2, name: 'bitrate', kind: 'scalar', T: 5 /*ScalarType.INT32*/ },
|
|
1521
|
+
]);
|
|
1522
|
+
}
|
|
1523
|
+
}
|
|
1524
|
+
/**
|
|
1525
|
+
* @generated MessageType for protobuf message stream.video.sfu.models.AudioBitrate
|
|
1526
|
+
*/
|
|
1527
|
+
export const AudioBitrate = new AudioBitrate$Type();
|
|
1528
|
+
// @generated message type with reflection information, may provide speed optimized methods
|
|
1464
1529
|
class TrackInfo$Type extends MessageType<TrackInfo> {
|
|
1465
1530
|
constructor() {
|
|
1466
1531
|
super('stream.video.sfu.models.TrackInfo', [
|
|
@@ -16,22 +16,7 @@ import { StreamSfuClient } from '../StreamSfuClient';
|
|
|
16
16
|
import { AllSfuEvents, Dispatcher } from './Dispatcher';
|
|
17
17
|
import { withoutConcurrency } from '../helpers/concurrency';
|
|
18
18
|
import { StatsTracer, Tracer, traceRTCPeerConnection } from '../stats';
|
|
19
|
-
|
|
20
|
-
export type OnReconnectionNeeded = (
|
|
21
|
-
kind: WebsocketReconnectStrategy,
|
|
22
|
-
reason: string,
|
|
23
|
-
) => void;
|
|
24
|
-
|
|
25
|
-
export type BasePeerConnectionOpts = {
|
|
26
|
-
sfuClient: StreamSfuClient;
|
|
27
|
-
state: CallState;
|
|
28
|
-
connectionConfig?: RTCConfiguration;
|
|
29
|
-
dispatcher: Dispatcher;
|
|
30
|
-
onReconnectionNeeded?: OnReconnectionNeeded;
|
|
31
|
-
tag: string;
|
|
32
|
-
enableTracing: boolean;
|
|
33
|
-
iceRestartDelay?: number;
|
|
34
|
-
};
|
|
19
|
+
import { BasePeerConnectionOpts, OnReconnectionNeeded } from './types';
|
|
35
20
|
|
|
36
21
|
/**
|
|
37
22
|
* A base class for the `Publisher` and `Subscriber` classes.
|
package/src/rtc/Publisher.ts
CHANGED
|
@@ -1,7 +1,9 @@
|
|
|
1
|
+
import { BasePeerConnection } from './BasePeerConnection';
|
|
1
2
|
import {
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
3
|
+
PublishBundle,
|
|
4
|
+
PublisherConstructorOpts,
|
|
5
|
+
TrackPublishOptions,
|
|
6
|
+
} from './types';
|
|
5
7
|
import { NegotiationError } from './NegotiationError';
|
|
6
8
|
import { TransceiverCache } from './TransceiverCache';
|
|
7
9
|
import {
|
|
@@ -12,20 +14,17 @@ import {
|
|
|
12
14
|
} from '../gen/video/sfu/models/models';
|
|
13
15
|
import { VideoSender } from '../gen/video/sfu/event/events';
|
|
14
16
|
import {
|
|
17
|
+
computeAudioLayers,
|
|
15
18
|
computeVideoLayers,
|
|
16
19
|
toSvcEncodings,
|
|
17
20
|
toVideoLayers,
|
|
18
|
-
} from './
|
|
21
|
+
} from './layers';
|
|
19
22
|
import { isSvcCodec } from './codecs';
|
|
20
23
|
import { isAudioTrackType } from './helpers/tracks';
|
|
21
24
|
import { extractMid } from './helpers/sdp';
|
|
22
25
|
import { withoutConcurrency } from '../helpers/concurrency';
|
|
23
26
|
import { isReactNative } from '../helpers/platforms';
|
|
24
27
|
|
|
25
|
-
export type PublisherConstructorOpts = BasePeerConnectionOpts & {
|
|
26
|
-
publishOptions: PublishOption[];
|
|
27
|
-
};
|
|
28
|
-
|
|
29
28
|
/**
|
|
30
29
|
* The `Publisher` is responsible for publishing/unpublishing media streams to/from the SFU
|
|
31
30
|
*
|
|
@@ -77,8 +76,13 @@ export class Publisher extends BasePeerConnection {
|
|
|
77
76
|
*
|
|
78
77
|
* @param track the track to publish.
|
|
79
78
|
* @param trackType the track type to publish.
|
|
79
|
+
* @param options the publish options to use.
|
|
80
80
|
*/
|
|
81
|
-
publish = async (
|
|
81
|
+
publish = async (
|
|
82
|
+
track: MediaStreamTrack,
|
|
83
|
+
trackType: TrackType,
|
|
84
|
+
options: TrackPublishOptions = {},
|
|
85
|
+
) => {
|
|
82
86
|
if (!this.publishOptions.some((o) => o.trackType === trackType)) {
|
|
83
87
|
throw new Error(`No publish options found for ${TrackType[trackType]}`);
|
|
84
88
|
}
|
|
@@ -90,12 +94,17 @@ export class Publisher extends BasePeerConnection {
|
|
|
90
94
|
// appear in the SDP in multiple transceivers
|
|
91
95
|
const trackToPublish = this.cloneTrack(track);
|
|
92
96
|
|
|
93
|
-
const transceiver = this.transceiverCache.get(publishOption);
|
|
97
|
+
const { transceiver } = this.transceiverCache.get(publishOption) || {};
|
|
94
98
|
if (!transceiver) {
|
|
95
|
-
await this.addTransceiver(trackToPublish, publishOption);
|
|
99
|
+
await this.addTransceiver(trackToPublish, publishOption, options);
|
|
96
100
|
} else {
|
|
97
101
|
const previousTrack = transceiver.sender.track;
|
|
98
|
-
await this.updateTransceiver(
|
|
102
|
+
await this.updateTransceiver(
|
|
103
|
+
transceiver,
|
|
104
|
+
trackToPublish,
|
|
105
|
+
trackType,
|
|
106
|
+
options,
|
|
107
|
+
);
|
|
99
108
|
if (!isReactNative()) {
|
|
100
109
|
this.stopTrack(previousTrack);
|
|
101
110
|
}
|
|
@@ -109,11 +118,14 @@ export class Publisher extends BasePeerConnection {
|
|
|
109
118
|
private addTransceiver = async (
|
|
110
119
|
track: MediaStreamTrack,
|
|
111
120
|
publishOption: PublishOption,
|
|
121
|
+
options: TrackPublishOptions,
|
|
112
122
|
) => {
|
|
113
|
-
const
|
|
123
|
+
const encodings = isAudioTrackType(publishOption.trackType)
|
|
124
|
+
? computeAudioLayers(publishOption, options)
|
|
125
|
+
: computeVideoLayers(track, publishOption);
|
|
114
126
|
const sendEncodings = isSvcCodec(publishOption.codec?.name)
|
|
115
|
-
? toSvcEncodings(
|
|
116
|
-
:
|
|
127
|
+
? toSvcEncodings(encodings)
|
|
128
|
+
: encodings;
|
|
117
129
|
const transceiver = this.pc.addTransceiver(track, {
|
|
118
130
|
direction: 'sendonly',
|
|
119
131
|
sendEncodings,
|
|
@@ -125,7 +137,7 @@ export class Publisher extends BasePeerConnection {
|
|
|
125
137
|
|
|
126
138
|
const trackType = publishOption.trackType;
|
|
127
139
|
this.logger('debug', `Added ${TrackType[trackType]} transceiver`);
|
|
128
|
-
this.transceiverCache.add(publishOption, transceiver);
|
|
140
|
+
this.transceiverCache.add({ publishOption, transceiver, options });
|
|
129
141
|
this.trackIdToTrackType.set(track.id, trackType);
|
|
130
142
|
|
|
131
143
|
await this.negotiate();
|
|
@@ -138,11 +150,44 @@ export class Publisher extends BasePeerConnection {
|
|
|
138
150
|
transceiver: RTCRtpTransceiver,
|
|
139
151
|
track: MediaStreamTrack | null,
|
|
140
152
|
trackType: TrackType,
|
|
153
|
+
options: TrackPublishOptions = {},
|
|
141
154
|
) => {
|
|
142
155
|
const sender = transceiver.sender;
|
|
143
156
|
if (sender.track) this.trackIdToTrackType.delete(sender.track.id);
|
|
144
157
|
await sender.replaceTrack(track);
|
|
145
158
|
if (track) this.trackIdToTrackType.set(track.id, trackType);
|
|
159
|
+
if (isAudioTrackType(trackType)) {
|
|
160
|
+
await this.updateAudioPublishOptions(trackType, options);
|
|
161
|
+
}
|
|
162
|
+
};
|
|
163
|
+
|
|
164
|
+
/**
|
|
165
|
+
* Updates the publish options for the given track type.
|
|
166
|
+
*/
|
|
167
|
+
private updateAudioPublishOptions = async (
|
|
168
|
+
trackType: TrackType,
|
|
169
|
+
options: TrackPublishOptions,
|
|
170
|
+
) => {
|
|
171
|
+
for (const publishOption of this.publishOptions) {
|
|
172
|
+
if (publishOption.trackType !== trackType) continue;
|
|
173
|
+
const bundle = this.transceiverCache.get(publishOption);
|
|
174
|
+
if (!bundle) continue;
|
|
175
|
+
|
|
176
|
+
const { transceiver, options: current } = bundle;
|
|
177
|
+
if (current.audioBitrateProfile !== options.audioBitrateProfile) {
|
|
178
|
+
const encodings = computeAudioLayers(publishOption, options);
|
|
179
|
+
if (encodings && encodings.length > 0) {
|
|
180
|
+
const params = transceiver.sender.getParameters();
|
|
181
|
+
const [currentEncoding] = params.encodings;
|
|
182
|
+
const [targetEncoding] = encodings;
|
|
183
|
+
if (currentEncoding.maxBitrate !== targetEncoding.maxBitrate) {
|
|
184
|
+
currentEncoding.maxBitrate = targetEncoding.maxBitrate;
|
|
185
|
+
}
|
|
186
|
+
await transceiver.sender.setParameters(params);
|
|
187
|
+
}
|
|
188
|
+
}
|
|
189
|
+
this.transceiverCache.update(publishOption, { options });
|
|
190
|
+
}
|
|
146
191
|
};
|
|
147
192
|
|
|
148
193
|
/**
|
|
@@ -160,12 +205,12 @@ export class Publisher extends BasePeerConnection {
|
|
|
160
205
|
!!i.transceiver.sender.track &&
|
|
161
206
|
i.publishOption.trackType === trackType,
|
|
162
207
|
);
|
|
163
|
-
if (!item
|
|
208
|
+
if (!item) continue;
|
|
164
209
|
|
|
165
210
|
// take the track from the existing transceiver for the same track type,
|
|
166
211
|
// clone it and publish it with the new publish options
|
|
167
212
|
const track = this.cloneTrack(item.transceiver.sender.track!);
|
|
168
|
-
await this.addTransceiver(track, publishOption);
|
|
213
|
+
await this.addTransceiver(track, publishOption, item.options);
|
|
169
214
|
}
|
|
170
215
|
|
|
171
216
|
// stop publishing with options not required anymore -> [vp9]
|
|
@@ -372,11 +417,8 @@ export class Publisher extends BasePeerConnection {
|
|
|
372
417
|
getAnnouncedTracks = (sdp: string | undefined): TrackInfo[] => {
|
|
373
418
|
const trackInfos: TrackInfo[] = [];
|
|
374
419
|
for (const bundle of this.transceiverCache.items()) {
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
if (!track) continue;
|
|
378
|
-
|
|
379
|
-
trackInfos.push(this.toTrackInfo(transceiver, publishOption, sdp));
|
|
420
|
+
if (!bundle.transceiver.sender.track) continue;
|
|
421
|
+
trackInfos.push(this.toTrackInfo(bundle, sdp));
|
|
380
422
|
}
|
|
381
423
|
return trackInfos;
|
|
382
424
|
};
|
|
@@ -390,10 +432,9 @@ export class Publisher extends BasePeerConnection {
|
|
|
390
432
|
const sdp = this.pc.localDescription?.sdp;
|
|
391
433
|
const trackInfos: TrackInfo[] = [];
|
|
392
434
|
for (const publishOption of this.publishOptions) {
|
|
393
|
-
const
|
|
394
|
-
if (!
|
|
395
|
-
|
|
396
|
-
trackInfos.push(this.toTrackInfo(transceiver, publishOption, sdp));
|
|
435
|
+
const bundle = this.transceiverCache.get(publishOption);
|
|
436
|
+
if (!bundle || !bundle.transceiver.sender.track) continue;
|
|
437
|
+
trackInfos.push(this.toTrackInfo(bundle, sdp));
|
|
397
438
|
}
|
|
398
439
|
return trackInfos;
|
|
399
440
|
};
|
|
@@ -402,10 +443,10 @@ export class Publisher extends BasePeerConnection {
|
|
|
402
443
|
* Converts the given transceiver to a `TrackInfo` object.
|
|
403
444
|
*/
|
|
404
445
|
private toTrackInfo = (
|
|
405
|
-
|
|
406
|
-
publishOption: PublishOption,
|
|
446
|
+
bundle: PublishBundle,
|
|
407
447
|
sdp: string | undefined,
|
|
408
448
|
): TrackInfo => {
|
|
449
|
+
const { transceiver, publishOption } = bundle;
|
|
409
450
|
const track = transceiver.sender.track!;
|
|
410
451
|
const isTrackLive = track.readyState === 'live';
|
|
411
452
|
const layers = isTrackLive
|
|
@@ -414,16 +455,18 @@ export class Publisher extends BasePeerConnection {
|
|
|
414
455
|
this.transceiverCache.setLayers(publishOption, layers);
|
|
415
456
|
|
|
416
457
|
const isAudioTrack = isAudioTrackType(publishOption.trackType);
|
|
417
|
-
const isStereo = isAudioTrack && track.getSettings().channelCount === 2;
|
|
418
458
|
const transceiverIndex = this.transceiverCache.indexOf(transceiver);
|
|
419
459
|
const audioSettings = this.state.settings?.audio;
|
|
460
|
+
const stereo =
|
|
461
|
+
publishOption.trackType === TrackType.SCREEN_SHARE_AUDIO ||
|
|
462
|
+
(isAudioTrack && !!audioSettings?.hifi_audio_enabled);
|
|
420
463
|
|
|
421
464
|
return {
|
|
422
465
|
trackId: track.id,
|
|
423
466
|
layers: toVideoLayers(layers),
|
|
424
467
|
trackType: publishOption.trackType,
|
|
425
468
|
mid: extractMid(transceiver, transceiverIndex, sdp),
|
|
426
|
-
stereo
|
|
469
|
+
stereo,
|
|
427
470
|
dtx: isAudioTrack && !!audioSettings?.opus_dtx_enabled,
|
|
428
471
|
red: isAudioTrack && !!audioSettings?.redundant_coding_enabled,
|
|
429
472
|
muted: !isTrackLive,
|
package/src/rtc/Subscriber.ts
CHANGED
|
@@ -1,7 +1,5 @@
|
|
|
1
|
-
import {
|
|
2
|
-
|
|
3
|
-
BasePeerConnectionOpts,
|
|
4
|
-
} from './BasePeerConnection';
|
|
1
|
+
import { BasePeerConnection } from './BasePeerConnection';
|
|
2
|
+
import { BasePeerConnectionOpts } from './types';
|
|
5
3
|
import { NegotiationError } from './NegotiationError';
|
|
6
4
|
import { PeerType } from '../gen/video/sfu/models/models';
|
|
7
5
|
import { SubscriberOffer } from '../gen/video/sfu/event/events';
|