public static void Process(this IDirectBitmap bitmap, int radius) { using (var original = (IDirectBitmap) bitmap.Clone()) { Parallel.ForEach(Enumerable.Range(0, bitmap.Height), new ParallelOptions {MaxDegreeOfParallelism = Environment.ProcessorCount}, y => { var random = new Random(y); for (var x = 0; x < bitmap.Width; x++) { int x1 = DirectBitmapExtensionBase.NormalizeBounds( (int) (x + (random.Next(1000) / 1000.0 - 0.5) * radius), 0, bitmap.Width); int y1 = DirectBitmapExtensionBase.NormalizeBounds( (int) (y + (random.Next(1000) / 1000.0 - 0.5) * radius), 0, bitmap.Height); var c = original.GetPixel(x, y); bitmap.SetPixel(x1, y1, c); } }); } }
public static void ApplyConvolutionFilter(IDirectBitmap bitmap, Kernel ker) { using (var original = (IDirectBitmap)bitmap.Clone()) { Parallel.ForEach(Enumerable.Range(0, bitmap.Height), new ParallelOptions { MaxDegreeOfParallelism = Environment.ProcessorCount }, y => { for (var x = 0; x < bitmap.Width; x++) { var rsum = 0.0; var gsum = 0.0; var bsum = 0.0; for (var l = 0; l < ker.Width; l++) { for (var k = 0; k < ker.Height; k++) { var n = NormalizeBounds(x - (l - ker.Width / 2), 0, bitmap.Width); var m = NormalizeBounds(y - (k - ker.Height / 2), 0, bitmap.Height); var p = original.GetPixel(n, m); rsum += ker.Get(k, l) * p.R; gsum += ker.Get(k, l) * p.G; bsum += ker.Get(k, l) * p.B; } } var r = ColorRange((int)rsum); var g = ColorRange((int)gsum); var b = ColorRange((int)bsum); bitmap.SetPixel(x, y, Color.FromArgb(r, g, b)); } }); } }
public static void ApplyConvolutionFilter(IDirectBitmap bitmap, Kernel kerX, Kernel kerY) { using (var original = (IDirectBitmap)bitmap.Clone()) { Parallel.ForEach(Enumerable.Range(0, bitmap.Height), new ParallelOptions { MaxDegreeOfParallelism = Environment.ProcessorCount }, y => { for (var x = 0; x < bitmap.Width; x++) { double rx = 0.0, gx = 0.0, bx = 0.0; double ry = 0.0, gy = 0.0, by = 0.0; for (var l = 0; l < kerX.Width; l++) { for (var k = 0; k < kerX.Height; k++) { var n = NormalizeBounds(x - (l - kerX.Width / 2), 0, bitmap.Width); var m = NormalizeBounds(y - (k - kerX.Height / 2), 0, bitmap.Height); if (original != null) { var p = original.GetPixel(n, m); rx += kerX.Get(k, l) * p.R; bx += kerX.Get(k, l) * p.G; gx += kerX.Get(k, l) * p.B; ry += kerY.Get(k, l) * p.R; @by += kerY.Get(k, l) * p.G; gy += kerY.Get(k, l) * p.B; } } } var bsum = Math.Sqrt(bx * bx + @by * @by); var gsum = Math.Sqrt(gx * gx + gy * gy); var rsum = Math.Sqrt(rx * rx + ry * ry); var r = ColorRange((int)rsum); var g = ColorRange((int)gsum); var b = ColorRange((int)bsum); bitmap.SetPixel(x, y, Color.FromArgb(r, g, b)); } }); } }
public static void ProcessRotation(this IDirectBitmap bitmap, double angle) { angle *= -Math.PI / 180.0; var cos = Math.Cos(angle); var sin = Math.Sin(angle); var point1X = (-bitmap.Height * sin); var point1Y = (bitmap.Height * cos); var point2X = (bitmap.Width * cos - bitmap.Height * sin); var point2Y = (bitmap.Height * cos + bitmap.Width * sin); var point3X = (bitmap.Width * cos); var point3Y = (bitmap.Width * sin); var minx = Math.Min(0, Math.Min(point1X, Math.Min(point2X, point3X))); var miny = Math.Min(0, Math.Min(point1Y, Math.Min(point2Y, point3Y))); var maxx = Math.Max(0, Math.Max(point1X, Math.Max(point2X, point3X))); var maxy = Math.Max(0, Math.Max(point1Y, Math.Max(point2Y, point3Y))); var destBitmapWidth = (int)Math.Ceiling(Math.Abs(maxx) - minx + 1); var destBitmapHeight = (int)Math.Ceiling(Math.Abs(maxy) - miny + 1); using (var original = (IDirectBitmap)bitmap.Clone()) { bitmap.Resize(destBitmapWidth, destBitmapHeight); Parallel.ForEach(Enumerable.Range(0, bitmap.Height), new ParallelOptions { MaxDegreeOfParallelism = Environment.ProcessorCount }, y => { for (var x = 0; x < bitmap.Width; x++) { var oldX = ((x + minx) * cos + (y + miny) * sin); var oldY = ((y + miny) * cos - (x + minx) * sin); var checkRange = oldY >= 0 && oldY < original.Height && oldX >= 0 && oldX < original.Width; var c = checkRange ? original.BilinearInterpolaton(oldX, oldY) : Color.FromArgb(0, 0, 0); bitmap.SetPixel(x, y, c); } }); } }
public static void ProcessScale(this IDirectBitmap bitmap, double scale) { using (var original = (IDirectBitmap)bitmap.Clone()) { var newWidth = (int)(bitmap.Width * scale); var newHeight = (int)(bitmap.Height * scale); bitmap.Resize(newWidth, newHeight); Parallel.For(0, bitmap.Height - 1, new ParallelOptions { MaxDegreeOfParallelism = Environment.ProcessorCount }, y => { for (var x = 0; x < bitmap.Width; x++) { var oldX = x / scale; var oldY = y / scale; var c = original.BilinearInterpolaton(oldX, oldY); bitmap.SetPixel(x, y, c); } }); } }
public static void ProcessMedianFilter(this IDirectBitmap bitmap, int radius) { var d = 2 * radius + 1; var r = d / 2; using (var original = (IDirectBitmap)bitmap.Clone()) { Parallel.ForEach(Enumerable.Range(0, bitmap.Height), new ParallelOptions { MaxDegreeOfParallelism = Environment.ProcessorCount }, y => { var red = new byte[d * d]; var green = new byte[d * d]; var blue = new byte[d * d]; for (var x = 0; x < bitmap.Width; x++) { var p = 0; for (var i = 0; i < d; i++) { for (var j = 0; j < d; j++) { var xc = NormalizeBounds(x + (i - r), 0, bitmap.Width); var yc = NormalizeBounds(y + (j - r), 0, bitmap.Height); var c = original.GetPixel(xc, yc); red[p] = c.R; green[p] = c.G; blue[p] = c.B; p++; } } var rMed = red.OrderBy(e => e).ElementAt(p / 2); var gMed = green.OrderBy(e => e).ElementAt(p / 2); var bMed = blue.OrderBy(e => e).ElementAt(p / 2); bitmap.SetPixel(x, y, Color.FromArgb(rMed, gMed, bMed)); } }); } }