Skip to content

Commit

Permalink
Fix A/V sync for FIFO transcoding with passthrough audio.
Browse files Browse the repository at this point in the history
Allow to transcode file keeping the original audio content untouched while preserving A/V sync.

Thanks to Paul Gardiner for the A/V sync fix.
  • Loading branch information
jyavenard committed Jun 12, 2011
1 parent d07153d commit a787977
Showing 1 changed file with 15 additions and 9 deletions.
24 changes: 15 additions & 9 deletions mythtv/programs/mythtranscode/transcode.cpp
Expand Up @@ -78,6 +78,7 @@ class AudioReencodeBuffer : public AudioOutput
virtual void Reset(void)
{
audiobuffer_len = 0;
audiobuffer_frames = 0;
ab_count = 0;
}

Expand Down Expand Up @@ -107,7 +108,8 @@ class AudioReencodeBuffer : public AudioOutput

memcpy(audiobuffer + audiobuffer_len, buffer,
len);
audiobuffer_len += len;
audiobuffer_len += len;
audiobuffer_frames += frames;

// last_audiotime is at the end of the frame
last_audiotime = timecode + frames * 1000 /
Expand Down Expand Up @@ -222,7 +224,8 @@ class AudioReencodeBuffer : public AudioOutput
int ab_offset[128];
long long ab_time[128];
unsigned char *audiobuffer;
int audiobuffer_len, channels, bits, bytes_per_frame, eff_audiorate;
int audiobuffer_len, audiobuffer_frames;
int channels, bits, bytes_per_frame, eff_audiorate;
long long last_audiotime;
private:
bool m_passthru, m_initpassthru;
Expand Down Expand Up @@ -785,8 +788,8 @@ int Transcode::TranscodeFile(
long long lasttimecode = 0;
long long timecodeOffset = 0;

float rateTimeConv = arb->eff_audiorate * arb->bytes_per_frame / 1000.0;
float vidFrameTime = 1000.0 / video_frame_rate;
float rateTimeConv = arb->eff_audiorate / 1000.0f;
float vidFrameTime = 1000.0f / video_frame_rate;
int wait_recover = 0;
VideoOutput *videoOutput = player->getVideoOutput();
bool is_key = 0;
Expand Down Expand Up @@ -824,18 +827,21 @@ int Transcode::TranscodeFile(
if (fifow)
{
frame.buf = lastDecode->buf;
totalAudio += arb->audiobuffer_len;
totalAudio += arb->audiobuffer_frames;
int audbufTime = (int)(totalAudio / rateTimeConv);
int auddelta = arb->last_audiotime - audbufTime;
int vidTime = (int)(curFrameNum * vidFrameTime + 0.5);
int viddelta = frame.timecode - vidTime;
int delta = viddelta - auddelta;
if (abs(delta) < 500 && abs(delta) >= vidFrameTime)
{
QString msg = QString("Audio is %1ms %2 video at # %3")
.arg(abs(delta))
.arg(((delta > 0) ? "ahead of" : "behind"))
.arg((int)curFrameNum);
QString msg = QString("Audio is %1ms %2 video at # %3: "
"auddelta=%4, viddelta=%5")
.arg(abs(delta))
.arg(((delta > 0) ? "ahead of" : "behind"))
.arg((int)curFrameNum)
.arg(auddelta)
.arg(viddelta);
VERBOSE(VB_GENERAL, msg);
dropvideo = (delta > 0) ? 1 : -1;
wait_recover = 0;
Expand Down

0 comments on commit a787977

Please sign in to comment.