livekit-client 0.18.4-RC7 → 0.18.5

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.
Files changed (127) hide show
  1. package/README.md +2 -5
  2. package/dist/api/RequestQueue.d.ts +13 -12
  3. package/dist/api/RequestQueue.d.ts.map +1 -0
  4. package/dist/api/SignalClient.d.ts +67 -66
  5. package/dist/api/SignalClient.d.ts.map +1 -0
  6. package/dist/connect.d.ts +24 -23
  7. package/dist/connect.d.ts.map +1 -0
  8. package/dist/index.d.ts +27 -26
  9. package/dist/index.d.ts.map +1 -0
  10. package/dist/livekit-client.esm.mjs +638 -517
  11. package/dist/livekit-client.esm.mjs.map +1 -1
  12. package/dist/livekit-client.umd.js +1 -1
  13. package/dist/livekit-client.umd.js.map +1 -1
  14. package/dist/logger.d.ts +26 -25
  15. package/dist/logger.d.ts.map +1 -0
  16. package/dist/options.d.ts +128 -127
  17. package/dist/options.d.ts.map +1 -0
  18. package/dist/proto/google/protobuf/timestamp.d.ts +133 -132
  19. package/dist/proto/google/protobuf/timestamp.d.ts.map +1 -0
  20. package/dist/proto/livekit_models.d.ts +876 -875
  21. package/dist/proto/livekit_models.d.ts.map +1 -0
  22. package/dist/proto/livekit_rtc.d.ts +3904 -3903
  23. package/dist/proto/livekit_rtc.d.ts.map +1 -0
  24. package/dist/room/DeviceManager.d.ts +8 -7
  25. package/dist/room/DeviceManager.d.ts.map +1 -0
  26. package/dist/room/PCTransport.d.ts +16 -15
  27. package/dist/room/PCTransport.d.ts.map +1 -0
  28. package/dist/room/RTCEngine.d.ts +67 -66
  29. package/dist/room/RTCEngine.d.ts.map +1 -0
  30. package/dist/room/Room.d.ts +166 -165
  31. package/dist/room/Room.d.ts.map +1 -0
  32. package/dist/room/errors.d.ts +29 -28
  33. package/dist/room/errors.d.ts.map +1 -0
  34. package/dist/room/events.d.ts +391 -390
  35. package/dist/room/events.d.ts.map +1 -0
  36. package/dist/room/participant/LocalParticipant.d.ts +126 -125
  37. package/dist/room/participant/LocalParticipant.d.ts.map +1 -0
  38. package/dist/room/participant/Participant.d.ts +94 -93
  39. package/dist/room/participant/Participant.d.ts.map +1 -0
  40. package/dist/room/participant/ParticipantTrackPermission.d.ts +26 -25
  41. package/dist/room/participant/ParticipantTrackPermission.d.ts.map +1 -0
  42. package/dist/room/participant/RemoteParticipant.d.ts +40 -39
  43. package/dist/room/participant/RemoteParticipant.d.ts.map +1 -0
  44. package/dist/room/participant/publishUtils.d.ts +18 -17
  45. package/dist/room/participant/publishUtils.d.ts.map +1 -0
  46. package/dist/room/stats.d.ts +66 -65
  47. package/dist/room/stats.d.ts.map +1 -0
  48. package/dist/room/track/LocalAudioTrack.d.ts +20 -19
  49. package/dist/room/track/LocalAudioTrack.d.ts.map +1 -0
  50. package/dist/room/track/LocalTrack.d.ts +28 -27
  51. package/dist/room/track/LocalTrack.d.ts.map +1 -0
  52. package/dist/room/track/LocalTrackPublication.d.ts +38 -37
  53. package/dist/room/track/LocalTrackPublication.d.ts.map +1 -0
  54. package/dist/room/track/LocalVideoTrack.d.ts +31 -30
  55. package/dist/room/track/LocalVideoTrack.d.ts.map +1 -0
  56. package/dist/room/track/RemoteAudioTrack.d.ts +20 -19
  57. package/dist/room/track/RemoteAudioTrack.d.ts.map +1 -0
  58. package/dist/room/track/RemoteTrack.d.ts +16 -15
  59. package/dist/room/track/RemoteTrack.d.ts.map +1 -0
  60. package/dist/room/track/RemoteTrackPublication.d.ts +51 -50
  61. package/dist/room/track/RemoteTrackPublication.d.ts.map +1 -0
  62. package/dist/room/track/RemoteVideoTrack.d.ts +29 -27
  63. package/dist/room/track/RemoteVideoTrack.d.ts.map +1 -0
  64. package/dist/room/track/Track.d.ts +105 -100
  65. package/dist/room/track/Track.d.ts.map +1 -0
  66. package/dist/room/track/TrackPublication.d.ts +50 -49
  67. package/dist/room/track/TrackPublication.d.ts.map +1 -0
  68. package/dist/room/track/create.d.ts +24 -23
  69. package/dist/room/track/create.d.ts.map +1 -0
  70. package/dist/room/track/defaults.d.ts +5 -4
  71. package/dist/room/track/defaults.d.ts.map +1 -0
  72. package/dist/room/track/options.d.ts +232 -222
  73. package/dist/room/track/options.d.ts.map +1 -0
  74. package/dist/room/track/types.d.ts +19 -18
  75. package/dist/room/track/types.d.ts.map +1 -0
  76. package/dist/room/track/utils.d.ts +14 -13
  77. package/dist/room/track/utils.d.ts.map +1 -0
  78. package/dist/room/utils.d.ts +17 -15
  79. package/dist/room/utils.d.ts.map +1 -0
  80. package/dist/test/mocks.d.ts +12 -11
  81. package/dist/test/mocks.d.ts.map +1 -0
  82. package/dist/version.d.ts +3 -2
  83. package/dist/version.d.ts.map +1 -0
  84. package/package.json +4 -5
  85. package/src/api/RequestQueue.ts +53 -0
  86. package/src/api/SignalClient.ts +497 -0
  87. package/src/connect.ts +98 -0
  88. package/src/index.ts +49 -0
  89. package/src/logger.ts +56 -0
  90. package/src/options.ts +156 -0
  91. package/src/proto/google/protobuf/timestamp.ts +216 -0
  92. package/src/proto/livekit_models.ts +2456 -0
  93. package/src/proto/livekit_rtc.ts +2859 -0
  94. package/src/room/DeviceManager.ts +80 -0
  95. package/src/room/PCTransport.ts +88 -0
  96. package/src/room/RTCEngine.ts +695 -0
  97. package/src/room/Room.ts +970 -0
  98. package/src/room/errors.ts +65 -0
  99. package/src/room/events.ts +438 -0
  100. package/src/room/participant/LocalParticipant.ts +779 -0
  101. package/src/room/participant/Participant.ts +287 -0
  102. package/src/room/participant/ParticipantTrackPermission.ts +42 -0
  103. package/src/room/participant/RemoteParticipant.ts +263 -0
  104. package/src/room/participant/publishUtils.test.ts +144 -0
  105. package/src/room/participant/publishUtils.ts +258 -0
  106. package/src/room/stats.ts +134 -0
  107. package/src/room/track/LocalAudioTrack.ts +134 -0
  108. package/src/room/track/LocalTrack.ts +229 -0
  109. package/src/room/track/LocalTrackPublication.ts +87 -0
  110. package/src/room/track/LocalVideoTrack.test.ts +72 -0
  111. package/src/room/track/LocalVideoTrack.ts +295 -0
  112. package/src/room/track/RemoteAudioTrack.ts +86 -0
  113. package/src/room/track/RemoteTrack.ts +62 -0
  114. package/src/room/track/RemoteTrackPublication.ts +207 -0
  115. package/src/room/track/RemoteVideoTrack.ts +249 -0
  116. package/src/room/track/Track.ts +365 -0
  117. package/src/room/track/TrackPublication.ts +120 -0
  118. package/src/room/track/create.ts +122 -0
  119. package/src/room/track/defaults.ts +26 -0
  120. package/src/room/track/options.ts +292 -0
  121. package/src/room/track/types.ts +20 -0
  122. package/src/room/track/utils.test.ts +110 -0
  123. package/src/room/track/utils.ts +113 -0
  124. package/src/room/utils.ts +115 -0
  125. package/src/test/mocks.ts +17 -0
  126. package/src/version.ts +2 -0
  127. package/CHANGELOG.md +0 -5
@@ -325,9 +325,9 @@ livekitLogger.setLevel(LogLevel.info);
325
325
  function setLogLevel(level) {
326
326
  livekitLogger.setLevel(level);
327
327
  }
328
- /**
329
- * use this to hook into the logging function to allow sending internal livekit logs to third party services
330
- * if set, the browser logs will lose their stacktrace information (see https://github.com/pimterry/loglevel#writing-plugins)
328
+ /**
329
+ * use this to hook into the logging function to allow sending internal livekit logs to third party services
330
+ * if set, the browser logs will lose their stacktrace information (see https://github.com/pimterry/loglevel#writing-plugins)
331
331
  */
332
332
 
333
333
  function setLogExtension(extension) {
@@ -9229,237 +9229,237 @@ var MediaDeviceFailure;
9229
9229
  MediaDeviceFailure.getFailure = getFailure;
9230
9230
  })(MediaDeviceFailure || (MediaDeviceFailure = {}));
9231
9231
 
9232
- /**
9233
- * Events are the primary way LiveKit notifies your application of changes.
9234
- *
9235
- * The following are events emitted by [[Room]], listen to room events like
9236
- *
9237
- * ```typescript
9238
- * room.on(RoomEvent.TrackPublished, (track, publication, participant) => {})
9239
- * ```
9232
+ /**
9233
+ * Events are the primary way LiveKit notifies your application of changes.
9234
+ *
9235
+ * The following are events emitted by [[Room]], listen to room events like
9236
+ *
9237
+ * ```typescript
9238
+ * room.on(RoomEvent.TrackPublished, (track, publication, participant) => {})
9239
+ * ```
9240
9240
  */
9241
9241
  var RoomEvent;
9242
9242
 
