av_seek_frame将视频和音频跳转到指定时间戳,视频和音频不同步
环境:Qt+ffmpeg将本地MP4文件封装为rtsp流,使用av_seek_frame将视频和音频跳转到指定时间戳,
问题:音频视频不同步,且视频图画一直卡着不动
源码:
while(m_statue){//循环读取每一帧直到读完
if(OperationType.size()>0){
if(OperationType.dequeue() == 1){
int progress = ProgressTime.dequeue();
if(av_seek_frame(inAFmtCtx, inAStreamIndex, progress*AV_TIME_BASE, AVSEEK_FLAG_BACKWARD | AVSEEK_FLAG_ANY) == 0&&
av_seek_frame(inAFmtCtx, inVStreamIndex, progress*AV_TIME_BASE, AVSEEK_FLAG_BACKWARD | AVSEEK_FLAG_ANY) == 0){
qDebug()<<"跳转成功";
}
}
}
if(av_read_frame(inAFmtCtx, m_pkt)>=0){
if (m_pkt->stream_index == inVStreamIndex || m_pkt->stream_index == inAStreamIndex) {
if(m_pkt->stream_index == inVStreamIndex) {
m_pkt->stream_index = m_outVideoIndex;
m_pkt->dts *= 1;
}
if(m_pkt->stream_index == inAStreamIndex){
m_pkt->stream_index = m_outAudioIndex;
m_pkt->dts *= 1;
}
in_stream = inAFmtCtx->streams[m_pkt->stream_index];
//FIX me如果pts异常设置为0, 更为稳妥的做法是在前一帧上叠加
if(m_pkt->pts == AV_NOPTS_VALUE) {
m_pkt->pts *= 1;
}
if(m_pkt->dts == AV_NOPTS_VALUE) {
m_pkt->dts *= 1;
}
if(m_pkt->duration == AV_NOPTS_VALUE) {
m_pkt->duration = 0;
}
out_stream = outFmtCtx->streams[m_pkt->stream_index];
m_pkt->pts = av_rescale_q_rnd(m_pkt->pts, in_stream->time_base, out_stream->time_base, (enum AVRounding)(AV_ROUND_NEAR_INF | AV_ROUND_PASS_MINMAX));
m_pkt->dts = av_rescale_q_rnd(m_pkt->dts, in_stream->time_base, out_stream->time_base, (enum AVRounding)(AV_ROUND_NEAR_INF | AV_ROUND_PASS_MINMAX));
m_pkt->duration = av_rescale_q(m_pkt->duration, in_stream->time_base, out_stream->time_base);
m_pkt->pos = -1;
// 控制读取速率
if (m_pkt->stream_index == inVStreamIndex) {
int64_t duration_us = av_rescale_q(m_pkt->duration, in_stream->time_base, AV_TIME_BASE_Q);
av_usleep(duration_us);
}
if(av_interleaved_write_frame(outFmtCtx, m_pkt)<0){
qDebug()<<"Error muxing packet";
break;
}
//输出帧数
// frameIndex++;
// qDebug()<<"frameIndex:"<<frameIndex;
av_packet_unref(m_pkt);
}
}
}