public override ProcessResult Execute(ProcessExecutionParams p) { GrayscaleProcessor gp = new GrayscaleProcessor(new Bitmap(p.Bitmap), RgbToGrayscaleConversion.None); BitmapProcessor bp = new BitmapProcessor(p.Bitmap.Clone() as Bitmap); for (int dy = 0; dy < gp.Height; dy++) { for (int dx = 0; dx < gp.Width; dx++) { int pixel = (int)bp.GetPixel(dx, dy); int r = (pixel & 0x00ff0000) >> 16; int g = (pixel & 0x0000ff00) >> 08; int b = (pixel & 0x000000ff) >> 00; int max = Math.Max(Math.Max(r, g), b); int min = Math.Min(Math.Min(r, g), b); int range = max - min; int level = (r + g + b) / 3; int val = level - range; if (val > 255) { val = 255; } if (val < 0) { val = 0; } gp.SetPixel(dx, dy, (UInt32)level); } } GrayscaleProcessor gpSobel = (GrayscaleProcessor)gp.Clone(); new SobelEdgeDetector().Execute(gpSobel); ObjectLayer l1stLevel = Execute1stLevelSegmentation(gp, gpSobel); ObjectLayer l2ndLevel = Execute2ndLevelSegmentation(l1stLevel, gp); gpSobel.WriteBack = false; gp.WriteBack = false; gpSobel.Dispose(); gp.Dispose(); bp.Dispose(); gpSobel.Bitmap.Dispose(); gp.Bitmap.Dispose(); bp.Bitmap.Dispose(); l1stLevel.Name = "1st Level"; l2ndLevel.Name = "2nd Level"; return(new ProcessResult(new ObjectLayer[] { l1stLevel, l2ndLevel })); }