void initializeDevice() { try { _selectedDevice = comboBoxDevices.SelectedItem as ClooDevice; if (_context != null) { _startProcessing = false; // dispose previous context _context.Dispose(); _kernels = null; _context = null; _sampler = null; _queue = null; image2.Source = null; image3.Source = null; image4.Source = null; } if (_selectedDevice != null) { // create context _context = _selectedDevice.CreateContext(); _queue = _context.CreateCommandQueue(); _sampler = new ClooSampler(_context, false, ComputeImageAddressing.ClampToEdge, ComputeImageFiltering.Linear); _kernels = ClooProgramViolaJones.Create(_context); _haarObjectDetector = ClooHaarObjectDetector.CreateFaceDetector(_context, _queue, 640, 480); _haarObjectDetector.ScalingFactor = 1.25f; _haarObjectDetector.ScalingMode = ScalingMode.SmallerToLarger; _haarObjectDetector.MinSize = new System.Drawing.Size(30, 30); _haarObjectDetector.MaxSize = new System.Drawing.Size(100, 100); Stopwatch stopwatch = new Stopwatch(); stopwatch.Reset(); stopwatch.Start(); _histogram = new ClooBuffer<uint>(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.AllocateHostPointer, 32 * 32 * 32); _histogram2 = new ClooBuffer<uint>(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.AllocateHostPointer, 32 * 32 * 32); _clooImageByteOriginal = ClooImage2DByteRgbA.CreateFromBitmap(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.UseHostPointer, _bitmapImage1); _clooImageByteOriginal.WriteToDevice(_queue); _clooImageByteGrayOriginal = ClooImage2DByteA.CreateFromBitmap(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.UseHostPointer, _bitmapImage1); _clooImageByteGrayOriginal.WriteToDevice(_queue); _clooImageByteResult = ClooImage2DByteRgbA.Create(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.UseHostPointer, _bitmapImage1.Width, _bitmapImage1.Height); _clooImageByteResultA = ClooImage2DByteA.Create(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.UseHostPointer, _bitmapImage1.Width, _bitmapImage1.Height); _clooImageFloatOriginal = ClooImage2DFloatRgbA.Create(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.UseHostPointer, _bitmapImage1.Width, _bitmapImage1.Height); _clooImageFloatGrayOriginal = ClooImage2DFloatA.Create(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.UseHostPointer, _bitmapImage1.Width, _bitmapImage1.Height); _clooImageFloatTemp1 = ClooImage2DFloatRgbA.Create(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.UseHostPointer, _bitmapImage1.Width, _bitmapImage1.Height); _clooImageFloatTemp2 = ClooImage2DFloatRgbA.Create(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.UseHostPointer, _bitmapImage1.Width, _bitmapImage1.Height); _clooImageFloatATemp1 = ClooImage2DFloatA.Create(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.UseHostPointer, _bitmapImage1.Width, _bitmapImage1.Height); _clooImageFloatATemp2 = ClooImage2DFloatA.Create(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.UseHostPointer, _bitmapImage1.Width, _bitmapImage1.Height); _clooImageFloatIntegral = ClooImage2DFloatA.Create(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.UseHostPointer, _bitmapImage1.Width + 1, _bitmapImage1.Height + 1); _clooImageUIntIntegral = ClooImage2DUIntA.Create(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.UseHostPointer, _bitmapImage1.Width + 1, _bitmapImage1.Height + 1); _clooImageUIntIntegralSquare = ClooImage2DUIntA.Create(_context, ComputeMemoryFlags.ReadWrite | ComputeMemoryFlags.UseHostPointer, _bitmapImage1.Width + 1, _bitmapImage1.Height + 1); _queue.Finish(); label1.Content = stopwatch.ElapsedMilliseconds + " ms - original " + _bitmapImage1.Width + "x" + _bitmapImage1.Height; _startProcessing = true; Update(); Update(); } } catch (Exception ex) { // show exception MessageBox.Show(ex.Message, ex.GetType().ToString(), MessageBoxButton.OK, MessageBoxImage.Stop); } }
/// <summary> /// Denormalize float image /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="image">image</param> public void Denormalize(ClooCommandQueue queue, ClooImage2DFloatRgbA image) { Denormalize(queue, image, image); }
/// <summary> /// Calculates the difference between two images (e.g. for background subtraction) /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="source">image source</param> /// <param name="dest">image destination</param> public void Diff(ClooCommandQueue queue, ClooImage2DFloatRgbA source1, ClooImage2DFloatRgbA source2, ClooImage2DFloatA dest) { if (queue == null) throw new ArgumentNullException("queue"); if (source1 == null) throw new ArgumentNullException("source1"); if (source2 == null) throw new ArgumentNullException("source2"); if (dest == null) throw new ArgumentNullException("dest"); if ((source2.Width > source1.Width) || (source2.Height > source1.Height)) throw new ArgumentException("Second image (" + dest.Width + "x" + dest.Height + ") must have at least the same size as the first image (" + source1.Width + "x" + source1.Height + ")"); if ((source1.Width > dest.Width) || (source1.Height > dest.Height)) throw new ArgumentException("Destination image (" + dest.Width + "x" + dest.Height + ") must have at least the same size as the source image (" + source1.Width + "x" + source1.Height + ")"); KernelImageFloatDiff.SetArguments(source1, source2, dest); queue.Execute(KernelImageFloatDiff, null, new long[] { source2.Width, source2.Height }, null, null); dest.Modified = true; dest.Normalized = false; }
/// <summary> /// Clamps minimum and maximum value /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="image">image</param> /// <param name="minValue">minimum value</param> /// <param name="maxValue">maximum value</param> public void Clamp(ClooCommandQueue queue, ClooImage2DFloatRgbA image, float minValue, float maxValue) { Clamp(queue, image, image, minValue, maxValue); }
/// <summary> /// Denormalize float image /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="source">image source</param> /// <param name="dest">image destination</param> public void Denormalize(ClooCommandQueue queue, ClooImage2DFloatRgbA source, ClooImage2DFloatRgbA dest) { if (queue == null) throw new ArgumentNullException("queue"); if (source == null) throw new ArgumentNullException("source"); if (dest == null) throw new ArgumentNullException("dest"); if ((source.Width > dest.Width) || (source.Height > dest.Height)) throw new ArgumentException("Destination image (" + dest.Width + "x" + dest.Height + ") must have at least the same size as the source image (" + source.Width + "x" + source.Height + ")"); KernelImageFloatMultiplyValue.SetArguments(source, dest, 255f); queue.Execute(KernelImageFloatMultiplyValue, null, new long[] { source.Width, source.Height }, null, null); dest.Modified = true; dest.Normalized = false; }
/// <summary> /// Adds a constant value to all float values in an image /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="image">image</param> /// <param name="value">value to add</param> public void AddValue(ClooCommandQueue queue, ClooImage2DFloatRgbA image, float value) { AddValue(queue, image, image, value); }
/// <summary> /// Box blur image /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="source">image source</param> /// <param name="dest">image destination</param> /// <param name="sampler">sampler to be used for image reading</param> /// <param name="offset">offset</param> public void BoxBlur(ClooCommandQueue queue, ClooImage2DFloatRgbA source, ClooImage2DFloatRgbA dest, ClooSampler sampler, int offset) { if (queue == null) throw new ArgumentNullException("queue"); if (source == null) throw new ArgumentNullException("source"); if (dest == null) throw new ArgumentNullException("dest"); if ((source.Width > dest.Width) || (source.Height > dest.Height)) throw new ArgumentException("Destination image (" + dest.Width + "x" + dest.Height + ") must have at least the same size as the source image (" + source.Width + "x" + source.Height + ")"); KernelImageFloatBoxBlur.SetArguments(source, dest, sampler, offset); queue.Execute(KernelImageFloatBoxBlur, null, new long[] { source.Width, source.Height }, null, null); dest.Modified = true; dest.Normalized = source.Normalized; }
/// <summary> /// Swaps two channels in an image /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="source">source image</param> /// <param name="dest">destination image</param> /// <param name="offsetFrom">first channel offset (0..3)</param> /// <param name="offsetTo">second channel offset (0..3)</param> public void SwapChannel(ClooCommandQueue queue, ClooImage2DFloatRgbA source, ClooImage2DFloatRgbA dest, byte offsetFrom, byte offsetTo) { if (queue == null) throw new ArgumentNullException("queue"); if (source == null) throw new ArgumentNullException("source"); if (dest == null) throw new ArgumentNullException("dest"); if (offsetFrom > 3) throw new ArgumentOutOfRangeException("offsetFrom", String.Format("offset must be between 0..3 but was {0}", offsetFrom)); if (offsetTo > 3) throw new ArgumentOutOfRangeException("offsetTo", String.Format("offset must be between 0..3 but was {0}", offsetTo)); if ((source.Width > dest.Width) || (source.Height > dest.Height)) throw new ArgumentException("Destination image (" + dest.Width + "x" + dest.Height + ") must have at least the same size as the source image (" + source.Width + "x" + source.Height + ")"); KernelImageFloatSwapChannel.SetArguments(source, dest, offsetFrom, offsetTo); queue.Execute(KernelImageFloatSwapChannel, null, new long[] { source.Width, source.Height }, null, null); dest.Modified = true; dest.Normalized = source.Normalized; }
/// <summary> /// Makes all values absolute /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="source">image</param> public void Abs(ClooCommandQueue queue, ClooImage2DFloatRgbA image) { Abs(queue, image, image); }
/// <summary> /// Sets channel of a RGBA image /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="image">image</param> /// <param name="mask">mask image</param> /// <param name="offset">offset (0..3)</param> /// <param name="value">constant mask value</param> public void SetChannel(ClooCommandQueue queue, ClooImage2DFloatRgbA image, byte offset, byte value) { SetChannel(queue, image, image, offset, value); }
/// <summary> /// Sets a constant value to all float values in an image /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="image">image</param> /// <param name="value">value to set</param> public void SetValue(ClooCommandQueue queue, ClooImage2DFloatRgbA image, float value) { if (queue == null) throw new ArgumentNullException("queue"); if (image == null) throw new ArgumentNullException("image"); KernelImageFloatSetValue.SetArguments(image, value); queue.Execute(KernelImageFloatSetValue, null, new long[] { image.Width, image.Height }, null, null); image.Modified = true; }
/// <summary> /// Sets channel of a RGBA image /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="image">image</param> /// <param name="mask">mask image</param> /// <param name="offset">offset (0..3)</param> public void SetChannel(ClooCommandQueue queue, ClooImage2DFloatRgbA image, ClooImage2DFloatA mask, byte offset) { SetChannel(queue, image, mask, image, offset); }
/// <summary> /// RGB to HSL image /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="source">image source</param> /// <param name="dest">image destination</param> public void RgbToHsl(ClooCommandQueue queue, ClooImage2DFloatRgbA source, ClooImage2DFloatRgbA dest) { if (queue == null) throw new ArgumentNullException("queue"); if (source == null) throw new ArgumentNullException("source"); if (dest == null) throw new ArgumentNullException("dest"); if ((source.Width > dest.Width) || (source.Height > dest.Height)) throw new ArgumentException("Destination image (" + dest.Width + "x" + dest.Height + ") must have at least the same size as the source image (" + source.Width + "x" + source.Height + ")"); if (source.Normalized) { // use normalized kernel KernelImageFloatRgbToHslNorm.SetArguments(source, dest); queue.Execute(KernelImageFloatRgbToHslNorm, null, new long[] { source.Width, source.Height }, null, null); } else { // use normal kernel KernelImageFloatRgbToHsl.SetArguments(source, dest); queue.Execute(KernelImageFloatRgbToHsl, null, new long[] { source.Width, source.Height }, null, null); } dest.Modified = true; dest.Normalized = source.Normalized; }
/// <summary> /// Multiplies a constant value to all float values in an image /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="image">image</param> /// <param name="factor">factor to multiply</param> public void MultiplyValue(ClooCommandQueue queue, ClooImage2DFloatRgbA image, float factor) { MultiplyValue(queue, image, image, factor); }
/// <summary> /// Create histogram backprojection for RGB float image /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="source">image source</param> /// <param name="dest">image destination (for propability map)</param> /// <param name="srcHistogram">source histogram uint buffer (must be at least bins^3 in length)</param> /// <param name="frameHistogram">frame histogram uint buffer (must be at least bins^3 in length)</param> /// <param name="bins">number of bins</param> /// <param name="startX">start from X coordinate</param> /// <param name="startY">start from Y coordinate</param> /// <param name="width">width</param> /// <param name="height">height</param> public void HistogramBackprojection(ClooCommandQueue queue, ClooImage2DByteRgbA source, ClooImage2DFloatRgbA dest, ClooBuffer<uint> srcHistogram, ClooBuffer<uint> frameHistogram, byte bins, int startX = 0, int startY = 0, int width = 0, int height = 0) { if (queue == null) throw new ArgumentNullException("queue"); if (source == null) throw new ArgumentNullException("source"); if (dest == null) throw new ArgumentNullException("dest"); if (srcHistogram == null) throw new ArgumentNullException("srcHistogram"); if (frameHistogram == null) throw new ArgumentNullException("frameHistogram"); if (bins < 2) throw new ArgumentException("bins must be at least 2", "bins"); int length = bins * bins * bins; if (srcHistogram.Count < length) throw new ArgumentException("Buffer length for histogram must be at least " + length, "srcHistogram"); if (frameHistogram.Count < length) throw new ArgumentException("Buffer length for histogram must be at least " + length, "frameHistogram"); if (width == 0) width = source.Width - startX; if (height == 0) height = source.Height - startY; if (width < 0) throw new ArgumentOutOfRangeException("width"); if (height < 0) throw new ArgumentOutOfRangeException("height"); KernelImageByteRgbHistogramFloatBP.SetArguments(source, dest, srcHistogram, frameHistogram, bins, (uint)startX, (uint)startY); queue.Execute(KernelImageByteRgbHistogramFloatBP, null, new long[] { width, height }, null, null); dest.Modified = true; dest.Normalized = true; }
/// <summary> /// Flip image Y coordinate /// </summary> /// <param name="queue">cloo command queue</param> /// <param name="source">image source</param> /// <param name="dest">image destination</param> public void FlipY(ClooCommandQueue queue, ClooImage2DFloatRgbA source, ClooImage2DFloatRgbA dest) { if (queue == null) throw new ArgumentNullException("queue"); if (source == null) throw new ArgumentNullException("source"); if (dest == null) throw new ArgumentNullException("dest"); if (source == dest) throw new ArgumentException("Flipping kernel is not designed to run inline therefore source and destination must be different images"); if ((source.Width > dest.Width) || (source.Height > dest.Height)) throw new ArgumentException("Destination image (" + dest.Width + "x" + dest.Height + ") must have at least the same size as the source image (" + source.Width + "x" + source.Height + ")"); KernelImageFloatFlipY.SetArguments(source, dest); queue.Execute(KernelImageFloatFlipY, null, new long[] { source.Width, source.Height }, null, null); dest.Modified = true; dest.Normalized = source.Normalized; }