请求编写Delphi 7下ASIO 24位音频缓冲区解交错函数
为Delphi 7 ASIO组件实现24位声道解交错函数
首先需要在现有类型定义中补充24位缓冲区的相关类型:
// 适配ASIO常用的32位容器存储24位样本的类型 TBuffer24 = array[0..0] of LongWord; PBuffer24 = ^TBuffer24; // 适配紧凑3字节存储24位样本的类型(少数驱动会用) TBuffer24Packed = array[0..0] of Byte; PBuffer24Packed = ^TBuffer24Packed;
情况1:ASIO驱动以32位容器输出24位样本(主流场景)
大多数专业音频设备的ASIO驱动会把24位样本放在32位(4字节)的容器中存储(低24位为有效数据,高位按采样类型填充符号位或0),这种场景下的解交错函数逻辑和你现有32位函数一致:
procedure Deinterleave24(InputBuffer : PBuffer24; OutputBuffer : PBufferInfoArray; Samples, BufferIndex : LongWord); var i, j : LongWord; Dest : array[0..1] of PBuffer24; begin for i := 0 to 1 do // 固定处理左右2声道 Dest[i] := OutputBuffer[i].buffers[BufferIndex]; i := 0; while i < Samples do begin j := i shl 1; // 计算交错缓冲区中的左声道样本索引 Dest[0][i] := InputBuffer[j]; // 写入左声道样本 Dest[1][i] := InputBuffer[j + 1]; // 写入右声道样本 Inc(i); end; end;
情况2:ASIO驱动以紧凑3字节输出24位样本(小众场景)
少数驱动会采用无对齐的紧凑3字节存储24位样本,此时需要按字节级拷贝来完成解交错:
procedure Deinterleave24Packed(InputBuffer : PBuffer24Packed; OutputBuffer : PBufferInfoArray; Samples, BufferIndex : LongWord); var i : LongWord; SrcPtr : PByte; DestLeft, DestRight : PByte; const SampleSize = 3; // 24位样本固定占3字节 begin // 初始化源和目标缓冲区指针 SrcPtr := InputBuffer; DestLeft := OutputBuffer[0].buffers[BufferIndex]; DestRight := OutputBuffer[1].buffers[BufferIndex]; for i := 0 to Samples - 1 do begin // 拷贝左声道24位样本 Move(SrcPtr^, DestLeft^, SampleSize); Inc(SrcPtr, SampleSize); // 拷贝右声道24位样本 Move(SrcPtr^, DestRight^, SampleSize); Inc(SrcPtr, SampleSize); // 移动目标缓冲区指针到下一个样本位置 Inc(DestLeft, SampleSize); Inc(DestRight, SampleSize); end; end;
说明
- 优先使用
Deinterleave24,因为这是ASIO 24位输出的主流格式,性能和兼容性更好。 - 如果测试发现音频有杂音或异常,再尝试
Deinterleave24Packed适配紧凑存储的驱动。
内容的提问来源于stack exchange,提问作者Ross
相关产品推荐
相关产品推荐