9243
9243
  (function (RoomEvent) {
9244
- /**
9245
- * When the connection to the server has been interrupted and it's attempting
9246
- * to reconnect.
9244
+ /**
9245
+ * When the connection to the server has been interrupted and it's attempting
9246
+ * to reconnect.
9247
9247
  */
9248
9248
  RoomEvent["Reconnecting"] = "reconnecting";
9249
- /**
9250
- * Fires when a reconnection has been successful.
9249
+ /**
9250
+ * Fires when a reconnection has been successful.
9251
9251
  */
9252
9252
 
9253
9253
  RoomEvent["Reconnected"] = "reconnected";
9254
- /**
9255
- * When disconnected from room. This fires when room.disconnect() is called or
9256
- * when an unrecoverable connection issue had occured
9254
+ /**
9255
+ * When disconnected from room. This fires when room.disconnect() is called or
9256
+ * when an unrecoverable connection issue had occured
9257
9257
  */
9258
9258
 
9259
9259
  RoomEvent["Disconnected"] = "disconnected";
9260
- /**
9261
- * Whenever the connection state of the room changes
9262
- *
9263
- * args: ([[RoomState]])
9260
+ /**
9261
+ * Whenever the connection state of the room changes
9262
+ *
9263
+ * args: ([[RoomState]])
9264
9264
  */
9265
9265
 
9266
9266
  RoomEvent["StateChanged"] = "stateChanged";
9267
- /**
9268
- * When input or output devices on the machine have changed.
9267
+ /**
9268
+ * When input or output devices on the machine have changed.
9269
9269
  */
9270
9270
 
9271
9271
  RoomEvent["MediaDevicesChanged"] = "mediaDevicesChanged";
9272
- /**
9273
- * When a [[RemoteParticipant]] joins *after* the local
9274
- * participant. It will not emit events for participants that are already
9275
- * in the room
9276
- *
9277
- * args: ([[RemoteParticipant]])
9272
+ /**
9273
+ * When a [[RemoteParticipant]] joins *after* the local
9274
+ * participant. It will not emit events for participants that are already
9275
+ * in the room
9276
+ *
9277
+ * args: ([[RemoteParticipant]])
9278
9278
  */
9279
9279
 
9280
9280
  RoomEvent["ParticipantConnected"] = "participantConnected";
9281
- /**
9282
- * When a [[RemoteParticipant]] leaves *after* the local
9283
- * participant has joined.
9284
- *
9285
- * args: ([[RemoteParticipant]])
9281
+ /**
9282
+ * When a [[RemoteParticipant]] leaves *after* the local
9283
+ * participant has joined.
9284
+ *
9285
+ * args: ([[RemoteParticipant]])
9286
9286
  */
9287
9287
 
9288
9288
  RoomEvent["ParticipantDisconnected"] = "participantDisconnected";
9289
- /**
9290
- * When a new track is published to room *after* the local
9291
- * participant has joined. It will not fire for tracks that are already published.
9292
- *
9293
- * A track published doesn't mean the participant has subscribed to it. It's
9294
- * simply reflecting the state of the room.
9295
- *
9296
- * args: ([[RemoteTrackPublication]], [[RemoteParticipant]])
9289
+ /**
9290
+ * When a new track is published to room *after* the local
9291
+ * participant has joined. It will not fire for tracks that are already published.
9292
+ *
9293
+ * A track published doesn't mean the participant has subscribed to it. It's
9294
+ * simply reflecting the state of the room.
9295
+ *
9296
+ * args: ([[RemoteTrackPublication]], [[RemoteParticipant]])
9297
9297
  */
9298
9298
 
9299
9299
  RoomEvent["TrackPublished"] = "trackPublished";
9300
- /**
9301
- * The [[LocalParticipant]] has subscribed to a new track. This event will **always**
9302
- * fire as long as new tracks are ready for use.
9303
- *
9304
- * args: ([[RemoteTrack]], [[RemoteTrackPublication]], [[RemoteParticipant]])
9300
+ /**
9301
+ * The [[LocalParticipant]] has subscribed to a new track. This event will **always**
9302
+ * fire as long as new tracks are ready for use.
9303
+ *
9304
+ * args: ([[RemoteTrack]], [[RemoteTrackPublication]], [[RemoteParticipant]])
9305
9305
  */
9306
9306
 
9307
9307
  RoomEvent["TrackSubscribed"] = "trackSubscribed";
9308
- /**
9309
- * Could not subscribe to a track
9310
- *
9311
- * args: (track sid, [[RemoteParticipant]])
9308
+ /**
9309
+ * Could not subscribe to a track
9310
+ *
9311
+ * args: (track sid, [[RemoteParticipant]])
9312
9312
  */
9313
9313
 
9314
9314
  RoomEvent["TrackSubscriptionFailed"] = "trackSubscriptionFailed";
9315
- /**
9316
- * A [[RemoteParticipant]] has unpublished a track
9317
- *
9318
- * args: ([[RemoteTrackPublication]], [[RemoteParticipant]])
9315
+ /**
9316
+ * A [[RemoteParticipant]] has unpublished a track
9317
+ *
9318
+ * args: ([[RemoteTrackPublication]], [[RemoteParticipant]])
9319
9319
  */
9320
9320
 
9321
9321
  RoomEvent["TrackUnpublished"] = "trackUnpublished";
9322
- /**
9323
- * A subscribed track is no longer available. Clients should listen to this
9324
- * event and ensure they detach tracks.
9325
- *
9326
- * args: ([[Track]], [[RemoteTrackPublication]], [[RemoteParticipant]])
9322
+ /**
9323
+ * A subscribed track is no longer available. Clients should listen to this
9324
+ * event and ensure they detach tracks.
9325
+ *
9326
+ * args: ([[Track]], [[RemoteTrackPublication]], [[RemoteParticipant]])
9327
9327
  */
9328
9328
 
9329
9329
  RoomEvent["TrackUnsubscribed"] = "trackUnsubscribed";
9330
- /**
9331
- * A track that was muted, fires on both [[RemoteParticipant]]s and [[LocalParticipant]]
9332
- *
9333
- * args: ([[TrackPublication]], [[Participant]])
9330
+ /**
9331
+ * A track that was muted, fires on both [[RemoteParticipant]]s and [[LocalParticipant]]
9332
+ *
9333
+ * args: ([[TrackPublication]], [[Participant]])
9334
9334
  */
9335
9335
 
9336
9336
  RoomEvent["TrackMuted"] = "trackMuted";
9337
- /**
9338
- * A track that was unmuted, fires on both [[RemoteParticipant]]s and [[LocalParticipant]]
9339
- *
9340
- * args: ([[TrackPublication]], [[Participant]])
9337
+ /**
9338
+ * A track that was unmuted, fires on both [[RemoteParticipant]]s and [[LocalParticipant]]
9339
+ *
9340
+ * args: ([[TrackPublication]], [[Participant]])
9341
9341
  */
9342
9342
 
9343
9343
  RoomEvent["TrackUnmuted"] = "trackUnmuted";
9344
- /**
9345
- * A local track was published successfully. This event is helpful to know
9346
- * when to update your local UI with the newly published track.
9347
- *
9348
- * args: ([[LocalTrackPublication]], [[LocalParticipant]])
9344
+ /**
9345
+ * A local track was published successfully. This event is helpful to know
9346
+ * when to update your local UI with the newly published track.
9347
+ *
9348
+ * args: ([[LocalTrackPublication]], [[LocalParticipant]])
9349
9349
  */
9350
9350
 
9351
9351
  RoomEvent["LocalTrackPublished"] = "localTrackPublished";
9352
- /**
9353
- * A local track was unpublished. This event is helpful to know when to remove
9354
- * the local track from your UI.
9355
- *
9356
- * When a user stops sharing their screen by pressing "End" on the browser UI,
9357
- * this event will also fire.
9358
- *
9359
- * args: ([[LocalTrackPublication]], [[LocalParticipant]])
9352
+ /**
9353
+ * A local track was unpublished. This event is helpful to know when to remove
9354
+ * the local track from your UI.
9355
+ *
9356
+ * When a user stops sharing their screen by pressing "End" on the browser UI,
9357
+ * this event will also fire.
9358
+ *
9359
+ * args: ([[LocalTrackPublication]], [[LocalParticipant]])
9360
9360
  */
9361
9361
 
9362
9362
  RoomEvent["LocalTrackUnpublished"] = "localTrackUnpublished";
9363
- /**
9364
- * Active speakers changed. List of speakers are ordered by their audio level.
9365
- * loudest speakers first. This will include the LocalParticipant too.
9366
- *
9367
- * Speaker updates are sent only to the publishing participant and their subscribers.
9368
- *
9369
- * args: (Array<[[Participant]]>)
9363
+ /**
9364
+ * Active speakers changed. List of speakers are ordered by their audio level.
9365
+ * loudest speakers first. This will include the LocalParticipant too.
9366
+ *
9367
+ * Speaker updates are sent only to the publishing participant and their subscribers.
9368
+ *
9369
+ * args: (Array<[[Participant]]>)
9370
9370
  */
9371
9371
 
9372
9372
  RoomEvent["ActiveSpeakersChanged"] = "activeSpeakersChanged";
9373
- /**
9374
- * @deprecated Use ParticipantMetadataChanged instead
9375
- * @internal
9373
+ /**
9374
+ * @deprecated Use ParticipantMetadataChanged instead
9375
+ * @internal
9376
9376
  */
9377
9377
 
9378
9378
  RoomEvent["MetadataChanged"] = "metadataChanged";
9379
- /**
9380
- * Participant metadata is a simple way for app-specific state to be pushed to
9381
- * all users.
9382
- * When RoomService.UpdateParticipantMetadata is called to change a participant's
9383
- * state, *all* participants in the room will fire this event.
9384
- *
9385
- * args: (prevMetadata: string, [[Participant]])
9386
- *
9379
+ /**
9380
+ * Participant metadata is a simple way for app-specific state to be pushed to
9381
+ * all users.
9382
+ * When RoomService.UpdateParticipantMetadata is called to change a participant's
9383
+ * state, *all* participants in the room will fire this event.
9384
+ *
9385
+ * args: (prevMetadata: string, [[Participant]])
9386
+ *
9387
9387
  */
9388
9388
 
9389
9389
  RoomEvent["ParticipantMetadataChanged"] = "participantMetadataChanged";
9390
- /**
9391
- * Room metadata is a simple way for app-specific state to be pushed to
9392
- * all users.
9393
- * When RoomService.UpdateRoomMetadata is called to change a room's state,
9394
- * *all* participants in the room will fire this event.
9395
- *
9396
- * args: (string)
9390
+ /**
9391
+ * Room metadata is a simple way for app-specific state to be pushed to
9392
+ * all users.
9393
+ * When RoomService.UpdateRoomMetadata is called to change a room's state,
9394
+ * *all* participants in the room will fire this event.
9395
+ *
9396
+ * args: (string)
9397
9397
  */
9398
9398
 
9399
9399
  RoomEvent["RoomMetadataChanged"] = "roomMetadataChanged";
9400
- /**
9401
- * Data received from another participant.
9402
- * Data packets provides the ability to use LiveKit to send/receive arbitrary payloads.
9403
- * All participants in the room will receive the messages sent to the room.
9404
- *
9405
- * args: (payload: Uint8Array, participant: [[Participant]], kind: [[DataPacket_Kind]])
9400
+ /**
9401
+ * Data received from another participant.
9402
+ * Data packets provides the ability to use LiveKit to send/receive arbitrary payloads.
9403
+ * All participants in the room will receive the messages sent to the room.
9404
+ *
9405
+ * args: (payload: Uint8Array, participant: [[Participant]], kind: [[DataPacket_Kind]])
9406
9406
  */
9407
9407
 
9408
9408
  RoomEvent["DataReceived"] = "dataReceived";
9409
- /**
9410
- * Connection quality was changed for a Participant. It'll receive updates
9411
- * from the local participant, as well as any [[RemoteParticipant]]s that we are
9412
- * subscribed to.
9413
- *
9414
- * args: (connectionQuality: [[ConnectionQuality]], participant: [[Participant]])
9409
+ /**
9410
+ * Connection quality was changed for a Participant. It'll receive updates
9411
+ * from the local participant, as well as any [[RemoteParticipant]]s that we are
9412
+ * subscribed to.
9413
+ *
9414
+ * args: (connectionQuality: [[ConnectionQuality]], participant: [[Participant]])
9415
9415
  */
9416
9416
 
9417
9417
  RoomEvent["ConnectionQualityChanged"] = "connectionQualityChanged";
9418
- /**
9419
- * StreamState indicates if a subscribed (remote) track has been paused by the SFU
9420
- * (typically this happens because of subscriber's bandwidth constraints)
9421
- *
9422
- * When bandwidth conditions allow, the track will be resumed automatically.
9423
- * TrackStreamStateChanged will also be emitted when that happens.
9424
- *
9425
- * args: (pub: [[RemoteTrackPublication]], streamState: [[Track.StreamState]],
9426
- * participant: [[RemoteParticipant]])
9418
+ /**
9419
+ * StreamState indicates if a subscribed (remote) track has been paused by the SFU
9420
+ * (typically this happens because of subscriber's bandwidth constraints)
9421
+ *
9422
+ * When bandwidth conditions allow, the track will be resumed automatically.
9423
+ * TrackStreamStateChanged will also be emitted when that happens.
9424
+ *
9425
+ * args: (pub: [[RemoteTrackPublication]], streamState: [[Track.StreamState]],
9426
+ * participant: [[RemoteParticipant]])
9427
9427
  */
9428
9428
 
9429
9429
  RoomEvent["TrackStreamStateChanged"] = "trackStreamStateChanged";
9430
- /**
9431
- * One of subscribed tracks have changed its permissions for the current
9432
- * participant. If permission was revoked, then the track will no longer
9433
- * be subscribed. If permission was granted, a TrackSubscribed event will
9434
- * be emitted.
9435
- *
9436
- * args: (pub: [[RemoteTrackPublication]],
9437
- * status: [[TrackPublication.SubscriptionStatus]],
9438
- * participant: [[RemoteParticipant]])
9430
+ /**
9431
+ * One of subscribed tracks have changed its permissions for the current
9432
+ * participant. If permission was revoked, then the track will no longer
9433
+ * be subscribed. If permission was granted, a TrackSubscribed event will
9434
+ * be emitted.
9435
+ *
9436
+ * args: (pub: [[RemoteTrackPublication]],
9437
+ * status: [[TrackPublication.SubscriptionStatus]],
9438
+ * participant: [[RemoteParticipant]])
9439
9439
  */
9440
9440
 
9441
9441
  RoomEvent["TrackSubscriptionPermissionChanged"] = "trackSubscriptionPermissionChanged";
9442
- /**
9443
- * LiveKit will attempt to autoplay all audio tracks when you attach them to
9444
- * audio elements. However, if that fails, we'll notify you via AudioPlaybackStatusChanged.
9445
- * `Room.canPlayAudio` will indicate if audio playback is permitted.
9442
+ /**
9443
+ * LiveKit will attempt to autoplay all audio tracks when you attach them to
9444
+ * audio elements. However, if that fails, we'll notify you via AudioPlaybackStatusChanged.
9445
+ * `Room.canPlayAudio` will indicate if audio playback is permitted.
9446
9446
  */
9447
9447
 
9448
9448
  RoomEvent["AudioPlaybackStatusChanged"] = "audioPlaybackChanged";
9449
- /**
9450
- * When we have encountered an error while attempting to create a track.
9451
- * The errors take place in getUserMedia().
9452
- * Use MediaDeviceFailure.getFailure(error) to get the reason of failure.
9453
- * [[getAudioCreateError]] and [[getVideoCreateError]] will indicate if it had
9454
- * an error while creating the audio or video track respectively.
9455
- *
9456
- * args: (error: Error)
9449
+ /**
9450
+ * When we have encountered an error while attempting to create a track.
9451
+ * The errors take place in getUserMedia().
9452
+ * Use MediaDeviceFailure.getFailure(error) to get the reason of failure.
9453
+ * [[getAudioCreateError]] and [[getVideoCreateError]] will indicate if it had
9454
+ * an error while creating the audio or video track respectively.
9455
+ *
9456
+ * args: (error: Error)
9457
9457
  */
9458
9458
 
9459
9459
  RoomEvent["MediaDevicesError"] = "mediaDevicesError";
9460
- /**
9461
- * A participant's permission has changed. Currently only fired on LocalParticipant.
9462
- * args: (prevPermissions: [[ParticipantPermission]], participant: [[Participant]])
9460
+ /**
9461
+ * A participant's permission has changed. Currently only fired on LocalParticipant.
9462
+ * args: (prevPermissions: [[ParticipantPermission]], participant: [[Participant]])
9463
9463
  */
9464
9464
 
9465
9465
  RoomEvent["ParticipantPermissionsChanged"] = "participantPermissionsChanged";
@@ -9468,141 +9468,141 @@ var RoomEvent;
9468
9468
  var ParticipantEvent;
9469
9469
 
9470
9470
  (function (ParticipantEvent) {
9471
- /**
9472
- * When a new track is published to room *after* the local
9473
- * participant has joined. It will not fire for tracks that are already published.
9474
- *
9475
- * A track published doesn't mean the participant has subscribed to it. It's
9476
- * simply reflecting the state of the room.
9477
- *
9478
- * args: ([[RemoteTrackPublication]])
9471
+ /**
9472
+ * When a new track is published to room *after* the local
9473
+ * participant has joined. It will not fire for tracks that are already published.
9474
+ *
9475
+ * A track published doesn't mean the participant has subscribed to it. It's
9476
+ * simply reflecting the state of the room.
9477
+ *
9478
+ * args: ([[RemoteTrackPublication]])
9479
9479
  */
9480
9480
  ParticipantEvent["TrackPublished"] = "trackPublished";
9481
- /**
9482
- * Successfully subscribed to the [[RemoteParticipant]]'s track.
9483
- * This event will **always** fire as long as new tracks are ready for use.
9484
- *
9485
- * args: ([[RemoteTrack]], [[RemoteTrackPublication]])
9481
+ /**
9482
+ * Successfully subscribed to the [[RemoteParticipant]]'s track.
9483
+ * This event will **always** fire as long as new tracks are ready for use.
9484
+ *
9485
+ * args: ([[RemoteTrack]], [[RemoteTrackPublication]])
9486
9486
  */
9487
9487
 
9488
9488
  ParticipantEvent["TrackSubscribed"] = "trackSubscribed";
9489
- /**
9490
- * Could not subscribe to a track
9491
- *
9492
- * args: (track sid)
9489
+ /**
9490
+ * Could not subscribe to a track
9491
+ *
9492
+ * args: (track sid)
9493
9493
  */
9494
9494
 
9495
9495
  ParticipantEvent["TrackSubscriptionFailed"] = "trackSubscriptionFailed";
9496
- /**
9497
- * A [[RemoteParticipant]] has unpublished a track
9498
- *
9499
- * args: ([[RemoteTrackPublication]])
9496
+ /**
9497
+ * A [[RemoteParticipant]] has unpublished a track
9498
+ *
9499
+ * args: ([[RemoteTrackPublication]])
9500
9500
  */
9501
9501
 
9502
9502
  ParticipantEvent["TrackUnpublished"] = "trackUnpublished";
9503
- /**
9504
- * A subscribed track is no longer available. Clients should listen to this
9505
- * event and ensure they detach tracks.
9506
- *
9507
- * args: ([[RemoteTrack]], [[RemoteTrackPublication]])
9503
+ /**
9504
+ * A subscribed track is no longer available. Clients should listen to this
9505
+ * event and ensure they detach tracks.
9506
+ *
9507
+ * args: ([[RemoteTrack]], [[RemoteTrackPublication]])
9508
9508
  */
9509
9509
 
9510
9510
  ParticipantEvent["TrackUnsubscribed"] = "trackUnsubscribed";
9511
- /**
9512
- * A track that was muted, fires on both [[RemoteParticipant]]s and [[LocalParticipant]]
9513
- *
9514
- * args: ([[TrackPublication]])
9511
+ /**
9512
+ * A track that was muted, fires on both [[RemoteParticipant]]s and [[LocalParticipant]]
9513
+ *
9514
+ * args: ([[TrackPublication]])
9515
9515
  */
9516
9516
 
9517
9517
  ParticipantEvent["TrackMuted"] = "trackMuted";
9518
- /**
9519
- * A track that was unmuted, fires on both [[RemoteParticipant]]s and [[LocalParticipant]]
9520
- *
9521
- * args: ([[TrackPublication]])
9518
+ /**
9519
+ * A track that was unmuted, fires on both [[RemoteParticipant]]s and [[LocalParticipant]]
9520
+ *
9521
+ * args: ([[TrackPublication]])
9522
9522
  */
9523
9523
 
9524
9524
  ParticipantEvent["TrackUnmuted"] = "trackUnmuted";
9525
- /**
9526
- * A local track was published successfully. This event is helpful to know
9527
- * when to update your local UI with the newly published track.
9528
- *
9529
- * args: ([[LocalTrackPublication]])
9525
+ /**
9526
+ * A local track was published successfully. This event is helpful to know
9527
+ * when to update your local UI with the newly published track.
9528
+ *
9529
+ * args: ([[LocalTrackPublication]])
9530
9530
  */
9531
9531
 
9532
9532
  ParticipantEvent["LocalTrackPublished"] = "localTrackPublished";
9533
- /**
9534
- * A local track was unpublished. This event is helpful to know when to remove
9535
- * the local track from your UI.
9536
- *
9537
- * When a user stops sharing their screen by pressing "End" on the browser UI,
9538
- * this event will also fire.
9539
- *
9540
- * args: ([[LocalTrackPublication]])
9533
+ /**
9534
+ * A local track was unpublished. This event is helpful to know when to remove
9535
+ * the local track from your UI.
9536
+ *
9537
+ * When a user stops sharing their screen by pressing "End" on the browser UI,
9538
+ * this event will also fire.
9539
+ *
9540
+ * args: ([[LocalTrackPublication]])
9541
9541
  */
9542
9542
 
9543
9543
  ParticipantEvent["LocalTrackUnpublished"] = "localTrackUnpublished";
9544
- /**
9545
- * @deprecated Use ParticipantMetadataChanged instead
9546
- * @internal
9544
+ /**
9545
+ * @deprecated Use ParticipantMetadataChanged instead
9546
+ * @internal
9547
9547
  */
9548
9548
 
9549
9549
  ParticipantEvent["MetadataChanged"] = "metadataChanged";
9550
- /**
9551
- * Participant metadata is a simple way for app-specific state to be pushed to
9552
- * all users.
9553
- * When RoomService.UpdateParticipantMetadata is called to change a participant's
9554
- * state, *all* participants in the room will fire this event.
9555
- * To access the current metadata, see [[Participant.metadata]].
9556
- *
9557
- * args: (prevMetadata: string)
9558
- *
9550
+ /**
9551
+ * Participant metadata is a simple way for app-specific state to be pushed to
9552
+ * all users.
9553
+ * When RoomService.UpdateParticipantMetadata is called to change a participant's
9554
+ * state, *all* participants in the room will fire this event.
9555
+ * To access the current metadata, see [[Participant.metadata]].
9556
+ *
9557
+ * args: (prevMetadata: string)
9558
+ *
9559
9559
  */
9560
9560
 
9561
9561
  ParticipantEvent["ParticipantMetadataChanged"] = "participantMetadataChanged";
9562
- /**
9563
- * Data received from this participant as sender.
9564
- * Data packets provides the ability to use LiveKit to send/receive arbitrary payloads.
9565
- * All participants in the room will receive the messages sent to the room.
9566
- *
9567
- * args: (payload: Uint8Array, kind: [[DataPacket_Kind]])
9562
+ /**
9563
+ * Data received from this participant as sender.
9564
+ * Data packets provides the ability to use LiveKit to send/receive arbitrary payloads.
9565
+ * All participants in the room will receive the messages sent to the room.
9566
+ *
9567
+ * args: (payload: Uint8Array, kind: [[DataPacket_Kind]])
9568
9568
  */
9569
9569
 
9570
9570
  ParticipantEvent["DataReceived"] = "dataReceived";
9571
- /**
9572
- * Has speaking status changed for the current participant
9573
- *
9574
- * args: (speaking: boolean)
9571
+ /**
9572
+ * Has speaking status changed for the current participant
9573
+ *
9574
+ * args: (speaking: boolean)
9575
9575
  */
9576
9576
 
9577
9577
  ParticipantEvent["IsSpeakingChanged"] = "isSpeakingChanged";
9578
- /**
9579
- * Connection quality was changed for a Participant. It'll receive updates
9580
- * from the local participant, as well as any [[RemoteParticipant]]s that we are
9581
- * subscribed to.
9582
- *
9583
- * args: (connectionQuality: [[ConnectionQuality]])
9578
+ /**
9579
+ * Connection quality was changed for a Participant. It'll receive updates
9580
+ * from the local participant, as well as any [[RemoteParticipant]]s that we are
9581
+ * subscribed to.
9582
+ *
9583
+ * args: (connectionQuality: [[ConnectionQuality]])
9584
9584
  */
9585
9585
 
9586
9586
  ParticipantEvent["ConnectionQualityChanged"] = "connectionQualityChanged";
9587
- /**
9588
- * StreamState indicates if a subscribed track has been paused by the SFU
9589
- * (typically this happens because of subscriber's bandwidth constraints)
9590
- *
9591
- * When bandwidth conditions allow, the track will be resumed automatically.
9592
- * TrackStreamStateChanged will also be emitted when that happens.
9593
- *
9594
- * args: (pub: [[RemoteTrackPublication]], streamState: [[Track.StreamState]])
9587
+ /**
9588
+ * StreamState indicates if a subscribed track has been paused by the SFU
9589
+ * (typically this happens because of subscriber's bandwidth constraints)
9590
+ *
9591
+ * When bandwidth conditions allow, the track will be resumed automatically.
9592
+ * TrackStreamStateChanged will also be emitted when that happens.
9593
+ *
9594
+ * args: (pub: [[RemoteTrackPublication]], streamState: [[Track.StreamState]])
9595
9595
  */
9596
9596
 
9597
9597
  ParticipantEvent["TrackStreamStateChanged"] = "trackStreamStateChanged";
9598
- /**
9599
- * One of subscribed tracks have changed its permissions for the current
9600
- * participant. If permission was revoked, then the track will no longer
9601
- * be subscribed. If permission was granted, a TrackSubscribed event will
9602
- * be emitted.
9603
- *
9604
- * args: (pub: [[RemoteTrackPublication]],
9605
- * status: [[TrackPublication.SubscriptionStatus]])
9598
+ /**
9599
+ * One of subscribed tracks have changed its permissions for the current
9600
+ * participant. If permission was revoked, then the track will no longer
9601
+ * be subscribed. If permission was granted, a TrackSubscribed event will
9602
+ * be emitted.
9603
+ *
9604
+ * args: (pub: [[RemoteTrackPublication]],
9605
+ * status: [[TrackPublication.SubscriptionStatus]])
9606
9606
  */
9607
9607
 
9608
9608
  ParticipantEvent["TrackSubscriptionPermissionChanged"] = "trackSubscriptionPermissionChanged"; // fired only on LocalParticipant
@@ -9610,9 +9610,9 @@ var ParticipantEvent;
9610
9610
  /** @internal */
9611
9611
 
9612
9612
  ParticipantEvent["MediaDevicesError"] = "mediaDevicesError";
9613
- /**
9614
- * A participant's permission has changed. Currently only fired on LocalParticipant.
9615
- * args: (prevPermissions: [[ParticipantPermission]])
9613
+ /**
9614
+ * A participant's permission has changed. Currently only fired on LocalParticipant.
9615
+ * args: (prevPermissions: [[ParticipantPermission]])
9616
9616
  */
9617
9617
 
9618
9618
  ParticipantEvent["ParticipantPermissionsChanged"] = "participantPermissionsChanged";
@@ -9655,9 +9655,9 @@ var TrackEvent;
9655
9655
  /** @internal */
9656
9656
 
9657
9657
  TrackEvent["AudioPlaybackFailed"] = "audioPlaybackFailed";
9658
- /**
9659
- * @internal
9660
- * Only fires on LocalAudioTrack instances
9658
+ /**
9659
+ * @internal
9660
+ * Only fires on LocalAudioTrack instances
9661
9661
  */
9662
9662
 
9663
9663
  TrackEvent["AudioSilenceDetected"] = "audioSilenceDetected";
@@ -9673,15 +9673,15 @@ var TrackEvent;
9673
9673
  /** @internal */
9674
9674
 
9675
9675
  TrackEvent["ElementDetached"] = "elementDetached";
9676
- /**
9677
- * @internal
9678
- * Only fires on LocalTracks
9676
+ /**
9677
+ * @internal
9678
+ * Only fires on LocalTracks
9679
9679
  */
9680
9680
 
9681
9681
  TrackEvent["UpstreamPaused"] = "upstreamPaused";
9682
- /**
9683
- * @internal
9684
- * Only fires on LocalTracks
9682
+ /**
9683
+ * @internal
9684
+ * Only fires on LocalTracks
9685
9685
  */
9686
9686
 
9687
9687
  TrackEvent["UpstreamResumed"] = "upstreamResumed";
@@ -9783,7 +9783,7 @@ class DeviceManager {
9783
9783
  }
9784
9784
  DeviceManager.mediaDeviceKinds = ['audioinput', 'audiooutput', 'videoinput'];
9785
9785
 
9786
- const version = '0.18.4';
9786
+ const version = '0.18.5';
9787
9787
  const protocolVersion = 7;
9788
9788
 
9789
9789
  const separator = '|';
@@ -9848,24 +9848,47 @@ function getClientInfo() {
9848
9848
  });
9849
9849
  return info;
9850
9850
  }
9851
- let emptyMediaStreamTrack;
9852
- function getEmptyMediaStreamTrack() {
9853
- if (!emptyMediaStreamTrack) {
9851
+ let emptyVideoStreamTrack;
9852
+ function getEmptyVideoStreamTrack() {
9853
+ var _a;
9854
+
9855
+ if (!emptyVideoStreamTrack) {
9854
9856
  const canvas = document.createElement('canvas');
9855
9857
  canvas.width = 2;
9856
- canvas.height = 2; // @ts-ignore
9858
+ canvas.height = 2;
9859
+ (_a = canvas.getContext('2d')) === null || _a === void 0 ? void 0 : _a.fillRect(0, 0, canvas.width, canvas.height); // @ts-ignore
9857
9860
 
9858
9861
  const emptyStream = canvas.captureStream();
9859
- [emptyMediaStreamTrack] = emptyStream.getTracks();
9862
+ [emptyVideoStreamTrack] = emptyStream.getTracks();
9863
+
9864
+ if (!emptyVideoStreamTrack) {
9865
+ throw Error('Could not get empty media stream video track');
9866
+ }
9867
+
9868
+ emptyVideoStreamTrack.enabled = false;
9869
+ }
9870
+
9871
+ return emptyVideoStreamTrack;
9872
+ }
9873
+ let emptyAudioStreamTrack;
9874
+ function getEmptyAudioStreamTrack() {
9875
+ if (!emptyAudioStreamTrack) {
9876
+ // implementation adapted from https://blog.mozilla.org/webrtc/warm-up-with-replacetrack/
9877
+ const ctx = new AudioContext();
9878
+ const oscillator = ctx.createOscillator();
9879
+ const dst = ctx.createMediaStreamDestination();
9880
+ oscillator.connect(dst);
9881
+ oscillator.start();
9882
+ [emptyAudioStreamTrack] = dst.stream.getAudioTracks();
9860
9883
 
9861
- if (!emptyMediaStreamTrack) {
9862
- throw Error('Could not get empty media stream track');
9884
+ if (!emptyAudioStreamTrack) {
9885
+ throw Error('Could not get empty media stream audio track');
9863
9886
  }
9864
9887
 
9865
- emptyMediaStreamTrack.enabled = false;
9888
+ emptyAudioStreamTrack.enabled = false;
9866
9889
  }
9867
9890
 
9868
- return emptyMediaStreamTrack;
9891
+ return emptyAudioStreamTrack;
9869
9892
  }
9870
9893
 
9871
9894
  var events = {exports: {}};
@@ -10328,7 +10351,7 @@ class Track extends events.exports.EventEmitter {
10328
10351
  };
10329
10352
 
10330
10353
  this.kind = kind;
10331
- this.mediaStreamTrack = mediaTrack;
10354
+ this._mediaStreamTrack = mediaTrack;
10332
10355
  this.source = Track.Source.Unknown;
10333
10356
 
10334
10357
  if (isWeb()) {
@@ -10345,6 +10368,10 @@ class Track extends events.exports.EventEmitter {
10345
10368
  return this._currentBitrate;
10346
10369
  }
10347
10370
 
10371
+ get mediaStreamTrack() {
10372
+ return this._mediaStreamTrack;
10373
+ }
10374
+
10348
10375
  attach(element) {
10349
10376
  let elementType = 'audio';
10350
10377
 
@@ -10378,7 +10405,7 @@ class Track extends events.exports.EventEmitter {
10378
10405
  // we'll want to re-attach it in that case
10379
10406
 
10380
10407
 
10381
- attachToElement(this.mediaStreamTrack, element);
10408
+ attachToElement(this._mediaStreamTrack, element);
10382
10409
 
10383
10410
  if (element instanceof HTMLAudioElement) {
10384
10411
  // manually play audio to detect audio playback status
@@ -10396,7 +10423,7 @@ class Track extends events.exports.EventEmitter {
10396
10423
  detach(element) {
10397
10424
  // detach from a single element
10398
10425
  if (element) {
10399
- detachTrack(this.mediaStreamTrack, element);
10426
+ detachTrack(this._mediaStreamTrack, element);
10400
10427
  const idx = this.attachedElements.indexOf(element);
10401
10428
 
10402
10429
  if (idx >= 0) {
@@ -10410,7 +10437,7 @@ class Track extends events.exports.EventEmitter {
10410
10437
 
10411
10438
  const detached = [];
10412
10439
  this.attachedElements.forEach(elm => {
10413
- detachTrack(this.mediaStreamTrack, elm);
10440
+ detachTrack(this._mediaStreamTrack, elm);
10414
10441
  detached.push(elm);
10415
10442
  this.recycleElement(elm);
10416
10443
  this.emit(TrackEvent.ElementDetached, elm);
@@ -10421,7 +10448,7 @@ class Track extends events.exports.EventEmitter {
10421
10448
  }
10422
10449
 
10423
10450
  stop() {
10424
- this.mediaStreamTrack.stop();
10451
+ this._mediaStreamTrack.stop();
10425
10452
 
10426
10453
  if (isWeb()) {
10427
10454
  document.removeEventListener('visibilitychange', this.appVisibilityChangedListener);
@@ -10429,11 +10456,11 @@ class Track extends events.exports.EventEmitter {
10429
10456
  }
10430
10457
 
10431
10458
  enable() {
10432
- this.mediaStreamTrack.enabled = true;
10459
+ this._mediaStreamTrack.enabled = true;
10433
10460
  }
10434
10461
 
10435
10462
  disable() {
10436
- this.mediaStreamTrack.enabled = false;
10463
+ this._mediaStreamTrack.enabled = false;
10437
10464
  }
10438
10465
 
10439
10466
  recycleElement(element) {
@@ -10663,14 +10690,15 @@ class LocalTrack extends Track {
10663
10690
  this.emit(TrackEvent.Ended, this);
10664
10691
  };
10665
10692
 
10666
- this.mediaStreamTrack.addEventListener('ended', this.handleEnded);
10693
+ this._mediaStreamTrack.addEventListener('ended', this.handleEnded);
10694
+
10667
10695
  this.constraints = constraints !== null && constraints !== void 0 ? constraints : mediaTrack.getConstraints();
10668
10696
  this.reacquireTrack = false;
10669
10697
  this.wasMuted = false;
10670
10698
  }
10671
10699
 
10672
10700
  get id() {
10673
- return this.mediaStreamTrack.id;
10701
+ return this._mediaStreamTrack.id;
10674
10702
  }
10675
10703
 
10676
10704
  get dimensions() {
@@ -10681,7 +10709,7 @@ class LocalTrack extends Track {
10681
10709
  const {
10682
10710
  width,
10683
10711
  height
10684
- } = this.mediaStreamTrack.getSettings();
10712
+ } = this._mediaStreamTrack.getSettings();
10685
10713
 
10686
10714
  if (width && height) {
10687
10715
  return {
@@ -10696,8 +10724,8 @@ class LocalTrack extends Track {
10696
10724
  get isUpstreamPaused() {
10697
10725
  return this._isUpstreamPaused;
10698
10726
  }
10699
- /**
10700
- * @returns DeviceID of the device that is currently being used for this track
10727
+ /**
10728
+ * @returns DeviceID of the device that is currently being used for this track
10701
10729
  */
10702
10730
 
10703
10731
 
@@ -10710,7 +10738,8 @@ class LocalTrack extends Track {
10710
10738
  const {
10711
10739
  deviceId,
10712
10740
  groupId
10713
- } = this.mediaStreamTrack.getSettings();
10741
+ } = this._mediaStreamTrack.getSettings();
10742
+
10714
10743
  const kind = this.kind === Track.Kind.Audio ? 'audioinput' : 'videoinput';
10715
10744
  return DeviceManager.getInstance().normalizeDeviceId(kind, deviceId, groupId);
10716
10745
  }
@@ -10732,17 +10761,20 @@ class LocalTrack extends Track {
10732
10761
 
10733
10762
 
10734
10763
  this.attachedElements.forEach(el => {
10735
- detachTrack(this.mediaStreamTrack, el);
10764
+ detachTrack(this._mediaStreamTrack, el);
10736
10765
  });
10737
- this.mediaStreamTrack.removeEventListener('ended', this.handleEnded); // on Safari, the old audio track must be stopped before attempting to acquire
10766
+
10767
+ this._mediaStreamTrack.removeEventListener('ended', this.handleEnded); // on Safari, the old audio track must be stopped before attempting to acquire
10738
10768
  // the new track, otherwise the new track will stop with
10739
10769
  // 'A MediaStreamTrack ended due to a capture failure`
10740
10770
 
10741
- this.mediaStreamTrack.stop();
10771
+
10772
+ this._mediaStreamTrack.stop();
10773
+
10742
10774
  track.addEventListener('ended', this.handleEnded);
10743
10775
  livekitLogger.debug('replace MediaStreamTrack');
10744
10776
  await this.sender.replaceTrack(track);
10745
- this.mediaStreamTrack = track;
10777
+ this._mediaStreamTrack = track;
10746
10778
  this.attachedElements.forEach(el => {
10747
10779
  attachToElement(track, el);
10748
10780
  });
@@ -10773,20 +10805,23 @@ class LocalTrack extends Track {
10773
10805
 
10774
10806
 
10775
10807
  this.attachedElements.forEach(el => {
10776
- detachTrack(this.mediaStreamTrack, el);
10808
+ detachTrack(this._mediaStreamTrack, el);
10777
10809
  });
10778
- this.mediaStreamTrack.removeEventListener('ended', this.handleEnded); // on Safari, the old audio track must be stopped before attempting to acquire
10810
+
10811
+ this._mediaStreamTrack.removeEventListener('ended', this.handleEnded); // on Safari, the old audio track must be stopped before attempting to acquire
10779
10812
  // the new track, otherwise the new track will stop with
10780
10813
  // 'A MediaStreamTrack ended due to a capture failure`
10781
10814
 
10782
- this.mediaStreamTrack.stop(); // create new track and attach
10815
+
10816
+ this._mediaStreamTrack.stop(); // create new track and attach
10817
+
10783
10818
 
10784
10819
  const mediaStream = await navigator.mediaDevices.getUserMedia(streamConstraints);
10785
10820
  const newTrack = mediaStream.getTracks()[0];
10786
10821
  newTrack.addEventListener('ended', this.handleEnded);
10787
10822
  livekitLogger.debug('re-acquired MediaStreamTrack');
10788
10823
  await this.sender.replaceTrack(newTrack);
10789
- this.mediaStreamTrack = newTrack;
10824
+ this._mediaStreamTrack = newTrack;
10790
10825
  this.attachedElements.forEach(el => {
10791
10826
  attachToElement(newTrack, el);
10792
10827
  });
@@ -10801,12 +10836,12 @@ class LocalTrack extends Track {
10801
10836
  }
10802
10837
 
10803
10838
  this.isMuted = muted;
10804
- this.mediaStreamTrack.enabled = !muted;
10839
+ this._mediaStreamTrack.enabled = !muted;
10805
10840
  this.emit(muted ? TrackEvent.Muted : TrackEvent.Unmuted, this);
10806
10841
  }
10807
10842
 
10808
10843
  get needsReAcquisition() {
10809
- return this.mediaStreamTrack.readyState !== 'live' || this.mediaStreamTrack.muted || !this.mediaStreamTrack.enabled || this.reacquireTrack;
10844
+ return this._mediaStreamTrack.readyState !== 'live' || this._mediaStreamTrack.muted || !this._mediaStreamTrack.enabled || this.reacquireTrack;
10810
10845
  }
10811
10846
 
10812
10847
  async handleAppVisibilityChanged() {
@@ -10840,7 +10875,8 @@ class LocalTrack extends Track {
10840
10875
 
10841
10876
  this._isUpstreamPaused = true;
10842
10877
  this.emit(TrackEvent.UpstreamPaused, this);
10843
- await this.sender.replaceTrack(getEmptyMediaStreamTrack());
10878
+ const emptyTrack = this.kind === Track.Kind.Audio ? getEmptyAudioStreamTrack() : getEmptyVideoStreamTrack();
10879
+ await this.sender.replaceTrack(emptyTrack);
10844
10880
  }
10845
10881
 
10846
10882
  async resumeUpstream() {
@@ -10855,7 +10891,7 @@ class LocalTrack extends Track {
10855
10891
 
10856
10892
  this._isUpstreamPaused = false;
10857
10893
  this.emit(TrackEvent.UpstreamResumed, this);
10858
- await this.sender.replaceTrack(this.mediaStreamTrack);
10894
+ await this.sender.replaceTrack(this._mediaStreamTrack);
10859
10895
  }
10860
10896
 
10861
10897
  }
@@ -10924,9 +10960,9 @@ function constraintsForOptions(options) {
10924
10960
 
10925
10961
  return constraints;
10926
10962
  }
10927
- /**
10928
- * This function detects silence on a given [[Track]] instance.
10929
- * Returns true if the track seems to be entirely silent.
10963
+ /**
10964
+ * This function detects silence on a given [[Track]] instance.
10965
+ * Returns true if the track seems to be entirely silent.
10930
10966
  */
10931
10967
 
10932
10968
  async function detectSilence(track) {
@@ -10949,8 +10985,8 @@ async function detectSilence(track) {
10949
10985
 
10950
10986
  return false;
10951
10987
  }
10952
- /**
10953
- * @internal
10988
+ /**
10989
+ * @internal
10954
10990
  */
10955
10991
 
10956
10992
  function getNewAudioContext() {
@@ -10980,7 +11016,9 @@ class LocalAudioTrack extends LocalTrack {
10980
11016
  try {
10981
11017
  stats = await this.getSenderStats();
10982
11018
  } catch (e) {
10983
- livekitLogger.error('could not get audio sender stats', e);
11019
+ livekitLogger.error('could not get audio sender stats', {
11020
+ error: e
11021
+ });
10984
11022
  return;
10985
11023
  }
10986
11024
 
@@ -11014,7 +11052,7 @@ class LocalAudioTrack extends LocalTrack {
11014
11052
  if (this.source === Track.Source.Microphone && this.stopOnMute) {
11015
11053
  livekitLogger.debug('stopping mic track'); // also stop the track, so that microphone indicator is turned off
11016
11054
 
11017
- this.mediaStreamTrack.stop();
11055
+ this._mediaStreamTrack.stop();
11018
11056
  }
11019
11057
 
11020
11058
  await super.mute();
@@ -11168,7 +11206,9 @@ class LocalVideoTrack extends LocalTrack {
11168
11206
 
11169
11207
  stop() {
11170
11208
  this.sender = undefined;
11171
- this.mediaStreamTrack.getConstraints();
11209
+
11210
+ this._mediaStreamTrack.getConstraints();
11211
+
11172
11212
  super.stop();
11173
11213
  }
11174
11214
 
@@ -11176,7 +11216,7 @@ class LocalVideoTrack extends LocalTrack {
11176
11216
  if (this.source === Track.Source.Camera) {
11177
11217
  livekitLogger.debug('stopping camera track'); // also stop the track, so that camera indicator is turned off
11178
11218
 
11179
- this.mediaStreamTrack.stop();
11219
+ this._mediaStreamTrack.stop();
11180
11220
  }
11181
11221
 
11182
11222
  await super.mute();
@@ -11278,9 +11318,9 @@ class LocalVideoTrack extends LocalTrack {
11278
11318
 
11279
11319
  await this.restart(constraints);
11280
11320
  }
11281
- /**
11282
- * @internal
11283
- * Sets layers that should be publishing
11321
+ /**
11322
+ * @internal
11323
+ * Sets layers that should be publishing
11284
11324
  */
11285
11325
 
11286
11326
 
@@ -11357,7 +11397,7 @@ class LocalVideoTrack extends LocalTrack {
11357
11397
  if (!isMobile()) return;
11358
11398
 
11359
11399
  if (this.isInBackground && this.source === Track.Source.Camera) {
11360
- this.mediaStreamTrack.enabled = false;
11400
+ this._mediaStreamTrack.enabled = false;
11361
11401
  }
11362
11402
  }
11363
11403
 
@@ -11486,8 +11526,8 @@ class RemoteAudioTrack extends RemoteTrack {
11486
11526
 
11487
11527
  this.elementVolume = 1;
11488
11528
  }
11489
- /**
11490
- * sets the volume for all attached audio elements
11529
+ /**
11530
+ * sets the volume for all attached audio elements
11491
11531
  */
11492
11532
 
11493
11533
 
@@ -11498,8 +11538,8 @@ class RemoteAudioTrack extends RemoteTrack {
11498
11538
 
11499
11539
  this.elementVolume = volume;
11500
11540
  }
11501
- /**
11502
- * gets the volume for all attached audio elements
11541
+ /**
11542
+ * gets the volume for all attached audio elements
11503
11543
  */
11504
11544
 
11505
11545
 
@@ -11639,11 +11679,23 @@ class RemoteVideoTrack extends RemoteTrack {
11639
11679
  this.updateDimensions();
11640
11680
  }, REACTION_DELAY);
11641
11681
  this.adaptiveStreamSettings = adaptiveStreamSettings;
11682
+
11683
+ if (this.isAdaptiveStream) {
11684
+ this.streamState = Track.StreamState.Paused;
11685
+ }
11642
11686
  }
11643
11687
 
11644
11688
  get isAdaptiveStream() {
11645
11689
  return this.adaptiveStreamSettings !== undefined;
11646
11690
  }
11691
+
11692
+ get mediaStreamTrack() {
11693
+ if (this.isAdaptiveStream && this.attachedElements.length === 0) {
11694
+ throw Error('When using adaptiveStream, you need to use remoteVideoTrack.attach() to add the track to a HTMLVideoElement, direct usage of mediaStreamTrack is unsupported in this case');
11695
+ }
11696
+
11697
+ return this._mediaStreamTrack;
11698
+ }
11647
11699
  /** @internal */
11648
11700
 
11649
11701
 
@@ -11652,9 +11704,9 @@ class RemoteVideoTrack extends RemoteTrack {
11652
11704
  this.attachedElements.forEach(element => {
11653
11705
  // detach or attach
11654
11706
  if (muted) {
11655
- detachTrack(this.mediaStreamTrack, element);
11707
+ detachTrack(this._mediaStreamTrack, element);
11656
11708
  } else {
11657
- attachToElement(this.mediaStreamTrack, element);
11709
+ attachToElement(this._mediaStreamTrack, element);
11658
11710
  }
11659
11711
  });
11660
11712
  }
@@ -11848,8 +11900,8 @@ class TrackPublication extends events.exports.EventEmitter {
11848
11900
  get isSubscribed() {
11849
11901
  return this.track !== undefined;
11850
11902
  }
11851
- /**
11852
- * an [AudioTrack] if this publication holds an audio track
11903
+ /**
11904
+ * an [AudioTrack] if this publication holds an audio track
11853
11905
  */
11854
11906
 
11855
11907
 
@@ -11858,8 +11910,8 @@ class TrackPublication extends events.exports.EventEmitter {
11858
11910
  return this.track;
11859
11911
  }
11860
11912
  }
11861
- /**
11862
- * an [VideoTrack] if this publication holds a video track
11913
+ /**
11914
+ * an [VideoTrack] if this publication holds a video track
11863
11915
  */
11864
11916
 
11865
11917
 
@@ -11945,8 +11997,8 @@ class LocalTrackPublication extends TrackPublication {
11945
11997
  get videoTrack() {
11946
11998
  return super.videoTrack;
11947
11999
  }
11948
- /**
11949
- * Mute the track associated with this publication
12000
+ /**
12001
+ * Mute the track associated with this publication
11950
12002
  */
11951
12003
 
11952
12004
 
@@ -11955,8 +12007,8 @@ class LocalTrackPublication extends TrackPublication {
11955
12007
 
11956
12008
  return (_a = this.track) === null || _a === void 0 ? void 0 : _a.mute();
11957
12009
  }
11958
- /**
11959
- * Unmute track associated with this publication
12010
+ /**
12011
+ * Unmute track associated with this publication
11960
12012
  */
11961
12013
 
11962
12014
 
@@ -11965,10 +12017,10 @@ class LocalTrackPublication extends TrackPublication {
11965
12017
 
11966
12018
  return (_a = this.track) === null || _a === void 0 ? void 0 : _a.unmute();
11967
12019
  }
11968
- /**
11969
- * Pauses the media stream track associated with this publication from being sent to the server
11970
- * and signals "muted" event to other participants
11971
- * Useful if you want to pause the stream without pausing the local media stream track
12020
+ /**
12021
+ * Pauses the media stream track associated with this publication from being sent to the server
12022
+ * and signals "muted" event to other participants
12023
+ * Useful if you want to pause the stream without pausing the local media stream track
11972
12024
  */
11973
12025
 
11974
12026
 
@@ -11977,9 +12029,9 @@ class LocalTrackPublication extends TrackPublication {
11977
12029
 
11978
12030
  await ((_a = this.track) === null || _a === void 0 ? void 0 : _a.pauseUpstream());
11979
12031
  }
11980
- /**
11981
- * Resumes sending the media stream track associated with this publication to the server after a call to [[pauseUpstream()]]
11982
- * and signals "unmuted" event to other participants (unless the track is explicitly muted)
12032
+ /**
12033
+ * Resumes sending the media stream track associated with this publication to the server after a call to [[pauseUpstream()]]
12034
+ * and signals "unmuted" event to other participants (unless the track is explicitly muted)
11983
12035
  */
11984
12036
 
11985
12037
 
@@ -12024,8 +12076,8 @@ var AudioPresets;
12024
12076
  maxBitrate: 32000
12025
12077
  };
12026
12078
  })(AudioPresets || (AudioPresets = {}));
12027
- /**
12028
- * Sane presets for video resolution/encoding
12079
+ /**
12080
+ * Sane presets for video resolution/encoding
12029
12081
  */
12030
12082
 
12031
12083
 
@@ -12055,8 +12107,8 @@ const VideoPresets = {
12055
12107
  /** @deprecated */
12056
12108
  fhd: new VideoPreset(1920, 1080, 3000000, 30)
12057
12109
  };
12058
- /**
12059
- * Four by three presets
12110
+ /**
12111
+ * Four by three presets
12060
12112
  */
12061
12113
 
12062
12114
  const VideoPresets43 = {
@@ -12154,11 +12206,11 @@ class Participant extends events.exports.EventEmitter {
12154
12206
  getTracks() {
12155
12207
  return Array.from(this.tracks.values());
12156
12208
  }
12157
- /**
12158
- * Finds the first track that matches the source filter, for example, getting
12159
- * the user's camera track with getTrackBySource(Track.Source.Camera).
12160
- * @param source
12161
- * @returns
12209
+ /**
12210
+ * Finds the first track that matches the source filter, for example, getting
12211
+ * the user's camera track with getTrackBySource(Track.Source.Camera).
12212
+ * @param source
12213
+ * @returns
12162
12214
  */
12163
12215
 
12164
12216
 
@@ -12191,10 +12243,10 @@ class Participant extends events.exports.EventEmitter {
12191
12243
  }
12192
12244
  }
12193
12245
  }
12194
- /**
12195
- * Finds the first track that matches the track's name.
12196
- * @param name
12197
- * @returns
12246
+ /**
12247
+ * Finds the first track that matches the track's name.
12248
+ * @param name
12249
+ * @returns
12198
12250
  */
12199
12251
 
12200
12252
 
@@ -12404,9 +12456,10 @@ function computeVideoEncodings(isScreenShare, width, height, options) {
12404
12456
  }
12405
12457
 
12406
12458
  const useSimulcast = options === null || options === void 0 ? void 0 : options.simulcast;
12459
+ const scalabilityMode = options === null || options === void 0 ? void 0 : options.scalabilityMode;
12407
12460
 
12408
- if (!videoEncoding && !useSimulcast || !width || !height) {
12409
- // when we aren't simulcasting, will need to return a single encoding without
12461
+ if (!videoEncoding && !useSimulcast && !scalabilityMode || !width || !height) {
12462
+ // when we aren't simulcasting or svc, will need to return a single encoding without
12410
12463
  // capping bandwidth. we always require a encoding for dynacast
12411
12464
  return [{}];
12412
12465
  }
@@ -12417,11 +12470,41 @@ function computeVideoEncodings(isScreenShare, width, height, options) {
12417
12470
  livekitLogger.debug('using video encoding', videoEncoding);
12418
12471
  }
12419
12472
 
12473
+ const original = new VideoPreset(width, height, videoEncoding.maxBitrate, videoEncoding.maxFramerate);
12474
+ livekitLogger.debug("scalabilityMode ".concat(scalabilityMode));
12475
+
12476
+ if (scalabilityMode) {
12477
+ const encodings = []; // svc use first encoding as the original, so we sort encoding from high to low
12478
+
12479
+ switch (scalabilityMode) {
12480
+ case 'L3T3':
12481
+ for (let i = 0; i < 3; i += 1) {
12482
+ encodings.push({
12483
+ rid: videoRids[2 - i],
12484
+ scaleResolutionDownBy: 2 ** i,
12485
+ maxBitrate: videoEncoding ? videoEncoding.maxBitrate / 2 ** i : 0,
12486
+
12487
+ /* @ts-ignore */
12488
+ maxFramerate: original.encoding.maxFramerate,
12489
+
12490
+ /* @ts-ignore */
12491
+ scalabilityMode: 'L3T3'
12492
+ });
12493
+ }
12494
+
12495
+ livekitLogger.debug('encodings', encodings);
12496
+ return encodings;
12497
+
12498
+ default:
12499
+ // TODO : support other scalability modes
12500
+ throw new Error("unsupported scalabilityMode: ".concat(scalabilityMode));
12501
+ }
12502
+ }
12503
+
12420
12504
  if (!useSimulcast) {
12421
12505
  return [videoEncoding];
12422
12506
  }
12423
12507
 
12424
- const original = new VideoPreset(width, height, videoEncoding.maxBitrate, videoEncoding.maxFramerate);
12425
12508
  let presets = [];
12426
12509
 
12427
12510
  if (isScreenShare) {
@@ -12590,9 +12673,9 @@ class RemoteTrackPublication extends TrackPublication {
12590
12673
  this.emitTrackUpdate();
12591
12674
  };
12592
12675
  }
12593
- /**
12594
- * Subscribe or unsubscribe to this remote track
12595
- * @param subscribed true to subscribe to a track, false to unsubscribe
12676
+ /**
12677
+ * Subscribe or unsubscribe to this remote track
12678
+ * @param subscribed true to subscribe to a track, false to unsubscribe
12596
12679
  */
12597
12680
 
12598
12681
 
@@ -12622,8 +12705,8 @@ class RemoteTrackPublication extends TrackPublication {
12622
12705
 
12623
12706
  return TrackPublication.SubscriptionStatus.Subscribed;
12624
12707
  }
12625
- /**
12626
- * Returns true if track is subscribed, and ready for playback
12708
+ /**
12709
+ * Returns true if track is subscribed, and ready for playback
12627
12710
  */
12628
12711
 
12629
12712
 
@@ -12642,11 +12725,11 @@ class RemoteTrackPublication extends TrackPublication {
12642
12725
  get isEnabled() {
12643
12726
  return !this.disabled;
12644
12727
  }
12645
- /**
12646
- * disable server from sending down data for this track. this is useful when
12647
- * the participant is off screen, you may disable streaming down their video
12648
- * to reduce bandwidth requirements
12649
- * @param enabled
12728
+ /**
12729
+ * disable server from sending down data for this track. this is useful when
12730
+ * the participant is off screen, you may disable streaming down their video
12731
+ * to reduce bandwidth requirements
12732
+ * @param enabled
12650
12733
  */
12651
12734
 
12652
12735
 
@@ -12658,12 +12741,12 @@ class RemoteTrackPublication extends TrackPublication {
12658
12741
  this.disabled = !enabled;
12659
12742
  this.emitTrackUpdate();
12660
12743
  }
12661
- /**
12662
- * for tracks that support simulcasting, adjust subscribed quality
12663
- *
12664
- * This indicates the highest quality the client can accept. if network
12665
- * bandwidth does not allow, server will automatically reduce quality to
12666
- * optimize for uninterrupted video
12744
+ /**
12745
+ * for tracks that support simulcasting, adjust subscribed quality
12746
+ *
12747
+ * This indicates the highest quality the client can accept. if network
12748
+ * bandwidth does not allow, server will automatically reduce quality to
12749
+ * optimize for uninterrupted video
12667
12750
  */
12668
12751
 
12669
12752
 
@@ -12823,8 +12906,8 @@ class RemoteParticipant extends Participant {
12823
12906
  return track;
12824
12907
  }
12825
12908
  }
12826
- /**
12827
- * sets the volume on the participant's microphone track if it exists.
12909
+ /**
12910
+ * sets the volume on the participant's microphone track if it exists.
12828
12911
  */
12829
12912
 
12830
12913
 
@@ -12835,9 +12918,9 @@ class RemoteParticipant extends Participant {
12835
12918
  audioPublication.track.setVolume(volume);
12836
12919
  }
12837
12920
  }
12838
- /**
12839
- * gets the volume on the participant's microphone track
12840
- * returns undefined if no microphone track exists
12921
+ /**
12922
+ * gets the volume on the participant's microphone track
12923
+ * returns undefined if no microphone track exists
12841
12924
  */
12842
12925
 
12843
12926
 
@@ -13146,31 +13229,31 @@ class LocalParticipant extends Participant {
13146
13229
  return track;
13147
13230
  }
13148
13231
  }
13149
- /**
13150
- * Enable or disable a participant's camera track.
13151
- *
13152
- * If a track has already published, it'll mute or unmute the track.
13153
- * Resolves with a `LocalTrackPublication` instance if successful and `undefined` otherwise
13232
+ /**
13233
+ * Enable or disable a participant's camera track.
13234
+ *
13235
+ * If a track has already published, it'll mute or unmute the track.
13236
+ * Resolves with a `LocalTrackPublication` instance if successful and `undefined` otherwise
13154
13237
  */
13155
13238
 
13156
13239
 
13157
13240
  setCameraEnabled(enabled) {
13158
13241
  return this.setTrackEnabled(Track.Source.Camera, enabled);
13159
13242
  }
13160
- /**
13161
- * Enable or disable a participant's microphone track.
13162
- *
13163
- * If a track has already published, it'll mute or unmute the track.
13164
- * Resolves with a `LocalTrackPublication` instance if successful and `undefined` otherwise
13243
+ /**
13244
+ * Enable or disable a participant's microphone track.
13245
+ *
13246
+ * If a track has already published, it'll mute or unmute the track.
13247
+ * Resolves with a `LocalTrackPublication` instance if successful and `undefined` otherwise
13165
13248
  */
13166
13249
 
13167
13250
 
13168
13251
  setMicrophoneEnabled(enabled) {
13169
13252
  return this.setTrackEnabled(Track.Source.Microphone, enabled);
13170
13253
  }
13171
- /**
13172
- * Start or stop sharing a participant's screen
13173
- * Resolves with a `LocalTrackPublication` instance if successful and `undefined` otherwise
13254
+ /**
13255
+ * Start or stop sharing a participant's screen
13256
+ * Resolves with a `LocalTrackPublication` instance if successful and `undefined` otherwise
13174
13257
  */
13175
13258
 
13176
13259
 
@@ -13190,10 +13273,10 @@ class LocalParticipant extends Participant {
13190
13273
 
13191
13274
  return changed;
13192
13275
  }
13193
- /**
13194
- * Enable or disable publishing for a track by source. This serves as a simple
13195
- * way to manage the common tracks (camera, mic, or screen share).
13196
- * Resolves with LocalTrackPublication if successful and void otherwise
13276
+ /**
13277
+ * Enable or disable publishing for a track by source. This serves as a simple
13278
+ * way to manage the common tracks (camera, mic, or screen share).
13279
+ * Resolves with LocalTrackPublication if successful and void otherwise
13197
13280
  */
13198
13281
 
13199
13282
 
@@ -13266,9 +13349,9 @@ class LocalParticipant extends Participant {
13266
13349
 
13267
13350
  return track;
13268
13351
  }
13269
- /**
13270
- * Publish both camera and microphone at the same time. This is useful for
13271
- * displaying a single Permission Dialog box to the end user.
13352
+ /**
13353
+ * Publish both camera and microphone at the same time. This is useful for
13354
+ * displaying a single Permission Dialog box to the end user.
13272
13355
  */
13273
13356
 
13274
13357
 
@@ -13292,10 +13375,10 @@ class LocalParticipant extends Participant {
13292
13375
  this.pendingPublishing.delete(Track.Source.Microphone);
13293
13376
  }
13294
13377
  }
13295
- /**
13296
- * Create local camera and/or microphone tracks
13297
- * @param options
13298
- * @returns
13378
+ /**
13379
+ * Create local camera and/or microphone tracks
13380
+ * @param options
13381
+ * @returns
13299
13382
  */
13300
13383
 
13301
13384
 
@@ -13353,10 +13436,10 @@ class LocalParticipant extends Participant {
13353
13436
  return track;
13354
13437
  });
13355
13438
  }
13356
- /**
13357
- * Creates a screen capture tracks with getDisplayMedia().
13358
- * A LocalVideoTrack is always created and returned.
13359
- * If { audio: true }, and the browser supports audio capture, a LocalAudioTrack is also created.
13439
+ /**
13440
+ * Creates a screen capture tracks with getDisplayMedia().
13441
+ * A LocalVideoTrack is always created and returned.
13442
+ * If { audio: true }, and the browser supports audio capture, a LocalAudioTrack is also created.
13360
13443
  */
13361
13444
 
13362
13445
 
@@ -13405,15 +13488,15 @@ class LocalParticipant extends Participant {
13405
13488
 
13406
13489
  return localTracks;
13407
13490
  }
13408
- /**
13409
- * Publish a new track to the room
13410
- * @param track
13411
- * @param options
13491
+ /**
13492
+ * Publish a new track to the room
13493
+ * @param track
13494
+ * @param options
13412
13495
  */
13413
13496
 
13414
13497
 
13415
13498
  async publishTrack(track, options) {
13416
- var _a, _b, _c, _d, _e, _f;
13499
+ var _a, _b, _c, _d, _e, _f, _g;
13417
13500
 
13418
13501
  const opts = _objectSpread2(_objectSpread2({}, (_a = this.roomOptions) === null || _a === void 0 ? void 0 : _a.publishDefaults), options); // convert raw media track into audio or video track
13419
13502
 
@@ -13486,7 +13569,19 @@ class LocalParticipant extends Participant {
13486
13569
  const height = (_e = settings.height) !== null && _e !== void 0 ? _e : (_f = track.dimensions) === null || _f === void 0 ? void 0 : _f.height; // width and height should be defined for video
13487
13570
 
13488
13571
  req.width = width !== null && width !== void 0 ? width : 0;
13489
- req.height = height !== null && height !== void 0 ? height : 0;
13572
+ req.height = height !== null && height !== void 0 ? height : 0; // for svc codecs, disable simulcast and enable scalability L3T3
13573
+ // by default
13574
+
13575
+ if (track instanceof LocalVideoTrack) {
13576
+ if ((opts === null || opts === void 0 ? void 0 : opts.videoCodec) === 'vp9' || (opts === null || opts === void 0 ? void 0 : opts.videoCodec) === 'av1') {
13577
+ opts.simulcast = false;
13578
+ opts.scalabilityMode = (_g = opts.scalabilityMode) !== null && _g !== void 0 ? _g : 'L3T3';
13579
+ } else {
13580
+ // other codecs, unset scalability
13581
+ opts.scalabilityMode = undefined;
13582
+ }
13583
+ }
13584
+
13490
13585
  encodings = computeVideoEncodings(track.source === Track.Source.ScreenShare, width, height, opts);
13491
13586
  req.layers = videoLayersFromEncodings(req.width, req.height, encodings);
13492
13587
  } else if (track.kind === Track.Kind.Audio && opts.audioBitrate) {
@@ -13516,6 +13611,11 @@ class LocalParticipant extends Participant {
13516
13611
  }
13517
13612
 
13518
13613
  const transceiver = this.engine.publisher.pc.addTransceiver(track.mediaStreamTrack, transceiverInit);
13614
+
13615
+ if (opts.videoCodec) {
13616
+ this.setPreferredCodec(transceiver, track.kind, opts.videoCodec);
13617
+ }
13618
+
13519
13619
  this.engine.negotiate(); // store RTPSender
13520
13620
 
13521
13621
  track.sender = transceiver.sender;
@@ -13526,10 +13626,6 @@ class LocalParticipant extends Participant {
13526
13626
  track.startMonitor();
13527
13627
  }
13528
13628
 
13529
- if (opts.videoCodec) {
13530
- this.setPreferredCodec(transceiver, track.kind, opts.videoCodec);
13531
- }
13532
-
13533
13629
  this.addTrackPublication(publication); // send event for publication
13534
13630
 
13535
13631
  this.emit(ParticipantEvent.LocalTrackPublished, publication);
@@ -13621,16 +13717,16 @@ class LocalParticipant extends Participant {
13621
13717
  });
13622
13718
  return publications;
13623
13719
  }
13624
- /**
13625
- * Publish a new data payload to the room. Data will be forwarded to each
13626
- * participant in the room if the destination argument is empty
13627
- *
13628
- * @param data Uint8Array of the payload. To send string data, use TextEncoder.encode
13629
- * @param kind whether to send this as reliable or lossy.
13630
- * For data that you need delivery guarantee (such as chat messages), use Reliable.
13631
- * For data that should arrive as quickly as possible, but you are ok with dropped
13632
- * packets, use Lossy.
13633
- * @param destination the participants who will receive the message
13720
+ /**
13721
+ * Publish a new data payload to the room. Data will be forwarded to each
13722
+ * participant in the room if the destination argument is empty
13723
+ *
13724
+ * @param data Uint8Array of the payload. To send string data, use TextEncoder.encode
13725
+ * @param kind whether to send this as reliable or lossy.
13726
+ * For data that you need delivery guarantee (such as chat messages), use Reliable.
13727
+ * For data that should arrive as quickly as possible, but you are ok with dropped
13728
+ * packets, use Lossy.
13729
+ * @param destination the participants who will receive the message
13634
13730
  */
13635
13731
 
13636
13732
 
@@ -13657,22 +13753,22 @@ class LocalParticipant extends Participant {
13657
13753
  };
13658
13754
  await this.engine.sendDataPacket(packet, kind);
13659
13755
  }
13660
- /**
13661
- * Control who can subscribe to LocalParticipant's published tracks.
13662
- *
13663
- * By default, all participants can subscribe. This allows fine-grained control over
13664
- * who is able to subscribe at a participant and track level.
13665
- *
13666
- * Note: if access is given at a track-level (i.e. both [allParticipantsAllowed] and
13667
- * [ParticipantTrackPermission.allTracksAllowed] are false), any newer published tracks
13668
- * will not grant permissions to any participants and will require a subsequent
13669
- * permissions update to allow subscription.
13670
- *
13671
- * @param allParticipantsAllowed Allows all participants to subscribe all tracks.
13672
- * Takes precedence over [[participantTrackPermissions]] if set to true.
13673
- * By default this is set to true.
13674
- * @param participantTrackPermissions Full list of individual permissions per
13675
- * participant/track. Any omitted participants will not receive any permissions.
13756
+ /**
13757
+ * Control who can subscribe to LocalParticipant's published tracks.
13758
+ *
13759
+ * By default, all participants can subscribe. This allows fine-grained control over
13760
+ * who is able to subscribe at a participant and track level.
13761
+ *
13762
+ * Note: if access is given at a track-level (i.e. both [allParticipantsAllowed] and
13763
+ * [ParticipantTrackPermission.allTracksAllowed] are false), any newer published tracks
13764
+ * will not grant permissions to any participants and will require a subsequent
13765
+ * permissions update to allow subscription.
13766
+ *
13767
+ * @param allParticipantsAllowed Allows all participants to subscribe all tracks.
13768
+ * Takes precedence over [[participantTrackPermissions]] if set to true.
13769
+ * By default this is set to true.
13770
+ * @param participantTrackPermissions Full list of individual permissions per
13771
+ * participant/track. Any omitted participants will not receive any permissions.
13676
13772
  */
13677
13773
 
13678
13774
 
@@ -13711,21 +13807,38 @@ class LocalParticipant extends Participant {
13711
13807
 
13712
13808
  const cap = RTCRtpSender.getCapabilities(kind);
13713
13809
  if (!cap) return;
13714
- const selected = cap.codecs.find(c => {
13810
+ let selected;
13811
+ const codecs = [];
13812
+ cap.codecs.forEach(c => {
13715
13813
  const codec = c.mimeType.toLowerCase();
13716
- const matchesVideoCodec = codec === "video/".concat(videoCodec); // for h264 codecs that have sdpFmtpLine available, use only if the
13814
+ const matchesVideoCodec = codec === "video/".concat(videoCodec);
13815
+
13816
+ if (selected !== undefined) {
13817
+ codecs.push(c);
13818
+ return;
13819
+ } // for h264 codecs that have sdpFmtpLine available, use only if the
13717
13820
  // profile-level-id is 42e01f for cross-browser compatibility
13718
13821
 
13822
+
13719
13823
  if (videoCodec === 'h264' && c.sdpFmtpLine) {
13720
- return matchesVideoCodec && c.sdpFmtpLine.includes('profile-level-id=42e01f');
13824
+ if (matchesVideoCodec && c.sdpFmtpLine.includes('profile-level-id=42e01f')) {
13825
+ selected = c;
13826
+ return;
13827
+ }
13721
13828
  }
13722
13829
 
13723
- return matchesVideoCodec || codec === 'audio/opus';
13830
+ if (matchesVideoCodec || codec === 'audio/opus') {
13831
+ selected = c;
13832
+ return;
13833
+ }
13834
+
13835
+ codecs.push(c);
13724
13836
  });
13725
13837
 
13726
13838
  if (selected && 'setCodecPreferences' in transceiver) {
13727
13839
  // @ts-ignore
13728
- transceiver.setCodecPreferences([selected]);
13840
+ codecs.unshift(selected);
13841
+ transceiver.setCodecPreferences(codecs);
13729
13842
  }
13730
13843
  }
13731
13844
  /** @internal */
@@ -18097,9 +18210,11 @@ class RTCEngine extends events.exports.EventEmitter {
18097
18210
  };
18098
18211
 
18099
18212
  let primaryPC = this.publisher.pc;
18213
+ let secondaryPC = this.subscriber.pc;
18100
18214
 
18101
18215
  if (joinResponse.subscriberPrimary) {
18102
- primaryPC = this.subscriber.pc; // in subscriber primary mode, server side opens sub data channels.
18216
+ primaryPC = this.subscriber.pc;
18217
+ secondaryPC = this.publisher.pc; // in subscriber primary mode, server side opens sub data channels.
18103
18218
 
18104
18219
  this.subscriber.pc.ondatachannel = this.handleDataChannel;
18105
18220
  }
@@ -18130,11 +18245,18 @@ class RTCEngine extends events.exports.EventEmitter {
18130
18245
  // on Safari, PeerConnection will switch to 'disconnected' during renegotiation
18131
18246
  if (this.pcState === PCState.Connected) {
18132
18247
  this.pcState = PCState.Disconnected;
18133
- this.handleDisconnect('peerconnection');
18248
+ this.handleDisconnect('primary peerconnection');
18134
18249
  }
18135
18250
  }
18136
18251
  };
18137
18252
 
18253
+ secondaryPC.onconnectionstatechange = async () => {
18254
+ // also reconnect if secondary peerconnection fails
18255
+ if (secondaryPC.connectionState === 'failed') {
18256
+ this.handleDisconnect('secondary peerconnection');
18257
+ }
18258
+ };
18259
+
18138
18260
  if (isWeb()) {
18139
18261
  this.subscriber.pc.ontrack = ev => {
18140
18262
  this.emit(EngineEvent.MediaTrackAdded, ev.track, ev.streams[0], ev.receiver);
@@ -18488,12 +18610,11 @@ const publishDefaults = {
18488
18610
  };
18489
18611
  const audioDefaults = {
18490
18612
  autoGainControl: true,
18491
- channelCount: 1,
18492
18613
  echoCancellation: true,
18493
18614
  noiseSuppression: true
18494
18615
  };
18495
18616
  const videoDefaults = {
18496
- resolution: VideoPresets.h540.resolution
18617
+ resolution: VideoPresets.h720.resolution
18497
18618
  };
18498
18619
 
18499
18620
  var RoomState;
@@ -18503,20 +18624,20 @@ var RoomState;
18503
18624
  RoomState["Connected"] = "connected";
18504
18625
  RoomState["Reconnecting"] = "reconnecting";
18505
18626
  })(RoomState || (RoomState = {}));
18506
- /**
18507
- * In LiveKit, a room is the logical grouping for a list of participants.
18508
- * Participants in a room can publish tracks, and subscribe to others' tracks.
18509
- *
18510
- * a Room fires [[RoomEvent | RoomEvents]].
18511
- *
18512
- * @noInheritDoc
18627
+ /**
18628
+ * In LiveKit, a room is the logical grouping for a list of participants.
18629
+ * Participants in a room can publish tracks, and subscribe to others' tracks.
18630
+ *
18631
+ * a Room fires [[RoomEvent | RoomEvents]].
18632
+ *
18633
+ * @noInheritDoc
18513
18634
  */
18514
18635
 
18515
18636
 
18516
18637
  class Room extends events.exports.EventEmitter {
18517
- /**
18518
- * Creates a new Room, the primary construct for a LiveKit session.
18519
- * @param options
18638
+ /**
18639
+ * Creates a new Room, the primary construct for a LiveKit session.
18640
+ * @param options
18520
18641
  */
18521
18642
  constructor(options) {
18522
18643
  var _this;
@@ -18526,9 +18647,9 @@ class Room extends events.exports.EventEmitter {
18526
18647
  super();
18527
18648
  _this = this;
18528
18649
  this.state = RoomState.Disconnected;
18529
- /**
18530
- * list of participants that are actively speaking. when this changes
18531
- * a [[RoomEvent.ActiveSpeakersChanged]] event is fired
18650
+ /**
18651
+ * list of participants that are actively speaking. when this changes
18652
+ * a [[RoomEvent.ActiveSpeakersChanged]] event is fired
18532
18653
  */
18533
18654
 
18534
18655
  this.activeSpeakers = []; // available after connected
@@ -18640,8 +18761,8 @@ class Room extends events.exports.EventEmitter {
18640
18761
  });
18641
18762
  });
18642
18763
  };
18643
- /**
18644
- * disconnects the room, emits [[RoomEvent.Disconnected]]
18764
+ /**
18765
+ * disconnects the room, emits [[RoomEvent.Disconnected]]
18645
18766
  */
18646
18767
 
18647
18768
 
@@ -18936,13 +19057,13 @@ class Room extends events.exports.EventEmitter {
18936
19057
  }
18937
19058
  }).on(EngineEvent.Restarting, this.handleRestarting).on(EngineEvent.Restarted, this.handleRestarted);
18938
19059
  }
18939
- /**
18940
- * getLocalDevices abstracts navigator.mediaDevices.enumerateDevices.
18941
- * In particular, it handles Chrome's unique behavior of creating `default`
18942
- * devices. When encountered, it'll be removed from the list of devices.
18943
- * The actual default device will be placed at top.
18944
- * @param kind
18945
- * @returns a list of available local devices
19060
+ /**
19061
+ * getLocalDevices abstracts navigator.mediaDevices.enumerateDevices.
19062
+ * In particular, it handles Chrome's unique behavior of creating `default`
19063
+ * devices. When encountered, it'll be removed from the list of devices.
19064
+ * The actual default device will be placed at top.
19065
+ * @param kind
19066
+ * @returns a list of available local devices
18946
19067
  */
18947
19068
 
18948
19069
 
@@ -18950,10 +19071,10 @@ class Room extends events.exports.EventEmitter {
18950
19071
  let requestPermissions = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : true;
18951
19072
  return DeviceManager.getInstance().getDevices(kind, requestPermissions);
18952
19073
  }
18953
- /**
18954
- * retrieves a participant by identity
18955
- * @param identity
18956
- * @returns
19074
+ /**
19075
+ * retrieves a participant by identity
19076
+ * @param identity
19077
+ * @returns
18957
19078
  */
18958
19079
 
18959
19080
 
@@ -18968,8 +19089,8 @@ class Room extends events.exports.EventEmitter {
18968
19089
  return this.localParticipant;
18969
19090
  }
18970
19091
  }
18971
- /**
18972
- * @internal for testing
19092
+ /**
19093
+ * @internal for testing
18973
19094
  */
18974
19095
 
18975
19096
 
@@ -19006,12 +19127,12 @@ class Room extends events.exports.EventEmitter {
19006
19127
  this.engine.client.sendSimulateScenario(req);
19007
19128
  }
19008
19129
  }
19009
- /**
19010
- * Browsers have different policies regarding audio playback. Most requiring
19011
- * some form of user interaction (click/tap/etc).
19012
- * In those cases, audio will be silent until a click/tap triggering one of the following
19013
- * - `startAudio`
19014
- * - `getUserMedia`
19130
+ /**
19131
+ * Browsers have different policies regarding audio playback. Most requiring
19132
+ * some form of user interaction (click/tap/etc).
19133
+ * In those cases, audio will be silent until a click/tap triggering one of the following
19134
+ * - `startAudio`
19135
+ * - `getUserMedia`
19015
19136
  */
19016
19137
 
19017
19138
 
@@ -19036,23 +19157,23 @@ class Room extends events.exports.EventEmitter {
19036
19157
  throw err;
19037
19158
  }
19038
19159
  }
19039
- /**
19040
- * Returns true if audio playback is enabled
19160
+ /**
19161
+ * Returns true if audio playback is enabled
19041
19162
  */
19042
19163
 
19043
19164
 
19044
19165
  get canPlaybackAudio() {
19045
19166
  return this.audioEnabled;
19046
19167
  }
19047
- /**
19048
- * Switches all active device used in this room to the given device.
19049
- *
19050
- * Note: setting AudioOutput is not supported on some browsers. See [setSinkId](https://developer.mozilla.org/en-US/docs/Web/API/HTMLMediaElement/setSinkId#browser_compatibility)
19051
- *
19052
- * @param kind use `videoinput` for camera track,
19053
- * `audioinput` for microphone track,
19054
- * `audiooutput` to set speaker for all incoming audio tracks
19055
- * @param deviceId
19168
+ /**
19169
+ * Switches all active device used in this room to the given device.
19170
+ *
19171
+ * Note: setting AudioOutput is not supported on some browsers. See [setSinkId](https://developer.mozilla.org/en-US/docs/Web/API/HTMLMediaElement/setSinkId#browser_compatibility)
19172
+ *
19173
+ * @param kind use `videoinput` for camera track,
19174
+ * `audioinput` for microphone track,
19175
+ * `audiooutput` to set speaker for all incoming audio tracks
19176
+ * @param deviceId
19056
19177
  */
19057
19178
 
19058
19179
 
@@ -19248,10 +19369,10 @@ class Room extends events.exports.EventEmitter {
19248
19369
  }
19249
19370
 
19250
19371
  const previousSdp = this.engine.subscriber.pc.localDescription;
19251
- /* 1. autosubscribe on, so subscribed tracks = all tracks - unsub tracks,
19252
- in this case, we send unsub tracks, so server add all tracks to this
19253
- subscribe pc and unsub special tracks from it.
19254
- 2. autosubscribe off, we send subscribed tracks.
19372
+ /* 1. autosubscribe on, so subscribed tracks = all tracks - unsub tracks,
19373
+ in this case, we send unsub tracks, so server add all tracks to this
19374
+ subscribe pc and unsub special tracks from it.
19375
+ 2. autosubscribe off, we send subscribed tracks.
19255
19376
  */
19256
19377
 
19257
19378
  const sendUnsub = ((_a = this.connOptions) === null || _a === void 0 ? void 0 : _a.autoSubscribe) || false;
@@ -19277,9 +19398,9 @@ class Room extends events.exports.EventEmitter {
19277
19398
  dataChannels: this.localParticipant.dataChannelsInfo()
19278
19399
  });
19279
19400
  }
19280
- /**
19281
- * After resuming, we'll need to notify the server of the current
19282
- * subscription settings.
19401
+ /**
19402
+ * After resuming, we'll need to notify the server of the current
19403
+ * subscription settings.
19283
19404
  */
19284
19405
 
19285
19406
 
@@ -19308,24 +19429,24 @@ class Room extends events.exports.EventEmitter {
19308
19429
 
19309
19430
  }
19310
19431
 
19311
- /**
19312
- * @deprecated Use room.connect() instead
19313
- *
19314
- * Connects to a LiveKit room, shorthand for `new Room()` and [[Room.connect]]
19315
- *
19316
- * ```typescript
19317
- * connect('wss://myhost.livekit.io', token, {
19318
- * // publish audio and video tracks on joining
19319
- * audio: true,
19320
- * video: true,
19321
- * captureDefaults: {
19322
- * facingMode: 'user',
19323
- * },
19324
- * })
19325
- * ```
19326
- * @param url URL to LiveKit server
19327
- * @param token AccessToken, a JWT token that includes authentication and room details
19328
- * @param options
19432
+ /**
19433
+ * @deprecated Use room.connect() instead
19434
+ *
19435
+ * Connects to a LiveKit room, shorthand for `new Room()` and [[Room.connect]]
19436
+ *
19437
+ * ```typescript
19438
+ * connect('wss://myhost.livekit.io', token, {
19439
+ * // publish audio and video tracks on joining
19440
+ * audio: true,
19441
+ * video: true,
19442
+ * captureDefaults: {
19443
+ * facingMode: 'user',
19444
+ * },
19445
+ * })
19446
+ * ```
19447
+ * @param url URL to LiveKit server
19448
+ * @param token AccessToken, a JWT token that includes authentication and room details
19449
+ * @param options
19329
19450
  */
19330
19451
 
19331
19452
  async function connect(url, token, options) {
@@ -19403,11 +19524,11 @@ async function connect(url, token, options) {
19403
19524
  return room;
19404
19525
  }
19405
19526
 
19406
- /**
19407
- * Creates a local video and audio track at the same time. When acquiring both
19408
- * audio and video tracks together, it'll display a single permission prompt to
19409
- * the user instead of two separate ones.
19410
- * @param options
19527
+ /**
19528
+ * Creates a local video and audio track at the same time. When acquiring both
19529
+ * audio and video tracks together, it'll display a single permission prompt to
19530
+ * the user instead of two separate ones.
19531
+ * @param options
19411
19532
  */
19412
19533
 
19413
19534
  async function createLocalTracks(options) {
@@ -19443,9 +19564,9 @@ async function createLocalTracks(options) {
19443
19564
  return track;
19444
19565
  });
19445
19566
  }
19446
- /**
19447
- * Creates a [[LocalVideoTrack]] with getUserMedia()
19448
- * @param options
19567
+ /**
19568
+ * Creates a [[LocalVideoTrack]] with getUserMedia()
19569
+ * @param options
19449
19570
  */
19450
19571
 
19451
19572
  async function createLocalVideoTrack(options) {
@@ -19462,10 +19583,10 @@ async function createLocalAudioTrack(options) {
19462
19583
  });
19463
19584
  return tracks[0];
19464
19585
  }
19465
- /**
19466
- * Creates a screen capture tracks with getDisplayMedia().
19467
- * A LocalVideoTrack is always created and returned.
19468
- * If { audio: true }, and the browser supports audio capture, a LocalAudioTrack is also created.
19586
+ /**
19587
+ * Creates a screen capture tracks with getDisplayMedia().
19588
+ * A LocalVideoTrack is always created and returned.
19589
+ * If { audio: true }, and the browser supports audio capture, a LocalAudioTrack is also created.
19469
19590
  */
19470
19591
 
19471
19592
  async function createLocalScreenTracks(options) {