static RgbToCieConverter()
        {
            var gamutA = new Gamut(new Point(0.704, 0.296), new Point(0.2151, 0.7106), new Point(0.138, 0.080));
            var gamutB = new Gamut(new Point(0.675, 0.322), new Point(0.4090, 0.5180), new Point(0.167, 0.040));
            var gamutC = new Gamut(new Point(0.692, 0.308), new Point(0.1700, 0.7000), new Point(0.153, 0.048));

            //http://www.developers.meethue.com/documentation/supported-lights
            _gamutAssignment = new Dictionary<string, Gamut>(StringComparer.OrdinalIgnoreCase)
            {
                {"LCT001", gamutB},
                {"LCT007", gamutB},
                {"LCT010", gamutC},
                {"LCT014", gamutC},
                {"LCT002", gamutB},
                {"LCT003", gamutB},
                {"LCT011", gamutC},
                {"LST001", gamutA},
                {"LLC010", gamutA},
                {"LLC011", gamutA},
                {"LLC012", gamutA},
                {"LLC006", gamutA},
                {"LLC007", gamutA},
                {"LLC013", gamutA},
                {"LLM001", gamutB},
                {"LLC020", gamutC},
                {"LST002", gamutC}
            };
        }
        private static Point GetCentroid(Gamut gamut)
        {
            var x = (gamut.Red.X + gamut.Green.X + gamut.Blue.X) / 3d;
            var y = (gamut.Red.Y + gamut.Green.Y + gamut.Blue.Y) / 3d;

            return(new Point(x, y));
        }
Exemple #3
0
        public double GetAverageY()
        {
            var imagePath = ImagePath;

            if (!File.Exists(imagePath))
            {
                throw new FileNotFoundException();
            }

            int core = ProcessingCore;

            using (var bitmap = new Bitmap(imagePath))
            {
                // 対象領域を分割
                int resolution = bitmap.Height / core;
                var rects      = new Rectangle[core];
                for (int i = 0; i < rects.Length - 1; i++)
                {
                    rects[i] = new Rectangle(0, resolution * i, bitmap.Width, resolution);
                }
                rects[core - 1] = new Rectangle(0, resolution * (core - 1), bitmap.Width, bitmap.Height - resolution * (core - 1));

                int bytesPerPixel = Image.GetPixelFormatSize(bitmap.PixelFormat) / 8;
                var bitmapData    = bitmap.LockBits(new Rectangle(0, 0, bitmap.Width, bitmap.Height), ImageLockMode.ReadOnly, bitmap.PixelFormat);

                var rgb = Task.WhenAll(rects.Select(async x =>
                                                    await ProcessUsingLockbitsAndUnsafe(bitmapData, bytesPerPixel, x))).Result;

                bitmap.UnlockBits(bitmapData);
                return(rgb.Select(x => Gamut.GetY(x.R, x.G, x.B)).Average());
            }
        }
        static RgbToCieConverter()
        {
            var gamutA = new Gamut(new Point(0.704, 0.296), new Point(0.2151, 0.7106), new Point(0.138, 0.080));
            var gamutB = new Gamut(new Point(0.675, 0.322), new Point(0.4090, 0.5180), new Point(0.167, 0.040));
            var gamutC = new Gamut(new Point(0.692, 0.308), new Point(0.1700, 0.7000), new Point(0.153, 0.048));

            //http://www.developers.meethue.com/documentation/supported-lights
            _gamutAssignment = new Dictionary <string, Gamut>(StringComparer.OrdinalIgnoreCase)
            {
                { "LCT001", gamutB },
                { "LCT007", gamutB },
                { "LCT010", gamutC },
                { "LCT014", gamutC },
                { "LCT002", gamutB },
                { "LCT003", gamutB },
                { "LCT011", gamutC },
                { "LST001", gamutA },
                { "LLC010", gamutA },
                { "LLC011", gamutA },
                { "LLC012", gamutA },
                { "LLC006", gamutA },
                { "LLC007", gamutA },
                { "LLC013", gamutA },
                { "LLM001", gamutB },
                { "LLC020", gamutC },
                { "LST002", gamutC }
            };
        }
        public double GetAverageY()
        {
            var path = ImagePath;

            using (Image <Rgba32> image = Image.Load(path))
            {
                var width  = image.Width;
                var height = image.Height;

                ulong sumR = 0, sumG = 0, sumB = 0;
                for (int y = 0; y < height; y++)
                {
                    foreach (var pixel in image.GetPixelRowSpan(y))
                    {
                        sumB += pixel.B;
                        sumG += pixel.G;
                        sumR += pixel.R;
                    }
                }
                var count = (double)(width * height);
                var aveR  = sumR / count;
                var aveG  = sumG / count;
                var aveB  = sumB / count;
                return(Gamut.GetY(R: aveR, G: aveG, B: aveB));
            }
        }
        public static RGBColour XYtoRGB(Point point, string model)
        {
            if (model != null)
            {
                Gamut gamut = Gamut.ForModel(model);
                point = gamut.NearestContainedPoint(point);
            }

            point = Gamut.PhilipsWideGamut.NearestContainedPoint(point);

            double Y = 1.0;
            double X = (Y / point.y) * point.x;
            double Z = (Y / point.y) * point.z;

            double r = X * 1.656492 - Y * 0.354851 - Z * 0.255038;
            double g = -X * 0.707196 + Y * 1.655397 + Z * 0.036152;
            double b = X * 0.051713 - Y * 0.121364 + Z * 1.011530;

            double maxComponent = Math.Max(Math.Max(r, g), b);

            if (maxComponent > 1.0)
            {
                r /= maxComponent;
                g /= maxComponent;
                b /= maxComponent;
            }

            r = Gamma(r);
            g = Gamma(g);
            b = Gamma(b);

            return(new RGBColour(r, g, b));
        }
        public static Point RgbToXY(RGBColour colour, string model)
        {
            double r = InverseGamma(colour.red);
            double g = InverseGamma(colour.green);
            double b = InverseGamma(colour.blue);

            double X = r * 0.664511f + g * 0.154324f + b * 0.162028f;
            double Y = r * 0.283881f + g * 0.668433f + b * 0.047685f;
            double Z = r * 0.000088f + g * 0.072310f + b * 0.986039f;

            Point xyPoint = new Point(0.0, 0.0);

            if ((X + Y + Z) > 0.0)
            {
                xyPoint = new Point(X / (X + Y + Z), Y / (X + Y + Z));
            }

            if (model != null)
            {
                Gamut gamut = Gamut.ForModel(model);

                return(gamut.NearestContainedPoint(xyPoint));
            }

            return(xyPoint);
        }
        private static IEnumerable <LineSegment> GetLineSegments(Gamut gamut)
        {
            yield return(new LineSegment(gamut.Red, gamut.Green));

            yield return(new LineSegment(gamut.Red, gamut.Blue));

            yield return(new LineSegment(gamut.Blue, gamut.Green));
        }
