Skip to content

Commit 4ea6c3e

Browse files
committed
refactor: audio timestamp
1 parent b6a4ad9 commit 4ea6c3e

File tree

9 files changed

+666
-248
lines changed

9 files changed

+666
-248
lines changed

.vscode/settings.json

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,12 @@
33
"[javascript]": {
44
"editor.defaultFormatter": "esbenp.prettier-vscode"
55
},
6+
"[typescript]": {"editor.defaultFormatter": "esbenp.prettier-vscode"},
7+
"[typescriptreact]": {"editor.defaultFormatter": "esbenp.prettier-vscode"},
8+
"[javascriptreact]": {"editor.defaultFormatter": "esbenp.prettier-vscode"},
9+
"[json]": {"editor.defaultFormatter": "esbenp.prettier-vscode"},
10+
"[css]": {"editor.defaultFormatter": "esbenp.prettier-vscode"},
11+
"[markdown]": {"editor.defaultFormatter": "esbenp.prettier-vscode"},
612
"[rust]": {
713
"editor.defaultFormatter": "rust-lang.rust-analyzer",
814
"editor.inlayHints.enabled": "on"

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@ Being Deployed to Github Pages.
88

99
- https://nttcom.github.io/moq-wasm/
1010

11-
1211
## Implementation
1312

1413
Supported version: draft-ietf-moq-transport-10
@@ -108,6 +107,7 @@ cargo run -p moqt-server-sample -- --log <Log Level>
108107
### Run moqt-client-sample
109108

110109
```shell
110+
cd js && npm install
111111
make client
112112
```
113113

js/examples/call/src/media/mediaSubscriber.ts

Lines changed: 8 additions & 63 deletions
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,6 @@ interface AudioSubscriptionContext {
2222
worker: Worker
2323
writer: WritableStreamDefaultWriter<AudioData>
2424
stream: MediaStream
25-
baseTimestamp: number | null
2625
}
2726

2827
export class MediaSubscriber {
@@ -50,18 +49,16 @@ export class MediaSubscriber {
5049
| { type: 'frame'; frame: VideoFrame }
5150
| { type: 'bitrate'; kbps: number }
5251
| { type: 'latency'; media: 'video'; ms: number }
53-
| { frame: VideoFrame }
54-
if ('type' in data && data.type === 'bitrate') {
52+
if (data.type === 'bitrate') {
5553
this.handlers.onRemoteVideoBitrate?.(userId, data.kbps)
5654
return
5755
}
58-
if ('type' in data && data.type === 'latency') {
56+
if (data.type === 'latency') {
5957
this.handlers.onRemoteVideoLatency?.(userId, data.ms)
6058
return
6159
}
62-
const frame = 'type' in data ? data.frame : data.frame
6360
await writer.ready
64-
await writer.write(frame)
61+
await writer.write(data.frame)
6562
}
6663

6764
const stream = new MediaStream([generator])
@@ -86,29 +83,24 @@ export class MediaSubscriber {
8683
userId,
8784
worker,
8885
writer,
89-
stream: new MediaStream([generator]),
90-
baseTimestamp: null
86+
stream: new MediaStream([generator])
9187
}
9288
worker.onmessage = async (event: MessageEvent) => {
9389
const data = event.data as
9490
| { type: 'audioData'; audioData: AudioData }
9591
| { type: 'bitrate'; kbps: number }
9692
| { type: 'latency'; media: 'audio'; ms: number }
97-
| { audioData: AudioData }
98-
if ('type' in data && data.type === 'bitrate') {
93+
if (data.type === 'bitrate') {
9994
this.handlers.onRemoteAudioBitrate?.(userId, data.kbps)
10095
return
10196
}
102-
if ('type' in data && data.type === 'latency') {
97+
if (data.type === 'latency') {
10398
this.handlers.onRemoteAudioLatency?.(userId, data.ms)
10499
return
105100
}
106-
const audioData = 'type' in data ? data.audioData : data.audioData
107-
const retimedAudioData = this.retimeAudioData(audioData, context)
108-
console.debug(audioData.timestamp, '->', retimedAudioData.timestamp)
101+
const audioData = data.audioData
109102
await writer.ready
110-
await writer.write(retimedAudioData)
111-
audioData.close()
103+
await writer.write(audioData)
112104
}
113105

114106
this.audioContexts.set(trackAlias, context)
@@ -138,51 +130,4 @@ export class MediaSubscriber {
138130
[payload.buffer]
139131
)
140132
}
141-
142-
private retimeAudioData(audioData: AudioData, context: AudioSubscriptionContext): AudioData {
143-
const originalTimestamp = audioData.timestamp
144-
if (context.baseTimestamp === null) {
145-
context.baseTimestamp = originalTimestamp
146-
}
147-
const playbackTimestamp = originalTimestamp - context.baseTimestamp
148-
return this.cloneAudioDataWithTimestamp(audioData, playbackTimestamp)
149-
}
150-
151-
private cloneAudioDataWithTimestamp(audioData: AudioData, timestamp: number): AudioData {
152-
const options: AudioDataCopyToOptions = {
153-
planeIndex: 0,
154-
frameCount: audioData.numberOfFrames
155-
}
156-
const byteLength = audioData.allocationSize(options)
157-
const format = audioData.format as AudioSampleFormat
158-
const buffer = new ArrayBuffer(byteLength)
159-
const view = this.createAudioBufferView(format, buffer)
160-
audioData.copyTo(view, options)
161-
return new AudioData({
162-
format,
163-
sampleRate: audioData.sampleRate,
164-
numberOfFrames: audioData.numberOfFrames,
165-
numberOfChannels: audioData.numberOfChannels,
166-
timestamp,
167-
data: buffer
168-
})
169-
}
170-
171-
private createAudioBufferView(format: AudioSampleFormat, buffer: ArrayBuffer): ArrayBufferView {
172-
switch (format) {
173-
case 'u8':
174-
case 'u8-planar':
175-
return new Uint8Array(buffer)
176-
case 's16':
177-
case 's16-planar':
178-
return new Int16Array(buffer)
179-
case 's32':
180-
case 's32-planar':
181-
return new Int32Array(buffer)
182-
case 'f32':
183-
case 'f32-planar':
184-
default:
185-
return new Float32Array(buffer)
186-
}
187-
}
188133
}

0 commit comments

Comments
 (0)