【问题标题】:NV12 Format support in Bitmapimage C#位图图像 C# 中的 NV12 格式支持
【发布时间】:2013-07-16 14:02:50
【问题描述】:

BitmapImageWriteableBitmapImage 是否支持 NV12 格式。或者我们可以从一个以 NV12 格式排列的字节数组创建一个BitmapImageWriteableBitmapImage 吗?

谢谢

【问题讨论】:

  • 您是否设法实现了您的 NV12 转换器方法?

标签: c# bitmapimage yuv writeablebitmap nv12-nv21


【解决方案1】:

没有。 NV12 不在支持的PixelFormats 中。

您必须先将字节数组转换为支持的像素格式。 This 答案显示了如何为 YUV 执行此操作,并且可能会帮助您编写类似的方法来从 NV12 进行转换。

编辑:

Here 是用于将 NV21 (!) 转换为 RGB 的 C++ 代码。与NV12 的唯一区别是UV 值的顺序,因此很容易适应。

【讨论】:

    【解决方案2】:

    带着这个答案从未来滑入。

    此方法将 NV12 数据的 byte[] 数组转换为 BMP 图像。

    public static Bitmap TransformNv12ToBmpFaster(byte[] data, int width, int height, IGraphLogger logger)
            {
                Stopwatch watch = new Stopwatch();
                watch.Start();
    
                var bmp = new Bitmap(width, height, PixelFormat.Format32bppPArgb);
                var bmpData = bmp.LockBits(
                    new Rectangle(0, 0, bmp.Width, bmp.Height),
                    ImageLockMode.ReadWrite,
                    PixelFormat.Format32bppRgb);
    
                var uvStart = width * height;
                for (var y = 0; y < height; y++)
                {
                    var pos = y * width;
                    var posInBmp = y * bmpData.Stride;
                    for (var x = 0; x < width; x++)
                    {
                        var vIndex = uvStart + ((y >> 1) * width) + (x & ~1);
    
                        //// https://msdn.microsoft.com/en-us/library/windows/desktop/dd206750(v=vs.85).aspx
                        //// https://en.wikipedia.org/wiki/YUV
                        var c = data[pos] - 16;
                        var d = data[vIndex] - 128;
                        var e = data[vIndex + 1] - 128;
                        c = c < 0 ? 0 : c;
    
                        var r = ((298 * c) + (409 * e) + 128) >> 8;
                        var g = ((298 * c) - (100 * d) - (208 * e) + 128) >> 8;
                        var b = ((298 * c) + (516 * d) + 128) >> 8;
                        r = r.Clamp(0, 255);
                        g = g.Clamp(0, 255);
                        b = b.Clamp(0, 255);
    
                        Marshal.WriteInt32(bmpData.Scan0, posInBmp + (x << 2), (b << 0) | (g << 8) | (r << 16) | (0xFF << 24));
                        pos++;
                    }
                }
    
                bmp.UnlockBits(bmpData);
    
                watch.Stop();
                logger.Info($"Took {watch.ElapsedMilliseconds} ms to lock and unlock");
    
                return bmp;
            }
    

    我得到了这个 Microsoft Graph Samples 存储库,here

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2021-12-20
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-08-04
      • 2021-11-05
      相关资源
      最近更新 更多