gpt4 book ai didi

audio - Libav 和 xaudio2 - 音频不播放

转载 作者:行者123 更新时间:2023-12-03 00:53:16 25 4
gpt4 key购买 nike

我正在尝试使用 xaudio2 使用 libav 播放音频。我正在使用的 xaudio2 代码适用于使用 avcodec_decode_audio2 的较旧的 ffmpeg,但 avcodec_decode_audio4 已弃用该代码。我尝试了各种 libav 示例,但似乎无法播放音频。视频播放良好(或者说它现在播放得很快,因为我还没有编写任何同步代码)。

首先音频被初始化,没有错误,视频被初始化,然后数据包:

while (1) {
//is this packet from the video or audio stream?
if (packet.stream_index == player.v_id) {
add_video_to_queue(&packet);
} else if (packet.stream_index == player.a_id) {
add_sound_to_queue(&packet);
} else {
av_free_packet(&packet);
}
}

然后在 add_sound_to_queue 中:
int add_sound_to_queue(AVPacket * packet) {
AVFrame *decoded_frame = NULL;
int done = AVCODEC_MAX_AUDIO_FRAME_SIZE;
int got_frame = 0;

if (!decoded_frame) {
if (!(decoded_frame = avcodec_alloc_frame())) {
printf("[ADD_SOUND_TO_QUEUE] Out of memory\n");
return -1;
}
} else {
avcodec_get_frame_defaults(decoded_frame);
}

if (avcodec_decode_audio4(player.av_acodecctx, decoded_frame, &got_frame, packet) < 0) {
printf("[ADD_SOUND_TO_QUEUE] Error in decoding audio\n");
av_free_packet(packet);
//continue;
return -1;
}
if (got_frame) {
int data_size;
if (packet->size > done) {
data_size = done;
} else {
data_size = packet->size;
}
BYTE * snd = (BYTE *)malloc( data_size * sizeof(BYTE));

XMemCpy(snd,
AudioBytes,
data_size * sizeof(BYTE)
);

XMemSet(&g_SoundBuffer,0,sizeof(XAUDIO2_BUFFER));

g_SoundBuffer.AudioBytes = data_size;
g_SoundBuffer.pAudioData = snd;
g_SoundBuffer.pContext = (VOID*)snd;

XAUDIO2_VOICE_STATE state;
while( g_pSourceVoice->GetState( &state ), state.BuffersQueued > 60 ) {
WaitForSingleObject( XAudio2_Notifier.hBufferEndEvent, INFINITE );
}

g_pSourceVoice->SubmitSourceBuffer( &g_SoundBuffer );
}
return 0;
}

我似乎无法找出问题所在,我在 init、打开视频、编解码器处理等中添加了错误消息。如前所述,xaudio2 代码正在使用较旧的 ffmpeg,所以也许我错过了 avcodec_decode_audio4 的某些内容?

如果这个代码片段还不够,我可以发布整个代码,这些只是代码中我认为问题所在的地方:(

最佳答案

我没有看到您访问 decoded_frame解码后的任何地方。否则,您希望如何获取数据?

BYTE * snd = (BYTE *)malloc( data_size * sizeof(BYTE));

这看起来也很可疑,因为 data_size是从数据包大小得出的。数据包大小是压缩数据的大小,与解码后的PCM帧大小关系不大。

解码后的数据位于 decoded_frame->extended_data ,它是指向数据平面的指针数组,请参阅 here详情。解码数据的大小由 decoded_frame->nb_samples决定.请注意,在最近的 Libav 版本中,许多解码器返回平面音频,因此不同的 channel 存在于不同的数据缓冲区中。对于许多用例,您需要将其转换为交错格式,其中只有一个缓冲区包含所有 channel 。使用 libavresample为了那个原因。

关于audio - Libav 和 xaudio2 - 音频不播放,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18423324/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com