質問

私は、インターネット上のY値を読んだものから、

は、輝度値であり、グレースケール画像を作成するために使用することができます。次のリンク: http://www.bobpowell.net/grayscale.htm には、いくつかを持っていますビットマップ画像の輝度を作業上のC#コード:

{
  Bitmap bm = new Bitmap(source.Width,source.Height);
  for(int y=0;y<bm.Height;y++)        public Bitmap ConvertToGrayscale(Bitmap source)
  {
    for(int x=0;x<bm.Width;x++)
    {
      Color c=source.GetPixel(x,y);
      int luma = (int)(c.R*0.3 + c.G*0.59+ c.B*0.11);
      bm.SetPixel(x,y,Color.FromArgb(luma,luma,luma));
    }
  }
  return bm;
}

Iは、YUV値を返すメソッドを有し、バイト配列内のYデータを有しています。私は、コードの現在の部分を持っており、Marshal.Copyに失敗している - 読み取りまたは書き込み保護されているメモリしようとした。

public Bitmap ConvertToGrayscale2(byte[] yuvData, int width, int height)
        {
            Bitmap bmp;
            IntPtr blue = IntPtr.Zero;

            int inputOffSet = 0;
            long[] pixels = new long[width * height];

            try
            {
                for (int y = 0; y < height; y++)
                {
                    int outputOffSet = y * width;
                    for (int x = 0; x < width; x++)
                    {
                        int grey = yuvData[inputOffSet + x] & 0xff;
                        unchecked
                        {
                            pixels[outputOffSet + x] = UINT_Constant | (grey * INT_Constant);
                        }
                    }

                    inputOffSet += width;
                }

                blue = Marshal.AllocCoTaskMem(pixels.Length);
                Marshal.Copy(pixels, 0, blue, pixels.Length); // fails here : Attempted to read or write protected memory


                bmp = new Bitmap(width, height, width, PixelFormat.Format24bppRgb, blue);

            }
            catch (Exception)
            {

                throw;
            }
            finally
            {
                if (blue != IntPtr.Zero)
                {
                    Marshal.FreeHGlobal(blue);
                    blue = IntPtr.Zero;
                }

            }

            return bmp;
        }

すべてのヘルプは?いただければ幸いです。

役に立ちましたか?

解決 3

私はこのコードを使用して実行している場合、これは安定している場合は、

私が一番上にいくつかのピクセルと黒画像を得るには、コーナーを残します:

 public static Bitmap ToGrayscale(byte[] yData, int width, int height)
    {
        Bitmap bm = new Bitmap(width, height, PixelFormat.Format32bppRgb);
        Rectangle dimension = new Rectangle(0, 0, bm.Width, bm.Height);
        BitmapData picData = bm.LockBits(dimension, ImageLockMode.ReadWrite, bm.PixelFormat);
        IntPtr pixelStateAddress = picData.Scan0;

        int stride = 4 * (int)Math.Ceiling(3 * width / 4.0);
        byte[] pixels = new byte[stride * height];

        try
        {
            for (int y = 0; y < height; y++)
            {
                for (int x = 0; x < width; x++)
                {
                    byte grey = yData[y * width + x];
                    pixels[y * stride + 3 * x] = grey;
                    pixels[y * stride + 3 * x + 1] = grey;
                    pixels[y * stride + 3 * x + 2] = grey;

                }
            }

            Marshal.Copy(pixels, 0, pixelStateAddress, pixels.Length);
            bm.UnlockBits(picData);
        }
        catch (Exception)
        {
            throw;
        }

        return bm;
    }

他のヒント

私はあなたがpixels.Lengthをのバイトの割り当てられていると思うが、多くのメモリとして8回(64ビット長または8であるpixels.Length のlong型を、コピーしていますバイト)のサイズである。

あなたが試すことができます:

blue = Marshal.AllocCoTaskMem(Marshal.SizeOf(pixels[0]) * pixels.Length); 

また、ビットマップコンストラクタの画素とPixelFormat.Format32bppRgbための使用はint [](これらは両方とも32ビットであるように)する必要があるかもしれません。 ] [長く使用すると24ビットピクセルフォーマットが期待されるものではないピクセルあたり64ビットを与える。

あなたが代わりにグレーかかわらのブルーの色合いで終わるかもしれない - 。UINT_ConstantとINT_Constantの自分の価値観が何であるかに依存します。

yuvData []はすでにバイトが含まれているとして、

は、やる "&0xffの" する必要はありません。

ここであなたが試みることができるアプローチの別のカップルがあります。

public Bitmap ConvertToGrayScale(byte[] yData, int width, int height)
{
    // 3 * width bytes per scanline, rounded up to a multiple of 4 bytes
    int stride = 4 * (int)Math.Ceiling(3 * width / 4.0);

    byte[] pixels = new byte[stride * height];
    for (int y = 0; y < height; y++)
    {
        for (int x = 0; x < width; x++)
        {
            byte grey = yData[y * width + x];
            pixels[y * stride + 3 * x] = grey;
            pixels[y * stride + 3 * x + 1] = grey;
            pixels[y * stride + 3 * x + 2] = grey;
        }
    }

    IntPtr pixelsPtr = Marshal.AllocCoTaskMem(pixels.Length);
    try
    {
        Marshal.Copy(pixels, 0, pixelsPtr, pixels.Length);

        Bitmap bitmap = new Bitmap(
            width, 
            height, 
            stride, 
            PixelFormat.Format24bppRgb, 
            pixelsPtr);
        return bitmap;
    }
    finally
    {
        Marshal.FreeHGlobal(pixelsPtr);
    }
}

public Bitmap ConvertToGrayScale(byte[] yData, int width, int height)
{
    // 3 * width bytes per scanline, rounded up to a multiple of 4 bytes
    int stride = 4 * (int)Math.Ceiling(3 * width / 4.0);

    IntPtr pixelsPtr = Marshal.AllocCoTaskMem(stride * height);
    try
    {
        for (int y = 0; y < height; y++)
        {
            for (int x = 0; x < width; x++)
            {
                byte grey = yData[y * width + x];
                Marshal.WriteByte(pixelsPtr, y * stride + 3 * x, grey);
                Marshal.WriteByte(pixelsPtr, y * stride + 3 * x + 1, grey);
                Marshal.WriteByte(pixelsPtr, y * stride + 3 * x + 2, grey);
            }
        }

        Bitmap bitmap = new Bitmap(
            width,
            height,
            stride,
            PixelFormat.Format24bppRgb,
            pixelsPtr);
        return bitmap;
    }
    finally
    {
        Marshal.FreeHGlobal(pixelsPtr);
    }
}
ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top