Add device picker for webcams and microphones to the settings modal
This commit is contained in:
parent
f4568b9087
commit
55b17f62c4
|
@ -277,11 +277,12 @@ const app = Vue.createApp({
|
|||
}
|
||||
},
|
||||
watch: {
|
||||
"webcam.videoScale": () => {
|
||||
"webcam.videoScale": function() {
|
||||
document.querySelectorAll(".video-feeds > .feed").forEach(node => {
|
||||
node.style.width = null;
|
||||
node.style.height = null;
|
||||
});
|
||||
localStorage.videoScale = this.webcam.videoScale;
|
||||
},
|
||||
fontSizeClass() {
|
||||
// Store the setting persistently.
|
||||
|
@ -357,6 +358,10 @@ const app = Vue.createApp({
|
|||
this.fontSizeClass = localStorage.fontSizeClass;
|
||||
}
|
||||
|
||||
if (localStorage.videoScale != undefined) {
|
||||
this.webcam.videoScale = localStorage.videoScale;
|
||||
}
|
||||
|
||||
// Webcam mutality preferences from last broadcast.
|
||||
if (localStorage.videoMutual === "true") {
|
||||
this.webcam.mutual = true;
|
||||
|
@ -1127,7 +1132,9 @@ const app = Vue.createApp({
|
|||
},
|
||||
|
||||
// Start broadcasting my webcam.
|
||||
startVideo(force) {
|
||||
// - force=true to skip the NSFW modal prompt (this param is passed by the button in that modal)
|
||||
// - changeCamera=true to re-negotiate WebRTC connections with a new camera device (invoked by the Settings modal)
|
||||
startVideo({force=false, changeCamera=false}) {
|
||||
if (this.webcam.busy) return;
|
||||
|
||||
// If we are running in PermitNSFW mode, show the user the modal.
|
||||
|
@ -1136,11 +1143,24 @@ const app = Vue.createApp({
|
|||
return;
|
||||
}
|
||||
|
||||
this.webcam.busy = true;
|
||||
navigator.mediaDevices.getUserMedia({
|
||||
let mediaParams = {
|
||||
audio: true,
|
||||
video: true,
|
||||
}).then(stream => {
|
||||
video: {
|
||||
width: { max: 1280 },
|
||||
height: { max: 720 },
|
||||
},
|
||||
};
|
||||
|
||||
if (changeCamera) {
|
||||
// Name the specific devices chosen by the user.
|
||||
mediaParams.video.deviceId = { exact: this.webcam.videoDeviceID };
|
||||
mediaParams.audio = {
|
||||
deviceId: { exact: this.webcam.audioDeviceID },
|
||||
};
|
||||
}
|
||||
|
||||
this.webcam.busy = true;
|
||||
navigator.mediaDevices.getUserMedia(mediaParams).then(stream => {
|
||||
this.webcam.active = true;
|
||||
this.webcam.elem.srcObject = stream;
|
||||
this.webcam.stream = stream;
|
||||
|
@ -1159,6 +1179,11 @@ const app = Vue.createApp({
|
|||
|
||||
// Collect video and audio devices to let the user change them in their settings.
|
||||
this.getDevices();
|
||||
|
||||
// If we have changed devices, reconnect everybody's WebRTC channels for your existing watchers.
|
||||
if (changeCamera) {
|
||||
this.updateWebRTCStreams();
|
||||
}
|
||||
}).catch(err => {
|
||||
this.ChatClient(`Webcam error: ${err}`);
|
||||
}).finally(() => {
|
||||
|
@ -1177,11 +1202,13 @@ const app = Vue.createApp({
|
|||
this.webcam.audioDevices = [];
|
||||
devices.forEach(device => {
|
||||
if (device.kind === 'videoinput') {
|
||||
// console.log(`Video device ${device.deviceId} ${device.label}`);
|
||||
this.webcam.videoDevices.push({
|
||||
id: device.deviceId,
|
||||
label: device.label,
|
||||
});
|
||||
} else if (device.kind === 'audioinput') {
|
||||
// console.log(`Audio device ${device.deviceId} ${device.label}`);
|
||||
this.webcam.audioDevices.push({
|
||||
id: device.deviceId,
|
||||
label: device.label,
|
||||
|
@ -1193,6 +1220,36 @@ const app = Vue.createApp({
|
|||
})
|
||||
},
|
||||
|
||||
// Replace your video/audio streams for your watchers (on camera changes)
|
||||
updateWebRTCStreams() {
|
||||
console.log("Re-negotiating video and audio channels to your watchers.");
|
||||
for (let username of Object.keys(this.WebRTC.pc)) {
|
||||
let pc = this.WebRTC.pc[username];
|
||||
if (pc.answerer != undefined) {
|
||||
let oldTracks = pc.answerer.getSenders();
|
||||
let newTracks = this.webcam.stream.getTracks();
|
||||
|
||||
// Remove and replace the tracks.
|
||||
for (let old of oldTracks) {
|
||||
if (old.track.kind === 'audio') {
|
||||
for (let replace of newTracks) {
|
||||
if (replace.kind === 'audio') {
|
||||
old.replaceTrack(replace);
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (old.track.kind === 'video') {
|
||||
for (let replace of newTracks) {
|
||||
if (replace.kind === 'video') {
|
||||
old.replaceTrack(replace);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
// Begin connecting to someone else's webcam.
|
||||
openVideo(user, force) {
|
||||
if (user.username === this.username) {
|
||||
|
|
|
@ -114,13 +114,12 @@
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Under construction
|
||||
<div class="columns is-mobile" v-if="webcam.videoDevices.length > 0 || webcam.audioDevices.length > 0">
|
||||
|
||||
<div class="column">
|
||||
<label class="label">Video source</label>
|
||||
<div class="select is-fullwidth">
|
||||
<select v-model="webcam.videoDeviceID">
|
||||
<select v-model="webcam.videoDeviceID" @change="startVideo({changeCamera: true, force: true})">
|
||||
<option v-for="(d, i) in webcam.videoDevices"
|
||||
:value="d.id">
|
||||
[[ d.label || `Camera ${i}` ]]
|
||||
|
@ -132,7 +131,7 @@
|
|||
<div class="column">
|
||||
<label class="label">Audio source</label>
|
||||
<div class="select is-fullwidth">
|
||||
<select v-model="webcam.audioDeviceID">
|
||||
<select v-model="webcam.audioDeviceID" @change="startVideo({changeCamera: true, force: true})">
|
||||
<option v-for="(d, i) in webcam.audioDevices"
|
||||
:value="d.id">
|
||||
[[ d.label || `Microphone ${i}` ]]
|
||||
|
@ -141,7 +140,6 @@
|
|||
</div>
|
||||
</div>
|
||||
</div>
|
||||
-->
|
||||
|
||||
<h3 class="subtitle mb-2">Sounds</h3>
|
||||
|
||||
|
@ -360,7 +358,7 @@
|
|||
<div class="control has-text-centered">
|
||||
<button type="button"
|
||||
class="button is-link mr-4"
|
||||
@click="startVideo(true); nsfwModalCast.visible=false">Start webcam</button>
|
||||
@click="startVideo({force: true}); nsfwModalCast.visible=false">Start webcam</button>
|
||||
<button type="button"
|
||||
class="button"
|
||||
@click="nsfwModalCast.visible=false">Cancel</button>
|
||||
|
@ -442,7 +440,7 @@
|
|||
<button type="button"
|
||||
v-else
|
||||
class="button is-small is-success px-1"
|
||||
@click="startVideo()"
|
||||
@click="startVideo({})"
|
||||
:disabled="webcam.busy">
|
||||
<i class="fa fa-video mr-2"></i>
|
||||
Share webcam
|
||||
|
|
Loading…
Reference in New Issue
Block a user