[mythtv] YV12 problem
David Engel
david at istwok.net
Thu Dec 13 21:15:16 UTC 2018
On Thu, Dec 13, 2018 at 11:22:59AM +0100, Jean-Yves Avenard wrote:
> On Thu, 13 Dec 2018 at 04:28, David Engel <david at istwok.net> wrote:
>
> > I'm confused again. I thought we were talking about yv12 but you're
> > talking mostly about nv12. I know there are a plethora of pixel
> > formats but it's still mostly Greek alphabet soup to me until I get
> > further up to speed. If the hardware decoders generate nv12, how does
> > yv12 fit in? Is it a format that has to be converted to on the way to
> > output or something else?
>
> the only difference between NV12 and YUV420/YV12 is that U and V are
> interleaved for NV12.
>
> So YV12 is stored as:
> YYYY
> UUUU
> VVVV
>
> and NV12 is:
> YYYY
> UVUVUVUV
>
> that's it.
> information is identical just stored differently.
>
> YV12 fits in because all FFmpeg decoder outputs that format.
> If you have no hardware decoder you will get YV12 out
> If you use a hardware decoder you get NV12 out (with the buffer
> actually in GPU memory)
Thanks. That is very helpful.
> > I think that's kind of what I figured. The pixel format is already
> > known for the textures and handled appropriately, right? The
> > algorithm of which pixels from which lines/testures to mix with other
> > pixels remains the same.
>
> You do need to tell the GPU what textures you are you are feeding it.
> So with OpenGL, for YV12 you pass 3 textures buffer
> NV12 you pass 2 textures buffer.
>
> To show the difference on what the shader would be to access the YV12 pixel:
> float3 yuv = float3(
> tY.Sample(sSampler, aTexCoords).r,
> tCb.Sample(sSampler, aTexCoords).r,
> tCr.Sample(sSampler, aTexCoords).r);
> return CalculateYCbCrColor(yuv * vCoefficient);
>
> That's for nv12
> float y = tY.Sample(sSampler, aTexCoords).r;
> float2 cbcr = tCb.Sample(sSampler, aTexCoords).rg;
> return CalculateYCbCrColor(float3(y, cbcr) * vCoefficient);
>
> That's a D3D11 shader for Firefox OpenGL compositor (everything gets
> converted to RGB before being composited)
>
> You can see that for YV12 you access the data for U/V separately, and
> for NV12, together. that's it. 1 line change.
>
> If you were to do that in C, it would be:
> YV12
> Yvalue = Y[x] + y * strideY;
> Uvalue = U[x/2] + y * strideU;
> Vvalue = V[x/2] + y * strideV;
>
> With strideU=strideV=strideY/2
>
> For NV12:
> Yvalue = Y[x] + y * strideY;
> Uvalue = UV[int(x/2)*2] + y * strideUV;
> Vvalue = VV[int(x/2)*2+1] + y * strideUV;
>
> with strideUV = strideY
Helpful again. The C is quite understandable. The shader code is
still quite foreign to me, though.
This will hopefully help me review the yv12 changes in question.
David
--
David Engel
david at istwok.net
More information about the mythtv-dev
mailing list