From 9a5c31ce37a37c05fd5bed79a79b2f078fb5cda8 Mon Sep 17 00:00:00 2001 From: Steven Robertson <steven@strobe.cc> Date: Thu, 25 Dec 2014 15:04:10 -0800 Subject: [PATCH] Improve/fix vpx output --- cuburn/output.py | 49 +++++++++++++++++++++++++++--------------------- 1 file changed, 28 insertions(+), 21 deletions(-) diff --git a/cuburn/output.py b/cuburn/output.py index fe61e94..5d51f2f 100644 --- a/cuburn/output.py +++ b/cuburn/output.py @@ -231,50 +231,59 @@ class X264Output(Output, ClsMod): class VPxOutput(Output, ClsMod): lib = pixfmtlib - base = 'vpxenc --end-usage=3 -p 1 --cpu-used=-8 -o - -' + base = ('vpxenc --end-usage=3 -p 1 --cpu-used=-8 --lag-in-frames=4 ' + '--min-q=2 --disable-kf -o - -') def __init__(self, codec='vp9', fps=24, crf=15, pix_fmt='yuv420p'): super(VPxOutput, self).__init__() self.codec = codec self.pix_fmt = pix_fmt - self.framesize = None + self.dim = None self.subp = None self.outf = None self.args = self.base.split() if pix_fmt == 'yuv420p': self.out_filter = 'f32_to_yuv444p' - elif pix_fmt == 'yuv444p': - assert codec == 'vp9' - self.out_filter = 'f32_to_yuv444p' - self.args += ['--profile=1', '-i444'] - elif pix_fmt == 'yuv444p10': - assert codec == 'vp9' - self.out_filter = 'f32_to_yuv444p10' - self.args += ['-b', '10', '--input-bit-depth=10', - '--profile=3', '-i444'] else: - raise ValueError('Invalid pix_fmt: ' + pix_fmt) + assert codec == 'vp9' + if pix_fmt == 'yuv444p': + self.out_filter = 'f32_to_yuv444p' + self.args += ['--profile=1', '--i444'] + elif pix_fmt == 'yuv420p10': + assert codec == 'vp9' + self.out_filter = 'f32_to_yuv420p10' + self.args += ['-b', '10', '--input-bit-depth=10', '--profile=2'] + elif pix_fmt == 'yuv444p10': + assert codec == 'vp9' + self.out_filter = 'f32_to_yuv444p10' + self.args += ['-b', '10', '--input-bit-depth=10', + '--profile=3', '--i444'] + else: + raise ValueError('Invalid pix_fmt: ' + pix_fmt) self.args += ['--codec=' + codec, '--cq-level=' + str(crf), '--fps=%d/1' % fps] if codec == 'vp9': self.args += ['-t', '4'] def convert(self, fb, gnm, dim, stream=None): + self.dim = dim launchC(self.out_filter, self.mod, stream, dim, fb, fb.d_rb, fb.d_seeds) def copy(self, fb, dim, pool, stream=None): fmt = 'u1' - if self.out_filter in ('yuv444p10',): + if self.pix_fmt in ('yuv444p10', 'yuv420p10'): fmt = 'u2' - h_out = pool.allocate((3, dim.h, dim.w), fmt) + dims = (3, dim.h, dim.w) + if self.pix_fmt == 'yuv420p10': + dims = (dim.h * dim.w * 6 / 4,) + h_out = pool.allocate(dims, fmt) cuda.memcpy_dtoh_async(h_out, fb.d_back, stream) return h_out - def _spawn(self, framesize): - self.framesize = framesize - extras = ['-w', framesize[1], '-h', framesize[0]] + def _spawn(self): + extras = ['-w', self.dim.w, '-h', self.dim.h] self.outf = tempfile.TemporaryFile(bufsize=0) self.subp = Popen(map(str, self.args + extras), stdin=PIPE, stderr=PIPE, stdout=self.outf) @@ -313,12 +322,10 @@ class VPxOutput(Output, ClsMod): def encode(self, buf): out = ({}, []) - if buf is None or self.framesize != buf.shape[1:3]: - out = self._flush() if buf is None: - return out + return self._flush() if self.subp is None: - self._spawn(buf.shape[1:3]) + self._spawn() if self.pix_fmt == 'yuv420p': # Perform terrible chroma subsampling self._write(buf[0].tostring(), self.subp)