用确切的时间戳记录音频

Hug*_*une 7 java android audio-recording audiorecord wear-os

我想在 Android Wear 设备上录制原始音频,并将其与其他传感器数据(例如加速度计)完全同步。要录制原始音频,我使用AudioRecord,但如何确定音频流任何部分的正确时间戳?

基本问题是我从缓冲区获取原始音频帧,但没有关于这些帧在缓冲区中的时间长度、丢失的帧数等信息。

因此,为了获取我AudioRecord.read()在循环中调用的帧数据,但如何判断特定帧是何时录制的?

我可以看到三种确定时间戳的方法,但在我看来它们都是错误的:

  1. 调用之前或之后AudioRecord.startRecording(),通过调用获取当前系统时间SystemClock.elapsedRealtimeNanos(),然后根据采样率和帧大小计算每个chunk的时间。但是根据我的测试,在录制实际开始之前有一个明显的延迟。每当某些帧丢失时,例如当处理暂停片刻时,时间也会变得不同步。

  2. 获取之前或之后的当前系统时间AudioRecord.read()。但这可能不是记录这些数据的时间,这可能发生得更早一些。如果还没有可用的数据, read() 将阻塞并且之前获取的时间戳将完全错误。

  3. AudioRecord.getTimestamp()给出当前正在录制的帧的时间。但这不一定是我当前正在阅读的帧,我可能落后几帧,或者我可能错过了一些帧。根据初始测试,在开始后的一段时间内,时间戳只是零。

这会给我留下 6 个可能错误的时间戳,如下面的代码所示。这些中的任何一个甚至接近准确吗?

recorder = new AudioRecord(...)

// timeBeforeStart =  SystemClock.elapsedRealtimeNanos()
recorder.startRecording()
// timeAfterStart =  SystemClock.elapsedRealtimeNanos()

...

// timeBeforeRead =  SystemClock.elapsedRealtimeNanos()
// recorder.getTimestamp(frameTimeBeforeRead, AudioTimestamp.TIMEBASE_BOOTTIME)
recorder.read(myArray, 0, mySize);
// recorder.getTimestamp(frameTimeAfterRead, AudioTimestamp.TIMEBASE_BOOTTIME)
// timeAfterRead =  SystemClock.elapsedRealtimeNanos()
Run Code Online (Sandbox Code Playgroud)

以下哪种方法是确定与字节数组中的数据对应的时间戳的最准确方法?

是否有不同的方法来检索具有准确时间戳的原始音频数据?

bit*_*nox -2

您需要创建相关的音频和加速计信号 - 您还可以将手电筒、相机和扬声器等加入其中。

您需要测试哪些参与者和传感器具有哪些延迟和抖动,以找到能够关联事件的最佳解决方案(不使用外部设备),以便计算接收到的音频延迟和抖动。