FFmpeg ремуксирует части аудиофайла
Я пытаюсь повторно преобразовать отдельные треки из файла FLAC, используя библиотеки FFmpeg. Я получаю начальные временные метки из таблицы Cue, я ищу временные метки, используя файлы . Однако после записи пакетов в выходные файлы они имеют данные только с начала входного файла.
Это фрагмент кода, который открывает входной файл FLAC, а также создает выходной файл.AVFormatContext
для каждого трека. Я предполагаю, что проблемаavformat_seek_file
, похоже, ничего не делает, так как, хотя я и ищу начало дорожки, выходной файл содержит данные с начала ввода.
for(int i = 0; i <= sheet.ntracks; i++) {
sheet.avfmtctx = avformat_alloc_context();
if(avformat_open_input(&sheet.avfmtctx, sheet.file, NULL, NULL) < 0) {
fprintf(stderr,
"avformat_open_input(): failed to open %s\n",
sheet.file);
return 1;
}
int audio_stream_idx = -1;
for(int i = 0; i < sheet.avfmtctx->nb_streams; i++) {
if(sheet.avfmtctx->streams[i]->codecpar->codec_type == AVMEDIA_TYPE_AUDIO) {
audio_stream_idx = i;
break;
}
}
avformat_find_stream_info(sheet.avfmtctx, NULL);
AVFormatContext *output;
char *filepath = title_to_filepath(&sheet.tracks[i], sheet.file);
avformat_alloc_output_context2(&output, NULL, NULL, filepath);
AVStream *out_audio_stream = avformat_new_stream(output, NULL);
avcodec_parameters_copy(out_audio_stream->codecpar,
sheet.avfmtctx->streams[audio_stream_idx]->codecpar);
if(avio_open(&output->pb, filepath, AVIO_FLAG_WRITE) < 0) {
fprintf(stderr, "Failed to open %s for writing\n", filepath);
return 1;
}
if(avformat_write_header(output, NULL) < 0) {
fprintf(stderr, "avformat_write_header() failed\n");
return 1;
}
int64_t current_frame = sheet.tracks[i].index;
int64_t next_track_index = (i < sheet.ntracks) ?
sheet.tracks[i + 1].index :
INT64_MAX;
if(avformat_seek_file(sheet.avfmtctx,
-1,
INT64_MIN,
current_frame,
current_frame,
0) < 0) {
fprintf(stderr, "Failed to seek to the index of track %d\n", i);
avformat_free_context(sheet.avfmtctx);
sheet.avfmtctx = NULL;
av_write_trailer(output);
avio_closep(&output->pb);
avformat_free_context(output);
free(filepath);
continue;
}
AVPacket *pkt = av_packet_alloc();
int64_t pts_diff = AV_NOPTS_VALUE, dts_diff = AV_NOPTS_VALUE;
while(current_frame < next_track_index && !avio_feof(output->pb)) {
int ret;
if((ret = av_read_frame(sheet.avfmtctx, pkt)) < 0) {
if(ret != AVERROR_EOF)
fprintf(stderr, "av_read_frame() failed: %s\n", av_err2str(ret));
break;
}
if(pkt->stream_index != audio_stream_idx)
continue;
// runs only once
if(pts_diff == AV_NOPTS_VALUE && dts_diff == AV_NOPTS_VALUE) {
pts_diff = pkt->pts;
dts_diff = pkt->dts;
}
pkt->stream_index = 0; // first and only stream
pkt->pts -= pts_diff;
pkt->dts -= dts_diff;
pkt->pos = -1;
av_interleaved_write_frame(output, pkt);
current_frame++;
}
avformat_free_context(sheet.avfmtctx);
sheet.avfmtctx = NULL;
av_write_trailer(output);
av_packet_free(&pkt);
avio_closep(&output->pb);
avformat_free_context(output);
free(filepath);
}
current_frame
иnext_track_index
рассчитываются из строк INDEX в Cue sheet:MM * 60 * 75 + SS * 75 + FF
. Может ли кто-нибудь сказать мне, что я делаю неправильно, и как получить нужные мне данные из ввода?