Ejemplo n.º 1
0
        public static double[] AutoWhiteBalance(this PixelByte p)
        {
            double Gr = p.TrimBayer(0, 0).Med();
            double Gb = p.TrimBayer(1, 1).Med();
            double R  = p.TrimBayer(1, 0).Med();
            double B  = p.TrimBayer(0, 1).Med();

            return(new double[] { (Gr + Gb) / (2 * R), 1.0, (Gr + Gb) / (2 * B) });
        }
Ejemplo n.º 2
0
        public static Bitmap DemosaicingTest(this PixelByte p, double[] gain, double[,] matrix, double gamma, int bayer = 0)
        {
            #region 初期化
            int s = p.Size;
            int h = p.Height;
            int w = p.Width;

            byte[] buf = new byte[s * 3];

            double r = 0;
            double b = 0;
            double g = 0;

            Bitmap     bit    = new Bitmap(w, h, PixelFormat.Format24bppRgb);
            BitmapData bmpdat = bit.LockBits(new Rectangle(0, 0, w, h), ImageLockMode.WriteOnly, PixelFormat.Format24bppRgb);

            #endregion
            #region byte配列化
            //RGB信号作成(8x8)
            int x = 0;
            int y = 0;
            #region ベイヤ補間/一階調
            double gain_r = gain[0] / 9 / 255;
            double gain_g = gain[1] / 18 / 255;
            double gain_b = gain[2] / 9 / 255;

            Action FucA = () =>
            {
                r = (p[x + 1, y + 0] + p[x + 3, y + 0] + p[x + 5, y + 0]
                     + p[x + 1, y + 2] + p[x + 3, y + 2] + p[x + 5, y + 2]
                     + p[x + 1, y + 4] + p[x + 3, y + 4] + p[x + 5, y + 4]) * gain_r;

                g = (p[x + 0, y + 0] + p[x + 2, y + 0] + p[x + 4, y + 0]
                     + p[x + 1, y + 1] + p[x + 3, y + 1] + p[x + 5, y + 1]
                     + p[x + 0, y + 2] + p[x + 2, y + 2] + p[x + 4, y + 2]
                     + p[x + 1, y + 3] + p[x + 3, y + 3] + p[x + 5, y + 3]
                     + p[x + 0, y + 4] + p[x + 2, y + 4] + p[x + 4, y + 4]
                     + p[x + 1, y + 5] + p[x + 3, y + 5] + p[x + 5, y + 5]
                     ) * gain_g;

                b = (p[x + 0, y + 1] + p[x + 2, y + 1] + p[x + 4, y + 1]
                     + p[x + 0, y + 3] + p[x + 2, y + 3] + p[x + 4, y + 3]
                     + p[x + 0, y + 5] + p[x + 2, y + 5] + p[x + 4, y + 5]
                     ) * gain_b;
            };
            Action FucB = () =>
            {
                r = (p[x + 0, y + 0] + p[x + 2, y + 0] + p[x + 4, y + 0]
                     + p[x + 0, y + 2] + p[x + 2, y + 2] + p[x + 4, y + 2]
                     + p[x + 0, y + 4] + p[x + 2, y + 4] + p[x + 4, y + 4]) * gain_r;

                g = (p[x + 1, y + 0] + p[x + 3, y + 0] + p[x + 5, y + 0]
                     + p[x + 0, y + 1] + p[x + 2, y + 1] + p[x + 4, y + 1]
                     + p[x + 1, y + 2] + p[x + 3, y + 2] + p[x + 5, y + 2]
                     + p[x + 0, y + 3] + p[x + 2, y + 3] + p[x + 4, y + 3]
                     + p[x + 1, y + 4] + p[x + 3, y + 4] + p[x + 5, y + 4]
                     + p[x + 0, y + 5] + p[x + 2, y + 5] + p[x + 4, y + 5]
                     ) * gain_g;

                b = (p[x + 1, y + 1] + p[x + 3, y + 1] + p[x + 5, y + 1]
                     + p[x + 1, y + 3] + p[x + 3, y + 3] + p[x + 5, y + 3]
                     + p[x + 1, y + 5] + p[x + 3, y + 5] + p[x + 5, y + 5]
                     ) * gain_b;
            };
            Action FucC = () =>
            {
                r = (p[x + 1, y + 1] + p[x + 3, y + 1] + p[x + 5, y + 1]
                     + p[x + 1, y + 3] + p[x + 3, y + 3] + p[x + 5, y + 3]
                     + p[x + 1, y + 5] + p[x + 3, y + 5] + p[x + 5, y + 5]) * gain_r;

                g = (p[x + 1, y + 0] + p[x + 3, y + 0] + p[x + 5, y + 0]
                     + p[x + 0, y + 1] + p[x + 2, y + 1] + p[x + 4, y + 1]
                     + p[x + 1, y + 2] + p[x + 3, y + 2] + p[x + 5, y + 2]
                     + p[x + 0, y + 3] + p[x + 2, y + 3] + p[x + 4, y + 3]
                     + p[x + 1, y + 4] + p[x + 3, y + 4] + p[x + 5, y + 4]
                     + p[x + 0, y + 5] + p[x + 2, y + 5] + p[x + 4, y + 5]
                     ) * gain_g;

                b = (p[x + 0, y + 0] + p[x + 2, y + 0] + p[x + 4, y + 0]
                     + p[x + 0, y + 2] + p[x + 2, y + 2] + p[x + 4, y + 2]
                     + p[x + 0, y + 4] + p[x + 2, y + 4] + p[x + 4, y + 4]
                     ) * gain_b;
            };
            Action FucD = () =>
            {
                r = (p[x + 0, y + 1] + p[x + 2, y + 1] + p[x + 4, y + 1]
                     + p[x + 0, y + 3] + p[x + 2, y + 3] + p[x + 4, y + 3]
                     + p[x + 0, y + 5] + p[x + 2, y + 5] + p[x + 4, y + 5]) * gain_r;

                g = (p[x + 0, y + 0] + p[x + 2, y + 0] + p[x + 4, y + 0]
                     + p[x + 1, y + 1] + p[x + 3, y + 1] + p[x + 5, y + 1]
                     + p[x + 0, y + 2] + p[x + 2, y + 2] + p[x + 4, y + 2]
                     + p[x + 1, y + 3] + p[x + 3, y + 3] + p[x + 5, y + 3]
                     + p[x + 0, y + 4] + p[x + 2, y + 4] + p[x + 4, y + 4]
                     + p[x + 1, y + 5] + p[x + 3, y + 5] + p[x + 5, y + 5]
                     ) * gain_g;

                b = (p[x + 1, y + 0] + p[x + 3, y + 0] + p[x + 5, y + 0]
                     + p[x + 1, y + 2] + p[x + 3, y + 2] + p[x + 5, y + 2]
                     + p[x + 1, y + 4] + p[x + 3, y + 4] + p[x + 5, y + 4]
                     ) * gain_b;
            };


            #endregion
            #region マトリックス
            Action FuncMatrix = () =>
            {
                double rr = r;
                double gg = g;
                double bb = b;
                r = matrix[0, 0] * rr + matrix[0, 1] * gg + matrix[0, 2] * bb;
                g = matrix[1, 0] * rr + matrix[1, 1] * gg + matrix[1, 2] * bb;
                b = matrix[2, 0] * rr + matrix[2, 1] * gg + matrix[2, 2] * bb;
            };
            #endregion
            #region ガンマ
            Action FuncGamma = () =>
            {
                r = 255 * Math.Pow(r, gamma);
                g = 255 * Math.Pow(g, gamma);
                b = 255 * Math.Pow(b, gamma);
            };
            #endregion
            #region 配列化
            int    col        = 0;
            Action FuncToByte = () =>
            {
                //int col = (y * w + x) * 3;
                buf[col + 2] = (byte)(r < 0 ? 0 : (255 < r ? 255 : r));
                buf[col + 1] = (byte)(g < 0 ? 0 : (255 < g ? 255 : g));
                buf[col + 0] = (byte)(b < 0 ? 0 : (255 < b ? 255 : b));
            };
            #endregion
            Action Func1 = FucA;
            Action Func2 = FucB;
            Action Func3 = FucC;
            Action Func4 = FucD;
            switch (bayer)
            {
            case 0:
                Func1 = FucA;
                Func2 = FucB;
                Func3 = FucC;
                Func4 = FucD;
                break;

            case 1:
                Func1 = FucB;
                Func2 = FucA;
                Func3 = FucD;
                Func4 = FucC;
                break;

            case 2:
                Func1 = FucC;
                Func2 = FucD;
                Func3 = FucA;
                Func4 = FucB;
                break;

            case 3:
                Func1 = FucD;
                Func2 = FucC;
                Func3 = FucB;
                Func4 = FucA;
                break;
            }


            col = 0;
            for (y = 0; y < h - 6; y++)
            {
                for (x = 0; x < w - 6; x++)
                {
                    Func1();
                    FuncMatrix();
                    FuncGamma();
                    FuncToByte();
                    col += 3;

                    x++;

                    Func2();
                    FuncMatrix();
                    FuncGamma();
                    FuncToByte();
                    col += 3;
                }
                col += (3 * 6);
                y++;

                for (x = 0; x < w - 6; x++)
                {
                    Func3();
                    FuncMatrix();
                    FuncGamma();
                    FuncToByte();
                    col += 3;

                    x++;

                    Func4();
                    FuncMatrix();
                    FuncGamma();
                    FuncToByte();
                    col += 3;
                }
                col += (3 * 6);
            }

            #endregion
            #region BMPにマーシャルコピー/アンロック
            for (int j = 0; j < h; ++j)
            {
                IntPtr dst_line = (IntPtr)((Int64)bmpdat.Scan0 + j * bmpdat.Stride);
                Marshal.Copy(buf, j * w * 3, dst_line, w * 3);
            }
            bit.UnlockBits(bmpdat);
            #endregion

            return(bit);
        }