From 529b2fbb21c90087f1c47358b6150e5133f1d36d Mon Sep 17 00:00:00 2001 From: voluntas <nakai@shiguredo.jp> Date: Sat, 11 Jan 2025 18:01:03 +0900 Subject: [PATCH] lineWidth 100 --- biome.jsonc | 1 + check_stereo/main.ts | 127 ++++++++++---------------------- check_stereo_multi/main.ts | 147 +++++++++++++------------------------ messaging/main.ts | 44 ++++------- package.json | 2 +- recvonly/main.ts | 12 +-- replace_track/main.ts | 41 +++-------- sendonly/main.ts | 15 +--- sendrecv/main.ts | 15 +--- simulcast/main.ts | 83 ++++++--------------- spotlight_sendrecv/main.ts | 20 ++--- src/misc.ts | 5 +- tests/sendrecv.test.ts | 44 +++-------- 13 files changed, 167 insertions(+), 389 deletions(-) diff --git a/biome.jsonc b/biome.jsonc index 701180b..3551721 100644 --- a/biome.jsonc +++ b/biome.jsonc @@ -28,6 +28,7 @@ "javascript": { "formatter": { "enabled": true, + "lineWidth": 100, "indentStyle": "space" } } diff --git a/check_stereo/main.ts b/check_stereo/main.ts index b771e35..d26807a 100644 --- a/check_stereo/main.ts +++ b/check_stereo/main.ts @@ -28,50 +28,38 @@ document.addEventListener("DOMContentLoaded", async () => { // デバイスの変更を監視 navigator.mediaDevices.addEventListener("devicechange", updateDeviceLists); - document - .querySelector("#sendonly-connect") - ?.addEventListener("click", async () => { - const audioInputSelect = document.querySelector<HTMLSelectElement>( - "#sendonly-audio-input", - ); - const selectedAudioDeviceId = audioInputSelect?.value; - const stream = await navigator.mediaDevices.getUserMedia({ - video: false, - audio: { - deviceId: selectedAudioDeviceId - ? { exact: selectedAudioDeviceId } - : undefined, - echoCancellation: false, - noiseSuppression: false, - autoGainControl: false, - channelCount: 2, - sampleRate: 48000, - sampleSize: 16, - }, - }); - await sendonly.connect(stream); + document.querySelector("#sendonly-connect")?.addEventListener("click", async () => { + const audioInputSelect = document.querySelector<HTMLSelectElement>("#sendonly-audio-input"); + const selectedAudioDeviceId = audioInputSelect?.value; + const stream = await navigator.mediaDevices.getUserMedia({ + video: false, + audio: { + deviceId: selectedAudioDeviceId ? { exact: selectedAudioDeviceId } : undefined, + echoCancellation: false, + noiseSuppression: false, + autoGainControl: false, + channelCount: 2, + sampleRate: 48000, + sampleSize: 16, + }, }); + await sendonly.connect(stream); + }); - document - .querySelector("#recvonly-connect") - ?.addEventListener("click", async () => { - await recvonly.connect(); - }); + document.querySelector("#recvonly-connect")?.addEventListener("click", async () => { + await recvonly.connect(); + }); }); // デバイスリストを更新する関数 async function updateDeviceLists() { const devices = await navigator.mediaDevices.enumerateDevices(); - const audioInputSelect = document.querySelector<HTMLSelectElement>( - "#sendonly-audio-input", - ); + const audioInputSelect = document.querySelector<HTMLSelectElement>("#sendonly-audio-input"); if (audioInputSelect) { audioInputSelect.innerHTML = ""; - const audioInputDevices = devices.filter( - (device) => device.kind === "audioinput", - ); + const audioInputDevices = devices.filter((device) => device.kind === "audioinput"); for (const device of audioInputDevices) { const option = document.createElement("option"); option.value = device.deviceId; @@ -138,9 +126,7 @@ class SendonlyClient { if (!this.connection.pc) { return undefined; } - const sender = this.connection.pc - .getSenders() - .find((sender) => sender.track?.kind === "audio"); + const sender = this.connection.pc.getSenders().find((sender) => sender.track?.kind === "audio"); if (!sender) { return undefined; } @@ -148,8 +134,7 @@ class SendonlyClient { } private initializeCanvas() { - this.canvas = - document.querySelector<HTMLCanvasElement>("#sendonly-waveform"); + this.canvas = document.querySelector<HTMLCanvasElement>("#sendonly-waveform"); if (this.canvas) { this.canvasCtx = this.canvas.getContext("2d"); } @@ -199,8 +184,7 @@ class SendonlyClient { } // sendonly-stereo 要素に結果を反映 - const sendonlyStereoElement = - document.querySelector<HTMLDivElement>("#sendonly-stereo"); + const sendonlyStereoElement = document.querySelector<HTMLDivElement>("#sendonly-stereo"); if (sendonlyStereoElement) { sendonlyStereoElement.textContent = result; } @@ -224,11 +208,7 @@ class SendonlyClient { this.canvasCtx.fillStyle = "rgb(240, 240, 240)"; this.canvasCtx.fillRect(0, 0, width, height); - const drawChannel = ( - dataArray: Float32Array, - color: string, - offset: number, - ) => { + const drawChannel = (dataArray: Float32Array, color: string, offset: number) => { if (!this.canvasCtx) return; this.canvasCtx.lineWidth = 3; @@ -270,10 +250,7 @@ class SendonlyClient { this.canvasCtx.fillText(isMonaural ? "Monaural" : "Stereo", 10, 30); } - private isMonaural( - dataArrayL: Float32Array, - dataArrayR: Float32Array, - ): boolean { + private isMonaural(dataArrayL: Float32Array, dataArrayR: Float32Array): boolean { const threshold = 0.001; for (let i = 0; i < dataArrayL.length; i++) { if (Math.abs(dataArrayL[i] - dataArrayR[i]) > threshold) { @@ -289,9 +266,7 @@ class SendonlyClient { event.event_type === "connection.created" && this.connection.connectionId === event.connection_id ) { - const connectionIdElement = document.querySelector<HTMLDivElement>( - "#sendonly-connection-id", - ); + const connectionIdElement = document.querySelector<HTMLDivElement>("#sendonly-connection-id"); if (connectionIdElement) { connectionIdElement.textContent = event.connection_id; } @@ -301,13 +276,10 @@ class SendonlyClient { private startChannelCheck() { this.channelCheckInterval = window.setInterval(async () => { const channels = await this.getChannels(); - const channelElement = - document.querySelector<HTMLDivElement>("#sendonly-channels"); + const channelElement = document.querySelector<HTMLDivElement>("#sendonly-channels"); if (channelElement) { channelElement.textContent = - channels !== undefined - ? `getParameters codecs channels: ${channels}` - : "undefined"; + channels !== undefined ? `getParameters codecs channels: ${channels}` : "undefined"; } }, 1000); // 1秒ごとにチェック } @@ -335,11 +307,7 @@ class RecvonlyClient { this.secretKey = secretKey; this.sora = Sora.connection(signalingUrl, this.debug); - this.connection = this.sora.recvonly( - this.channelId, - undefined, - this.options, - ); + this.connection = this.sora.recvonly(this.channelId, undefined, this.options); this.connection.on("notify", this.onnotify.bind(this)); this.connection.on("track", this.ontrack.bind(this)); @@ -350,19 +318,15 @@ class RecvonlyClient { const jwt = await generateJwt(this.channelId, this.secretKey); this.connection.metadata = { access_token: jwt }; - const forceStereoOutputElement = - document.querySelector<HTMLInputElement>("#forceStereoOutput"); - const forceStereoOutput = forceStereoOutputElement - ? forceStereoOutputElement.checked - : false; + const forceStereoOutputElement = document.querySelector<HTMLInputElement>("#forceStereoOutput"); + const forceStereoOutput = forceStereoOutputElement ? forceStereoOutputElement.checked : false; this.connection.options.forceStereoOutput = forceStereoOutput; await this.connection.connect(); } private initializeCanvas() { - this.canvas = - document.querySelector<HTMLCanvasElement>("#recvonly-waveform"); + this.canvas = document.querySelector<HTMLCanvasElement>("#recvonly-waveform"); if (this.canvas) { this.canvasCtx = this.canvas.getContext("2d"); } @@ -412,8 +376,7 @@ class RecvonlyClient { } // 既存のコード - const recvonlyStereoElement = - document.querySelector<HTMLDivElement>("#recvonly-stereo"); + const recvonlyStereoElement = document.querySelector<HTMLDivElement>("#recvonly-stereo"); if (recvonlyStereoElement) { recvonlyStereoElement.textContent = result; } @@ -437,11 +400,7 @@ class RecvonlyClient { this.canvasCtx.fillStyle = "rgb(240, 240, 240)"; this.canvasCtx.fillRect(0, 0, width, height); - const drawChannel = ( - dataArray: Float32Array, - color: string, - offset: number, - ) => { + const drawChannel = (dataArray: Float32Array, color: string, offset: number) => { if (!this.canvasCtx) return; this.canvasCtx.lineWidth = 3; @@ -478,10 +437,7 @@ class RecvonlyClient { this.canvasCtx.fillText(isMonaural ? "Monaural" : "Stereo", 10, 30); } - private isMonaural( - dataArrayL: Float32Array, - dataArrayR: Float32Array, - ): boolean { + private isMonaural(dataArrayL: Float32Array, dataArrayR: Float32Array): boolean { const threshold = 0.001; for (let i = 0; i < dataArrayL.length; i++) { if (Math.abs(dataArrayL[i] - dataArrayR[i]) > threshold) { @@ -497,9 +453,7 @@ class RecvonlyClient { event.event_type === "connection.created" && this.connection.connectionId === event.connection_id ) { - const connectionIdElement = document.querySelector<HTMLDivElement>( - "#recvonly-connection-id", - ); + const connectionIdElement = document.querySelector<HTMLDivElement>("#recvonly-connection-id"); if (connectionIdElement) { connectionIdElement.textContent = event.connection_id; } @@ -513,13 +467,10 @@ class RecvonlyClient { this.analyzeAudioStream(new MediaStream([event.track])); // <audio> 要素に音声ストリームを設定 - const audioElement = - document.querySelector<HTMLAudioElement>("#recvonly-audio"); + const audioElement = document.querySelector<HTMLAudioElement>("#recvonly-audio"); if (audioElement) { audioElement.srcObject = stream; - audioElement - .play() - .catch((error) => console.error("音声の再生に失敗しました:", error)); + audioElement.play().catch((error) => console.error("音声の再生に失敗しました:", error)); } } } diff --git a/check_stereo_multi/main.ts b/check_stereo_multi/main.ts index bf80154..64ff1b9 100644 --- a/check_stereo_multi/main.ts +++ b/check_stereo_multi/main.ts @@ -34,59 +34,45 @@ document.addEventListener("DOMContentLoaded", async () => { // デバイスの変更を監視 navigator.mediaDevices.addEventListener("devicechange", updateDeviceLists); - document - .querySelector("#sendonly-connect-1") - ?.addEventListener("click", async () => { - const audioInputSelect = document.querySelector<HTMLSelectElement>( - "#sendonly-audio-input-1", - ); - const selectedAudioDeviceId = audioInputSelect?.value; - const stream = await navigator.mediaDevices.getUserMedia({ - video: false, - audio: { - deviceId: selectedAudioDeviceId - ? { exact: selectedAudioDeviceId } - : undefined, - echoCancellation: false, - noiseSuppression: false, - autoGainControl: false, - channelCount: 2, - sampleRate: 48000, - sampleSize: 16, - }, - }); - await sendonly1.connect(stream); + document.querySelector("#sendonly-connect-1")?.addEventListener("click", async () => { + const audioInputSelect = document.querySelector<HTMLSelectElement>("#sendonly-audio-input-1"); + const selectedAudioDeviceId = audioInputSelect?.value; + const stream = await navigator.mediaDevices.getUserMedia({ + video: false, + audio: { + deviceId: selectedAudioDeviceId ? { exact: selectedAudioDeviceId } : undefined, + echoCancellation: false, + noiseSuppression: false, + autoGainControl: false, + channelCount: 2, + sampleRate: 48000, + sampleSize: 16, + }, }); + await sendonly1.connect(stream); + }); - document - .querySelector("#sendonly-connect-2") - ?.addEventListener("click", async () => { - const audioInputSelect = document.querySelector<HTMLSelectElement>( - "#sendonly-audio-input-2", - ); - const selectedAudioDeviceId = audioInputSelect?.value; - const stream = await navigator.mediaDevices.getUserMedia({ - video: false, - audio: { - deviceId: selectedAudioDeviceId - ? { exact: selectedAudioDeviceId } - : undefined, - echoCancellation: false, - noiseSuppression: false, - autoGainControl: false, - channelCount: 2, - sampleRate: 48000, - sampleSize: 16, - }, - }); - await sendonly2.connect(stream); + document.querySelector("#sendonly-connect-2")?.addEventListener("click", async () => { + const audioInputSelect = document.querySelector<HTMLSelectElement>("#sendonly-audio-input-2"); + const selectedAudioDeviceId = audioInputSelect?.value; + const stream = await navigator.mediaDevices.getUserMedia({ + video: false, + audio: { + deviceId: selectedAudioDeviceId ? { exact: selectedAudioDeviceId } : undefined, + echoCancellation: false, + noiseSuppression: false, + autoGainControl: false, + channelCount: 2, + sampleRate: 48000, + sampleSize: 16, + }, }); + await sendonly2.connect(stream); + }); - document - .querySelector("#recvonly-connect") - ?.addEventListener("click", async () => { - await recvonly.connect(); - }); + document.querySelector("#recvonly-connect")?.addEventListener("click", async () => { + await recvonly.connect(); + }); }); // デバイスリストを更新する関数 @@ -100,9 +86,7 @@ async function updateDeviceLists() { if (audioInputSelect) { audioInputSelect.innerHTML = ""; - const audioInputDevices = devices.filter( - (device) => device.kind === "audioinput", - ); + const audioInputDevices = devices.filter((device) => device.kind === "audioinput"); for (const device of audioInputDevices) { const option = document.createElement("option"); option.value = device.deviceId; @@ -170,9 +154,7 @@ class SendonlyClient { if (!this.connection.pc) { return undefined; } - const sender = this.connection.pc - .getSenders() - .find((sender) => sender.track?.kind === "audio"); + const sender = this.connection.pc.getSenders().find((sender) => sender.track?.kind === "audio"); if (!sender) { return undefined; } @@ -258,11 +240,7 @@ class SendonlyClient { this.canvasCtx.fillStyle = "rgb(240, 240, 240)"; this.canvasCtx.fillRect(0, 0, width, height); - const drawChannel = ( - dataArray: Float32Array, - color: string, - offset: number, - ) => { + const drawChannel = (dataArray: Float32Array, color: string, offset: number) => { if (!this.canvasCtx) return; this.canvasCtx.lineWidth = 3; @@ -304,10 +282,7 @@ class SendonlyClient { this.canvasCtx.fillText(isMonaural ? "Monaural" : "Stereo", 10, 30); } - private isMonaural( - dataArrayL: Float32Array, - dataArrayR: Float32Array, - ): boolean { + private isMonaural(dataArrayL: Float32Array, dataArrayR: Float32Array): boolean { const threshold = 0.001; for (let i = 0; i < dataArrayL.length; i++) { if (Math.abs(dataArrayL[i] - dataArrayR[i]) > threshold) { @@ -340,9 +315,7 @@ class SendonlyClient { ); if (channelElement) { channelElement.textContent = - channels !== undefined - ? `getParameters codecs channels: ${channels}` - : "undefined"; + channels !== undefined ? `getParameters codecs channels: ${channels}` : "undefined"; } }, 1000); // 1秒ごとにチェック } @@ -369,11 +342,7 @@ class RecvonlyClient { this.options = {}; this.sora = Sora.connection(signalingUrl, this.debug); - this.connection = this.sora.recvonly( - this.channelId, - undefined, - this.options, - ); + this.connection = this.sora.recvonly(this.channelId, undefined, this.options); this.connection.on("notify", this.onnotify.bind(this)); this.connection.on("track", this.ontrack.bind(this)); } @@ -382,11 +351,8 @@ class RecvonlyClient { const jwt = await generateJwt(this.channelId, this.secretKey); this.connection.metadata = { access_token: jwt }; - const forceStereoOutputElement = - document.querySelector<HTMLInputElement>("#forceStereoOutput"); - const forceStereoOutput = forceStereoOutputElement - ? forceStereoOutputElement.checked - : false; + const forceStereoOutputElement = document.querySelector<HTMLInputElement>("#forceStereoOutput"); + const forceStereoOutput = forceStereoOutputElement ? forceStereoOutputElement.checked : false; this.connection.options.forceStereoOutput = forceStereoOutput; await this.connection.connect(); @@ -446,8 +412,7 @@ class RecvonlyClient { } // 既存のコード - const recvonlyStereoElement = - document.querySelector<HTMLDivElement>("#recvonly-stereo"); + const recvonlyStereoElement = document.querySelector<HTMLDivElement>("#recvonly-stereo"); if (recvonlyStereoElement) { recvonlyStereoElement.textContent = result; } @@ -462,11 +427,7 @@ class RecvonlyClient { } } - private drawWaveforms( - dataArrayL: Float32Array, - dataArrayR: Float32Array, - streamId: string, - ) { + private drawWaveforms(dataArrayL: Float32Array, dataArrayR: Float32Array, streamId: string) { const canvasCtx = this.canvasCtxs.get(streamId); const canvas = this.canvases.get(streamId); if (!canvasCtx || !canvas) return; @@ -477,11 +438,7 @@ class RecvonlyClient { canvasCtx.fillStyle = "rgb(240, 240, 240)"; canvasCtx.fillRect(0, 0, width, height); - const drawChannel = ( - dataArray: Float32Array, - color: string, - offset: number, - ) => { + const drawChannel = (dataArray: Float32Array, color: string, offset: number) => { if (!canvasCtx) return; canvasCtx.lineWidth = 3; @@ -518,10 +475,7 @@ class RecvonlyClient { canvasCtx.fillText(isMonaural ? "Monaural" : "Stereo", 10, 30); } - private isMonaural( - dataArrayL: Float32Array, - dataArrayR: Float32Array, - ): boolean { + private isMonaural(dataArrayL: Float32Array, dataArrayR: Float32Array): boolean { const threshold = 0.001; for (let i = 0; i < dataArrayL.length; i++) { if (Math.abs(dataArrayL[i] - dataArrayR[i]) > threshold) { @@ -537,9 +491,7 @@ class RecvonlyClient { event.event_type === "connection.created" && this.connection.connectionId === event.connection_id ) { - const connectionIdElement = document.querySelector<HTMLDivElement>( - "#recvonly-connection-id", - ); + const connectionIdElement = document.querySelector<HTMLDivElement>("#recvonly-connection-id"); if (connectionIdElement) { connectionIdElement.textContent = event.connection_id; } @@ -552,8 +504,7 @@ class RecvonlyClient { if (event.track.kind === "audio") { this.analyzeAudioStream(new MediaStream([event.track]), stream.id); const remoteAudioId = `remoteaudio-${stream.id}`; - const remoteAudios = - document.querySelector<HTMLDivElement>("#remote-audios"); + const remoteAudios = document.querySelector<HTMLDivElement>("#remote-audios"); if (remoteAudios && !remoteAudios.querySelector(`#${remoteAudioId}`)) { const remoteAudioDiv = document.createElement("div"); remoteAudioDiv.id = `remote-audio-${remoteAudioId}`; diff --git a/messaging/main.ts b/messaging/main.ts index 7f0035e..d1b5e06 100644 --- a/messaging/main.ts +++ b/messaging/main.ts @@ -21,13 +21,9 @@ document.addEventListener("DOMContentLoaded", async () => { const client = new SoraClient(signalingUrl, channelId, secretKey); document.querySelector("#connect")?.addEventListener("click", async () => { - const checkCompress = document.getElementById( - "check-compress", - ) as HTMLInputElement; + const checkCompress = document.getElementById("check-compress") as HTMLInputElement; const compress = checkCompress.checked; - const checkHeader = document.getElementById( - "check-header", - ) as HTMLInputElement; + const checkHeader = document.getElementById("check-header") as HTMLInputElement; const header = checkHeader.checked; await client.connect(compress, header); @@ -37,16 +33,12 @@ document.addEventListener("DOMContentLoaded", async () => { await client.disconnect(); }); - document - .querySelector("#send-message") - ?.addEventListener("click", async () => { - const value = document.querySelector<HTMLInputElement>( - "input[name=message]", - )?.value; - if (value !== undefined && value !== "") { - await client.sendMessage(value); - } - }); + document.querySelector("#send-message")?.addEventListener("click", async () => { + const value = document.querySelector<HTMLInputElement>("input[name=message]")?.value; + if (value !== undefined && value !== "") { + await client.sendMessage(value); + } + }); document.querySelector("#get-stats")?.addEventListener("click", async () => { const statsReport = await client.getStats(); @@ -54,14 +46,9 @@ document.addEventListener("DOMContentLoaded", async () => { for (const report of statsReport.values()) { statsReportJson.push(report); } - const statsReportJsonElement = - document.querySelector<HTMLPreElement>("#stats-report-json"); + const statsReportJsonElement = document.querySelector<HTMLPreElement>("#stats-report-json"); if (statsReportJsonElement) { - statsReportJsonElement.textContent = JSON.stringify( - statsReportJson, - null, - 2, - ); + statsReportJsonElement.textContent = JSON.stringify(statsReportJson, null, 2); } }); }); @@ -123,8 +110,7 @@ class SoraClient { async disconnect() { await this.connection.disconnect(); - const receivedMessagesElement = - document.querySelector("#received-messages"); + const receivedMessagesElement = document.querySelector("#received-messages"); if (receivedMessagesElement) { receivedMessagesElement.innerHTML = ""; } @@ -139,10 +125,7 @@ class SoraClient { async sendMessage(message: string) { if (message !== "") { - await this.connection.sendMessage( - "#example", - new TextEncoder().encode(message), - ); + await this.connection.sendMessage("#example", new TextEncoder().encode(message)); } } @@ -165,8 +148,7 @@ class SoraClient { } // 送信ボタンを有効にする - const sendMessageButton = - document.querySelector<HTMLButtonElement>("#send-message"); + const sendMessageButton = document.querySelector<HTMLButtonElement>("#send-message"); if (sendMessageButton) { sendMessageButton.disabled = false; } diff --git a/package.json b/package.json index a7dacc0..b0820c3 100644 --- a/package.json +++ b/package.json @@ -36,4 +36,4 @@ "engines": { "node": ">=18" } -} \ No newline at end of file +} diff --git a/recvonly/main.ts b/recvonly/main.ts index d3a2ef4..898eb5e 100644 --- a/recvonly/main.ts +++ b/recvonly/main.ts @@ -34,14 +34,9 @@ document.addEventListener("DOMContentLoaded", () => { for (const report of statsReport.values()) { statsReportJson.push(report); } - const statsReportJsonElement = - document.querySelector<HTMLPreElement>("#stats-report-json"); + const statsReportJsonElement = document.querySelector<HTMLPreElement>("#stats-report-json"); if (statsReportJsonElement) { - statsReportJsonElement.textContent = JSON.stringify( - statsReportJson, - null, - 2, - ); + statsReportJsonElement.textContent = JSON.stringify(statsReportJson, null, 2); } }); }); @@ -120,8 +115,7 @@ class SoraClient { // Sora の場合、event.streams には MediaStream が 1 つだけ含まれる const stream = event.streams[0]; const remoteVideoId = `remote-video-${stream.id}`; - const remoteVideos = - document.querySelector<HTMLDivElement>("#remote-videos"); + const remoteVideos = document.querySelector<HTMLDivElement>("#remote-videos"); if (remoteVideos && !remoteVideos.querySelector(`#${remoteVideoId}`)) { const remoteVideo = document.createElement("video"); remoteVideo.id = remoteVideoId; diff --git a/replace_track/main.ts b/replace_track/main.ts index 515047b..6bd1493 100644 --- a/replace_track/main.ts +++ b/replace_track/main.ts @@ -24,16 +24,14 @@ document.addEventListener("DOMContentLoaded", async () => { await client.connect(); }); - document - .querySelector("#replace-stream") - ?.addEventListener("click", async () => { - // audio: true, video: true なので要注意 - const stream = await navigator.mediaDevices.getUserMedia({ - audio: true, - video: true, - }); - await client.replaceStream(stream); + document.querySelector("#replace-stream")?.addEventListener("click", async () => { + // audio: true, video: true なので要注意 + const stream = await navigator.mediaDevices.getUserMedia({ + audio: true, + video: true, }); + await client.replaceStream(stream); + }); document.querySelector("#disconnect")?.addEventListener("click", async () => { await client.disconnect(); @@ -45,14 +43,9 @@ document.addEventListener("DOMContentLoaded", async () => { for (const report of statsReport.values()) { statsReportJson.push(report); } - const statsReportJsonElement = - document.querySelector<HTMLPreElement>("#stats-report-json"); + const statsReportJsonElement = document.querySelector<HTMLPreElement>("#stats-report-json"); if (statsReportJsonElement) { - statsReportJsonElement.textContent = JSON.stringify( - statsReportJson, - null, - 2, - ); + statsReportJsonElement.textContent = JSON.stringify(statsReportJson, null, 2); } }); }); @@ -83,11 +76,7 @@ class SoraClient { this.stream = new MediaStream(); this.sora = Sora.connection(signalingUrl, this.debug); - this.connection = this.sora.sendrecv( - this.channelId, - undefined, - this.options, - ); + this.connection = this.sora.sendrecv(this.channelId, undefined, this.options); this.connection.on("notify", this.onnotify.bind(this)); this.connection.on("track", this.ontrack.bind(this)); this.connection.on("removetrack", this.onremovetrack.bind(this)); @@ -110,16 +99,10 @@ class SoraClient { async replaceStream(stream: MediaStream) { if (stream.getAudioTracks().length > 0) { - await this.connection.replaceAudioTrack( - this.stream, - stream.getAudioTracks()[0], - ); + await this.connection.replaceAudioTrack(this.stream, stream.getAudioTracks()[0]); } if (stream.getVideoTracks().length > 0) { - await this.connection.replaceVideoTrack( - this.stream, - stream.getVideoTracks()[0], - ); + await this.connection.replaceVideoTrack(this.stream, stream.getVideoTracks()[0]); } this.stream = stream; } diff --git a/sendonly/main.ts b/sendonly/main.ts index c6c74dc..81ed3b8 100644 --- a/sendonly/main.ts +++ b/sendonly/main.ts @@ -38,14 +38,9 @@ document.addEventListener("DOMContentLoaded", async () => { for (const report of statsReport.values()) { statsReportJson.push(report); } - const statsReportJsonElement = - document.querySelector<HTMLPreElement>("#stats-report-json"); + const statsReportJsonElement = document.querySelector<HTMLPreElement>("#stats-report-json"); if (statsReportJsonElement) { - statsReportJsonElement.textContent = JSON.stringify( - statsReportJson, - null, - 2, - ); + statsReportJsonElement.textContent = JSON.stringify(statsReportJson, null, 2); } }); }); @@ -86,8 +81,7 @@ class SoraClient { await this.connection.connect(stream); - const videoElement = - document.querySelector<HTMLVideoElement>("#local-video"); + const videoElement = document.querySelector<HTMLVideoElement>("#local-video"); if (videoElement) { videoElement.srcObject = stream; } @@ -96,8 +90,7 @@ class SoraClient { async disconnect(): Promise<void> { await this.connection.disconnect(); - const videoElement = - document.querySelector<HTMLVideoElement>("#local-video"); + const videoElement = document.querySelector<HTMLVideoElement>("#local-video"); if (videoElement) { videoElement.srcObject = null; } diff --git a/sendrecv/main.ts b/sendrecv/main.ts index 70148b9..b4b4771 100644 --- a/sendrecv/main.ts +++ b/sendrecv/main.ts @@ -37,14 +37,9 @@ document.addEventListener("DOMContentLoaded", async () => { for (const report of statsReport.values()) { statsReportJson.push(report); } - const statsReportJsonElement = - document.querySelector<HTMLPreElement>("#stats-report-json"); + const statsReportJsonElement = document.querySelector<HTMLPreElement>("#stats-report-json"); if (statsReportJsonElement) { - statsReportJsonElement.textContent = JSON.stringify( - statsReportJson, - null, - 2, - ); + statsReportJsonElement.textContent = JSON.stringify(statsReportJson, null, 2); } }); }); @@ -66,11 +61,7 @@ class SoraClient { this.options = {}; this.sora = Sora.connection(signalingUrl, this.debug); - this.connection = this.sora.sendrecv( - this.channelId, - undefined, - this.options, - ); + this.connection = this.sora.sendrecv(this.channelId, undefined, this.options); this.connection.on("notify", this.onnotify.bind(this)); this.connection.on("track", this.ontrack.bind(this)); this.connection.on("removetrack", this.onremovetrack.bind(this)); diff --git a/simulcast/main.ts b/simulcast/main.ts index 3836847..c5521d6 100644 --- a/simulcast/main.ts +++ b/simulcast/main.ts @@ -19,45 +19,25 @@ document.addEventListener("DOMContentLoaded", () => { const channelName = urlParams.get("channelName") || ""; const channelId = `${channelIdPrefix}:${channelName}:${channelIdSuffix}`; - const sendonly = new SimulcastSendonlySoraClient( - signalingUrl, - channelId, - secretKey, - { - audio: false, - video: true, - videoCodecType: "VP8", - videoBitRate: 2500, - simulcast: true, - }, - ); - const recvonlyR0 = new SimulcastRecvonlySoraClient( - signalingUrl, - channelId, - secretKey, - { - simulcast: true, - simulcastRid: "r0", - }, - ); - const recvonlyR1 = new SimulcastRecvonlySoraClient( - signalingUrl, - channelId, - secretKey, - { - simulcast: true, - simulcastRid: "r1", - }, - ); - const recvonlyR2 = new SimulcastRecvonlySoraClient( - signalingUrl, - channelId, - secretKey, - { - simulcast: true, - simulcastRid: "r2", - }, - ); + const sendonly = new SimulcastSendonlySoraClient(signalingUrl, channelId, secretKey, { + audio: false, + video: true, + videoCodecType: "VP8", + videoBitRate: 2500, + simulcast: true, + }); + const recvonlyR0 = new SimulcastRecvonlySoraClient(signalingUrl, channelId, secretKey, { + simulcast: true, + simulcastRid: "r0", + }); + const recvonlyR1 = new SimulcastRecvonlySoraClient(signalingUrl, channelId, secretKey, { + simulcast: true, + simulcastRid: "r1", + }); + const recvonlyR2 = new SimulcastRecvonlySoraClient(signalingUrl, channelId, secretKey, { + simulcast: true, + simulcastRid: "r2", + }); document.querySelector("#connect")?.addEventListener("click", async () => { // sendonly @@ -92,14 +72,9 @@ document.addEventListener("DOMContentLoaded", () => { for (const report of statsReport.values()) { statsReportJson.push(report); } - const statsReportJsonElement = - document.querySelector<HTMLPreElement>("#stats-report-json"); + const statsReportJsonElement = document.querySelector<HTMLPreElement>("#stats-report-json"); if (statsReportJsonElement) { - statsReportJsonElement.textContent = JSON.stringify( - statsReportJson, - null, - 2, - ); + statsReportJsonElement.textContent = JSON.stringify(statsReportJson, null, 2); } }); }); @@ -126,11 +101,7 @@ class SimulcastSendonlySoraClient { this.options = options; this.sora = Sora.connection(signaling_url, this.debug); - this.connection = this.sora.sendonly( - this.channelId, - undefined, - this.options, - ); + this.connection = this.sora.sendonly(this.channelId, undefined, this.options); this.connection.on("notify", this.onnotify.bind(this)); } @@ -170,9 +141,7 @@ class SimulcastSendonlySoraClient { event.event_type === "connection.created" && event.connection_id === this.connection.connectionId ) { - const localVideoConnectionId = document.querySelector( - "#local-video-connection-id", - ); + const localVideoConnectionId = document.querySelector("#local-video-connection-id"); if (localVideoConnectionId) { localVideoConnectionId.textContent = `${event.connection_id}`; } @@ -202,11 +171,7 @@ class SimulcastRecvonlySoraClient { this.options = options; this.sora = Sora.connection(signaling_url, this.debug); - this.connection = this.sora.recvonly( - this.channelId, - undefined, - this.options, - ); + this.connection = this.sora.recvonly(this.channelId, undefined, this.options); this.connection.on("notify", this.onnotify.bind(this)); this.connection.on("track", this.ontrack.bind(this)); this.connection.on("removetrack", this.onremovetrack.bind(this)); diff --git a/spotlight_sendrecv/main.ts b/spotlight_sendrecv/main.ts index 5895c8b..47ea06b 100644 --- a/spotlight_sendrecv/main.ts +++ b/spotlight_sendrecv/main.ts @@ -55,11 +55,7 @@ class SoraClient { spotlightNumber: 1, }; - this.connection = this.sora.sendrecv( - this.channelId, - undefined, - this.options, - ); + this.connection = this.sora.sendrecv(this.channelId, undefined, this.options); this.connection.on("notify", this.onnotify.bind(this)); this.connection.on("track", this.ontrack.bind(this)); @@ -102,8 +98,7 @@ class SoraClient { event.event_type === "connection.created" && this.connection.connectionId === event.connection_id ) { - const connectionIdElement = - document.querySelector<HTMLDivElement>("#connection-id"); + const connectionIdElement = document.querySelector<HTMLDivElement>("#connection-id"); if (connectionIdElement) { connectionIdElement.textContent = event.connection_id; } @@ -113,8 +108,7 @@ class SoraClient { private ontrack(event: RTCTrackEvent): void { const stream = event.streams[0]; const remoteVideoId = `remote-video-${stream.id}`; - const remoteVideos = - document.querySelector<HTMLDivElement>("#remote-videos"); + const remoteVideos = document.querySelector<HTMLDivElement>("#remote-videos"); if (remoteVideos && !remoteVideos.querySelector(`#${remoteVideoId}`)) { const remoteVideo = document.createElement("video"); remoteVideo.id = remoteVideoId; @@ -131,13 +125,9 @@ class SoraClient { private onremovetrack(event: MediaStreamTrackEvent): void { const target = event.target as MediaStream; - const remoteVideo = document.querySelector<HTMLVideoElement>( - `#remote-video-${target.id}`, - ); + const remoteVideo = document.querySelector<HTMLVideoElement>(`#remote-video-${target.id}`); if (remoteVideo) { - document - .querySelector<HTMLDivElement>("#remote-videos") - ?.removeChild(remoteVideo); + document.querySelector<HTMLDivElement>("#remote-videos")?.removeChild(remoteVideo); } } } diff --git a/src/misc.ts b/src/misc.ts index 07b9d49..a14cb95 100644 --- a/src/misc.ts +++ b/src/misc.ts @@ -1,9 +1,6 @@ import * as jose from "jose"; -export const generateJwt = async ( - channelId: string, - secretKey: string, -): Promise<string> => { +export const generateJwt = async (channelId: string, secretKey: string): Promise<string> => { const header = { alg: "HS256", typ: "JWT" }; return ( new jose.SignJWT({ diff --git a/tests/sendrecv.test.ts b/tests/sendrecv.test.ts index e0b5760..a814870 100644 --- a/tests/sendrecv.test.ts +++ b/tests/sendrecv.test.ts @@ -6,12 +6,8 @@ test("sendrecv x2", async ({ browser }) => { // テストごとに異なる channelName を生成 const channelName = crypto.randomUUID(); - await sendrecv1.goto( - `http://localhost:9000/sendrecv/?channelName=${channelName}`, - ); - await sendrecv2.goto( - `http://localhost:9000/sendrecv/?channelName=${channelName}`, - ); + await sendrecv1.goto(`http://localhost:9000/sendrecv/?channelName=${channelName}`); + await sendrecv2.goto(`http://localhost:9000/sendrecv/?channelName=${channelName}`); await sendrecv1.click("#connect"); await sendrecv2.click("#connect"); @@ -20,20 +16,14 @@ test("sendrecv x2", async ({ browser }) => { await sendrecv1.waitForSelector("#connection-id:not(:empty)"); // "connection-id" 要素の内容を取得 - const sendrecv1ConnectionId = await sendrecv1.$eval( - "#connection-id", - (el) => el.textContent, - ); + const sendrecv1ConnectionId = await sendrecv1.$eval("#connection-id", (el) => el.textContent); console.log(`sendrecv1 connectionId=${sendrecv1ConnectionId}`); // "connection-id" 要素が存在し、その内容が空でないことを確認するまで待つ await sendrecv2.waitForSelector("#connection-id:not(:empty)"); // "connection-id" 要素の内容を取得 - const sendrecv2ConnectionId = await sendrecv2.$eval( - "#connection-id", - (el) => el.textContent, - ); + const sendrecv2ConnectionId = await sendrecv2.$eval("#connection-id", (el) => el.textContent); console.log(`sendrecv2 connectionId=${sendrecv2ConnectionId}`); // レース対策 @@ -48,15 +38,10 @@ test("sendrecv x2", async ({ browser }) => { // 統計情報が表示されるまで待機 await sendrecv1.waitForSelector("#stats-report-json"); // テキストコンテンツから統計情報を取得 - const sendrecv1StatsReportJson: Record<string, unknown>[] = - await sendrecv1.evaluate(() => { - const statsReportElement = document.querySelector( - "#stats-report-json", - ) as HTMLPreElement; - return statsReportElement - ? JSON.parse(statsReportElement.textContent || "[]") - : []; - }); + const sendrecv1StatsReportJson: Record<string, unknown>[] = await sendrecv1.evaluate(() => { + const statsReportElement = document.querySelector("#stats-report-json") as HTMLPreElement; + return statsReportElement ? JSON.parse(statsReportElement.textContent || "[]") : []; + }); const sendrecv1VideoOutboundRtpStats = sendrecv1StatsReportJson.find( (stats) => stats.type === "outbound-rtp" && stats.kind === "video", @@ -80,15 +65,10 @@ test("sendrecv x2", async ({ browser }) => { // 統計情報が表示されるまで待機 await sendrecv2.waitForSelector("#stats-report-json"); // デキストコンテンツから統計情報を取得 - const sendrecv2StatsReportJson: Record<string, unknown>[] = - await sendrecv2.evaluate(() => { - const statsReportElement = document.querySelector( - "#stats-report-json", - ) as HTMLPreElement; - return statsReportElement - ? JSON.parse(statsReportElement.textContent || "[]") - : []; - }); + const sendrecv2StatsReportJson: Record<string, unknown>[] = await sendrecv2.evaluate(() => { + const statsReportElement = document.querySelector("#stats-report-json") as HTMLPreElement; + return statsReportElement ? JSON.parse(statsReportElement.textContent || "[]") : []; + }); const sendrecv2VideoOutboundRtpStats = sendrecv2StatsReportJson.find( (stats) => stats.type === "outbound-rtp" && stats.kind === "video",