@@ -1006,7 +1006,7 @@ describe('setInitialMuteStates', () => {
10061006 beforeEach ( ( ) => {
10071007 session = new MockSession ( ) as any ;
10081008 audioSender = { track : { kind : 'audio' , enabled : true } } ;
1009- videoSender = { track : { kind : 'video' , enabled : true } } ;
1009+ videoSender = { track : { kind : 'video' , enabled : true , id : 'camera-track-1' } } ;
10101010 } ) ;
10111011
10121012 it ( 'should mute video' , async ( ) => {
@@ -1219,7 +1219,7 @@ describe('setVideoMute', () => {
12191219
12201220 await handler . setVideoMute ( session , { conversationId : session . conversationId , mute : false } ) ;
12211221
1222- expect ( mockSdk . logger . debug ) . toHaveBeenCalledWith ( expect . stringContaining ( 'Cannot unmute, a video track already exists' ) , expect . any ( Object ) , undefined ) ;
1222+ expect ( mockSdk . logger . debug ) . toHaveBeenCalledWith ( expect . stringContaining ( 'Cannot unmute, a camera video track already exists' ) , expect . any ( Object ) , undefined ) ;
12231223 } ) ;
12241224
12251225 it ( 'mute: should mute video track when there is no screen track and remove track from outboundStream' , async ( ) => {
@@ -1306,7 +1306,7 @@ describe('setVideoMute', () => {
13061306 const stream = new MockStream ( true ) ;
13071307 const spy = jest . spyOn ( mockSdk . media , 'startMedia' ) . mockResolvedValue ( stream as any ) ;
13081308 jest . spyOn ( mockSessionManager , 'getAllActiveSessions' ) . mockReturnValue ( [ { id : session . id } as IExtendedMediaSession ] ) ;
1309- jest . spyOn ( handler , 'addMediaToSession ' ) . mockResolvedValue ( ) ;
1309+ jest . spyOn ( handler , 'addReplaceTrackToSession ' ) . mockResolvedValue ( ) ;
13101310
13111311 session . _outboundStream = {
13121312 addTrack : jest . fn ( ) ,
@@ -1327,7 +1327,7 @@ describe('setVideoMute', () => {
13271327 const stream = new MockStream ( true ) ;
13281328 const spy = jest . spyOn ( mockSdk . media , 'startMedia' ) . mockResolvedValue ( stream as any ) ;
13291329 jest . spyOn ( mockSessionManager , 'getAllActiveSessions' ) . mockReturnValue ( [ { id : session . id } as IExtendedMediaSession ] ) ;
1330- jest . spyOn ( handler , 'addMediaToSession ' ) . mockResolvedValue ( ) ;
1330+ jest . spyOn ( handler , 'addReplaceTrackToSession ' ) . mockResolvedValue ( ) ;
13311331
13321332 session . _outboundStream = {
13331333 addTrack : jest . fn ( ) ,
@@ -1347,7 +1347,7 @@ describe('setVideoMute', () => {
13471347 const unmuteDeviceId = 'device-id' ;
13481348 const stream = new MockStream ( true ) ;
13491349 const spy = jest . spyOn ( mockSdk . media , 'startMedia' ) . mockResolvedValue ( stream as any ) ;
1350- jest . spyOn ( handler , 'addMediaToSession ' ) . mockResolvedValue ( ) ;
1350+ jest . spyOn ( handler , 'addReplaceTrackToSession ' ) . mockResolvedValue ( ) ;
13511351
13521352 session . _outboundStream = {
13531353 addTrack : jest . fn ( ) ,
@@ -1361,6 +1361,51 @@ describe('setVideoMute', () => {
13611361 expect ( session . unmute ) . not . toHaveBeenCalled ( ) ;
13621362 expect ( stream . getVideoTracks ( ) [ 0 ] . stop ) . toHaveBeenCalled ( ) ;
13631363 } ) ;
1364+
1365+ it ( 'mute: should find camera track when screen share exists' , async ( ) => {
1366+ const screenTrack = new MockTrack ( 'video' ) ;
1367+ screenTrack . id = 'screen-track-id' ;
1368+ const cameraTrack = new MockTrack ( 'video' ) ;
1369+ cameraTrack . id = 'camera-track-id' ;
1370+
1371+ session . _screenShareStream = {
1372+ getVideoTracks : jest . fn ( ) . mockReturnValue ( [ screenTrack ] )
1373+ } as any ;
1374+
1375+ session . _outboundStream = {
1376+ removeTrack : jest . fn ( ) ,
1377+ getVideoTracks : jest . fn ( ) . mockReturnValue ( [ cameraTrack ] )
1378+ } as any ;
1379+
1380+ jest . spyOn ( handler , 'getSendersByTrackType' ) . mockReturnValue ( [
1381+ { track : cameraTrack }
1382+ ] as any ) ;
1383+
1384+ await handler . setVideoMute ( session , { conversationId : session . conversationId , mute : true } ) ;
1385+
1386+ expect ( cameraTrack . stop ) . toHaveBeenCalled ( ) ;
1387+ expect ( session . mute ) . toHaveBeenCalledWith ( userId , 'video' ) ;
1388+ } ) ;
1389+
1390+ it ( 'unmute: should check for existing camera track when screen share exists' , async ( ) => {
1391+ const screenTrack = new MockTrack ( 'video' ) ;
1392+ screenTrack . id = 'screen-track-id' ;
1393+ const cameraTrack = new MockTrack ( 'video' ) ;
1394+ cameraTrack . id = 'camera-track-id' ;
1395+
1396+ session . _screenShareStream = {
1397+ getVideoTracks : jest . fn ( ) . mockReturnValue ( [ screenTrack ] )
1398+ } as any ;
1399+
1400+ session . _outboundStream = {
1401+ addTrack : jest . fn ( ) ,
1402+ getVideoTracks : jest . fn ( ) . mockReturnValue ( [ cameraTrack ] )
1403+ } as any ;
1404+
1405+ await handler . setVideoMute ( session , { conversationId : session . conversationId , mute : false } ) ;
1406+
1407+ expect ( mockSdk . logger . debug ) . toHaveBeenCalledWith ( expect . stringContaining ( 'Cannot unmute, a camera video track already exists' ) , expect . any ( Object ) , undefined ) ;
1408+ } ) ;
13641409} ) ;
13651410
13661411describe ( 'setAudioMute' , ( ) => {
@@ -1483,33 +1528,29 @@ describe('getSendersByTrackType', () => {
14831528
14841529describe ( 'startScreenShare' , ( ) => {
14851530 let displayMediaSpy : jest . SpyInstance < Promise < MediaStream > > ;
1486- let videoMuteSpy : jest . SpyInstance < Promise < void > > ;
1487- let addReplaceTrackToSession : jest . SpyInstance < Promise < any > > ;
1531+ let addMediaToSessionSpy : jest . SpyInstance < Promise < void > > ;
14881532 let session : VideoMediaSession ;
14891533
14901534 beforeEach ( ( ) => {
14911535 displayMediaSpy = jest . spyOn ( mockSdk . media , 'startDisplayMedia' ) . mockResolvedValue ( new MockStream ( { video : true } ) as any ) ;
1492- videoMuteSpy = jest . spyOn ( handler , 'setVideoMute' ) . mockResolvedValue ( ) ;
1493- addReplaceTrackToSession = jest . spyOn ( handler , 'addReplaceTrackToSession' ) . mockResolvedValue ( ) ;
1536+ addMediaToSessionSpy = jest . spyOn ( handler , 'addMediaToSession' ) . mockResolvedValue ( ) ;
14941537 session = new MockSession ( ) as any ;
14951538 } ) ;
14961539
1497- it ( 'should start media and mute video if it is not already muted ' , async ( ) => {
1540+ it ( 'should start media and add screen share track without replacing existing video ' , async ( ) => {
14981541 await handler . startScreenShare ( session ) ;
14991542
15001543 expect ( displayMediaSpy ) . toHaveBeenCalled ( ) ;
1501- expect ( videoMuteSpy ) . toHaveBeenCalled ( ) ;
1502- expect ( addReplaceTrackToSession ) . toHaveBeenCalled ( ) ;
1544+ expect ( addMediaToSessionSpy ) . toHaveBeenCalled ( ) ;
15031545 expect ( mockSessionManager . webrtcSessions . notifyScreenShareStart ) . toHaveBeenCalled ( ) ;
15041546 } ) ;
15051547
1506- it ( 'should not mute video if already muted ' , async ( ) => {
1548+ it ( 'should add screen share track regardless of video mute state ' , async ( ) => {
15071549 session . videoMuted = true ;
15081550 await handler . startScreenShare ( session ) ;
15091551
15101552 expect ( displayMediaSpy ) . toHaveBeenCalled ( ) ;
1511- expect ( videoMuteSpy ) . not . toHaveBeenCalled ( ) ;
1512- expect ( addReplaceTrackToSession ) . toHaveBeenCalled ( ) ;
1553+ expect ( addMediaToSessionSpy ) . toHaveBeenCalled ( ) ;
15131554 expect ( mockSessionManager . webrtcSessions . notifyScreenShareStart ) . toHaveBeenCalled ( ) ;
15141555 } ) ;
15151556
@@ -1534,12 +1575,10 @@ describe('startScreenShare', () => {
15341575} ) ;
15351576
15361577describe ( 'stopScreenShare' , ( ) => {
1537- let videoMuteSpy ;
15381578 let removeMediaSpy ;
15391579 let session ;
15401580
15411581 beforeEach ( ( ) => {
1542- videoMuteSpy = jest . spyOn ( handler , 'setVideoMute' ) . mockResolvedValue ( ) ;
15431582 removeMediaSpy = jest . spyOn ( handler , 'removeMediaFromSession' ) . mockResolvedValue ( ) ;
15441583 session = new MockSession ( ) ;
15451584 } ) ;
@@ -1549,49 +1588,34 @@ describe('stopScreenShare', () => {
15491588
15501589 await handler . stopScreenShare ( session ) ;
15511590
1552- expect ( videoMuteSpy ) . not . toHaveBeenCalled ( ) ;
15531591 expect ( removeMediaSpy ) . not . toHaveBeenCalled ( ) ;
15541592 expect ( mockSessionManager . webrtcSessions . notifyScreenShareStop ) . not . toHaveBeenCalled ( ) ;
15551593 } ) ;
15561594
1557- it ( 'should stop screen share tracks and unmute video if resurrectVideoOnScreenShareEnd' , async ( ) => {
1558- session . _resurrectVideoOnScreenShareEnd = true ;
1595+ it ( 'should remove screen share track and stop it' , async ( ) => {
15591596 session . _screenShareStream = new MockStream ( { video : true } ) ;
1597+ const screenTrack = session . _screenShareStream . _tracks [ 0 ] ;
15601598
1561- await handler . stopScreenShare ( session ) ;
1562-
1563- expect ( videoMuteSpy ) . toHaveBeenCalled ( ) ;
1564- expect ( session . _screenShareStream . _tracks [ 0 ] . stop ) . toHaveBeenCalled ( ) ;
1565- expect ( mockSessionManager . webrtcSessions . notifyScreenShareStop ) . toHaveBeenCalled ( ) ;
1566- } ) ;
1567-
1568- it ( 'should not unmute video if not resurrect' , async ( ) => {
1569- session . resurrectVideoOnScreenShareEnd = false ;
1570- session . _screenShareStream = new MockStream ( { video : true } ) ;
1571-
1572- const replaceSpy = jest . fn ( ) ;
1573- jest . spyOn ( session . pc , 'getSenders' ) . mockReturnValue ( [ { track : session . _screenShareStream . _tracks [ 0 ] , replaceTrack : replaceSpy } ] ) ;
1599+ jest . spyOn ( session . pc , 'getSenders' ) . mockReturnValue ( [ { track : screenTrack } ] ) ;
15741600
15751601 await handler . stopScreenShare ( session ) ;
15761602
1577- expect ( videoMuteSpy ) . not . toHaveBeenCalled ( ) ;
1578- expect ( session . _screenShareStream . _tracks [ 0 ] . stop ) . toHaveBeenCalled ( ) ;
1579- expect ( replaceSpy ) . toHaveBeenCalled ( ) ;
1603+ expect ( removeMediaSpy ) . toHaveBeenCalled ( ) ;
1604+ expect ( screenTrack . stop ) . toHaveBeenCalled ( ) ;
15801605 expect ( mockSessionManager . webrtcSessions . notifyScreenShareStop ) . toHaveBeenCalled ( ) ;
15811606 } ) ;
15821607
1583- it ( 'should toggle off of screen share AND keep video unmuted if something goes wrong when fetching device media' , async ( ) => {
1584- videoMuteSpy = jest . spyOn ( handler , 'setVideoMute' ) . mockRejectedValueOnce ( { message : 'Could not start video source' } ) . mockResolvedValueOnce ( ) ;
1585- session . _resurrectVideoOnScreenShareEnd = true ;
1608+ it ( 'should stop screen share track even if no sender found' , async ( ) => {
15861609 session . _screenShareStream = new MockStream ( { video : true } ) ;
1610+ const screenTrack = session . _screenShareStream . _tracks [ 0 ] ;
1611+
1612+ jest . spyOn ( session . pc , 'getSenders' ) . mockReturnValue ( [ ] ) ;
15871613
15881614 await handler . stopScreenShare ( session ) ;
15891615
1590- expect ( videoMuteSpy ) . toHaveBeenNthCalledWith ( 1 , session , { conversationId : session . conversationId , mute : false } , true ) ;
1591- expect ( videoMuteSpy ) . toHaveBeenNthCalledWith ( 2 , session , { conversationId : session . conversationId , mute : true } , false ) ;
1592- expect ( session . _screenShareStream . _tracks [ 0 ] . stop ) . toHaveBeenCalled ( ) ;
1616+ expect ( removeMediaSpy ) . not . toHaveBeenCalled ( ) ;
1617+ expect ( screenTrack . stop ) . toHaveBeenCalled ( ) ;
15931618 expect ( mockSessionManager . webrtcSessions . notifyScreenShareStop ) . toHaveBeenCalled ( ) ;
1594- jest . resetAllMocks ( ) ;
15951619 } ) ;
15961620} ) ;
15971621
0 commit comments