|
@@ -129,49 +129,46 @@ function _electLastVisibleRemoteVideo(tracks) {
|
129
|
129
|
* @returns {(string|undefined)}
|
130
|
130
|
*/
|
131
|
131
|
function _electParticipantInLargeVideo(state) {
|
132
|
|
- // 1. If a participant is pinned, they will be shown in the LargeVideo (
|
133
|
|
- // regardless of whether they are local or remote).
|
|
132
|
+ // 1. If a participant is pinned, they will be shown in the LargeVideo
|
|
133
|
+ // (regardless of whether they are local or remote).
|
134
|
134
|
const participants = state['features/base/participants'];
|
135
|
135
|
let participant = participants.find(p => p.pinned);
|
136
|
|
- let id = participant && participant.id;
|
137
|
|
-
|
138
|
|
- if (!id) {
|
139
|
|
- // 2. No participant is pinned so get the dominant speaker. But the
|
140
|
|
- // local participant won't be displayed in LargeVideo even if she is
|
141
|
|
- // the dominant speaker.
|
142
|
|
- participant = participants.find(p => p.dominantSpeaker && !p.local);
|
143
|
|
- id = participant && participant.id;
|
144
|
|
-
|
145
|
|
- if (!id) {
|
146
|
|
- // 3. There is no dominant speaker so select the remote participant
|
147
|
|
- // who last had visible video.
|
148
|
|
- const tracks = state['features/base/tracks'];
|
149
|
|
- const videoTrack = _electLastVisibleRemoteVideo(tracks);
|
150
|
|
-
|
151
|
|
- id = videoTrack && videoTrack.participantId;
|
152
|
|
-
|
153
|
|
- if (!id) {
|
154
|
|
- // 4. It's possible there is no participant with visible video.
|
155
|
|
- // This can happen for a number of reasons:
|
156
|
|
- // - there is only one participant (i.e. the local user),
|
157
|
|
- // - other participants joined with video muted.
|
158
|
|
- // As a last resort, pick the last participant who joined the
|
159
|
|
- // conference (regardless of whether they are local or
|
160
|
|
- // remote).
|
161
|
|
- //
|
162
|
|
- // HOWEVER: We don't want to show poltergeist or other bot type participants on stage
|
163
|
|
- // automatically, because it's misleading (users may think they are already
|
164
|
|
- // joined and maybe speaking).
|
165
|
|
- for (let i = participants.length; i > 0 && !participant; i--) {
|
166
|
|
- const p = participants[i - 1];
|
167
|
|
-
|
168
|
|
- !p.botType && (participant = p);
|
169
|
|
- }
|
170
|
|
-
|
171
|
|
- id = participant && participant.id;
|
172
|
|
- }
|
173
|
|
- }
|
|
136
|
+
|
|
137
|
+ if (participant) {
|
|
138
|
+ return participant.id;
|
|
139
|
+ }
|
|
140
|
+
|
|
141
|
+ // 2. Next, pick the most recent remote screenshare that was added to the conference.
|
|
142
|
+ const remoteScreenShares = state['features/video-layout'].remoteScreenShares;
|
|
143
|
+
|
|
144
|
+ if (remoteScreenShares?.length) {
|
|
145
|
+ return remoteScreenShares[remoteScreenShares.length - 1];
|
|
146
|
+ }
|
|
147
|
+
|
|
148
|
+ // 3. Next, pick the dominant speaker (other than self).
|
|
149
|
+ participant = participants.find(p => p.dominantSpeaker && !p.local);
|
|
150
|
+ if (participant) {
|
|
151
|
+ return participant.id;
|
|
152
|
+ }
|
|
153
|
+
|
|
154
|
+ // 4. Next, pick the most recent participant with video.
|
|
155
|
+ const tracks = state['features/base/tracks'];
|
|
156
|
+ const videoTrack = _electLastVisibleRemoteVideo(tracks);
|
|
157
|
+
|
|
158
|
+ if (videoTrack) {
|
|
159
|
+ return videoTrack.participantId;
|
|
160
|
+ }
|
|
161
|
+
|
|
162
|
+ // 5. As a last resort, select the participant that joined last (other than poltergist or other bot type
|
|
163
|
+ // participants).
|
|
164
|
+ for (let i = participants.length; i > 0 && !participant; i--) {
|
|
165
|
+ const p = participants[i - 1];
|
|
166
|
+
|
|
167
|
+ !p.botType && (participant = p);
|
|
168
|
+ }
|
|
169
|
+ if (participant) {
|
|
170
|
+ return participant.id;
|
174
|
171
|
}
|
175
|
172
|
|
176
|
|
- return id;
|
|
173
|
+ return participants.find(p => p.local)?.id;
|
177
|
174
|
}
|