Exemple #9
0
        public double GetAverageY()
        {
            var imagePath = ImagePath;

            if (!File.Exists(imagePath))
            {
                throw new FileNotFoundException();
            }

            using (var bitmap = new Bitmap(imagePath))
            {
                var(R, G, B) = ProcessUsingLockbitsAndUnsafeAndParallel(bitmap);
                return(Gamut.GetY(R, G, B));
            }
        }
Exemple #10
0
        public double GetAverageY()
        {
            var imagePath = ImagePath;

            if (!File.Exists(imagePath))
            {
                throw new FileNotFoundException();
            }

            using (var bitmap = new Bitmap(imagePath))
            {
                var rect = new Rectangle(0, 0, bitmap.Width, bitmap.Height);
                var(R, G, B) = ProcessUsingLockbitsAndUnsafe(bitmap, ref rect);
                return(Gamut.GetY(R, G, B));
            }
        }
        // 指定領域の平均輝度の読み込み
        private static double GetAverageY(BitmapImage bmp, ref Int32Rect rect)
        {
            if (bmp is null)
            {
                throw new ArgumentNullException(nameof(bmp));
            }
            if (rect.Width * rect.Height == 0)
            {
                throw new ArgumentException("RectArea");
            }

            int pixelsByte  = (bmp.Format.BitsPerPixel + 7) / 8; // bit→Byte変換
            int imageWidth  = bmp.PixelWidth;
            int imageHeight = bmp.PixelHeight;
            int rectX       = rect.X;
            int rectY       = rect.Y;
            int rectArea    = rect.Width * rect.Height;

            // 範囲制限(とりあえずで幅/高さを保つ方針で実装してます)
            if (imageWidth < rectX + rect.Width)
            {
                rectX = imageWidth - rect.Width;
            }
            if (imageHeight < rectY + rect.Height)
            {
                rectY = imageHeight - rect.Height;
            }

            var pixels      = new byte[rectArea * pixelsByte];
            var bitmapImage = bmp as BitmapSource;

            if (rectX != 0 || rectY != 0 || rect.Width != imageWidth || rect.Height != imageHeight)
            {
                bitmapImage = new CroppedBitmap(bmp, new Int32Rect(rectX, rectY, rect.Width, rect.Height));
            }

            try
            {
                bitmapImage.CopyPixels(pixels, rect.Width * pixelsByte, 0);
            }
            catch (System.Runtime.InteropServices.COMException ex)
            {
                Trace.WriteLine(ex.Message);    // 謎たまに起きる
            }

            // 1画素(カーソル用)の計算
            if (rectArea == 1)
            {
                if (pixelsByte < 3)
                {
                    //return new Gamut1(pixels[0]);
                }
                else
                {
                    //return new Gamut1(pixels[0], pixels[1], pixels[2]);
                }
            }
            else
            {
                if (pixelsByte <= 1)
                {
                    //return new Gamut2(pixels, new Size(rectWidth, rectHeight), pixelsByte);
                }
                else
                {
                    var(R, G, B) = GetAverage(pixels, rect.Width, rect.Height, pixelsByte);
                    return(Gamut.GetY(R, G, B));
                }
            }
            return(0);
        }
 private static IEnumerable<LineSegment> GetLineSegments(Gamut gamut)
 {
     yield return new LineSegment(gamut.Red, gamut.Green);
     yield return new LineSegment(gamut.Red, gamut.Blue);
     yield return new LineSegment(gamut.Blue, gamut.Green);
 }
 private static Point GetCentroid(Gamut gamut)
 {
     var x = (gamut.Red.X + gamut.Green.X + gamut.Blue.X)/3d;
     var y = (gamut.Red.Y + gamut.Green.Y + gamut.Blue.Y)/3d;
     return new Point(x, y);
 }