/// <summary> /// Provides a configured LinearGradient that can be used in combination with a GradientImageSource to provide a mask for the LensBlurEffect. /// It will expect the LensBlur will be blurred with 1 kernel when the double is different from None. /// </summary> /// <param name="ellipse">The band that represents the focus area in the image. Pixels within this band won't be blurred. /// Areas outside of the area will be progressively more blurred as the distance from the focus band increases.</param> /// <param name="strength">Strength of the blur.</param> /// <returns>A LinearGradient that can be used in combination with a GradientImageSource to be used by LensBlur.</returns> public static RadialGradient GenerateGradient(FocusEllipse ellipse, KernelGenerator kernelGenerator) { if (kernelGenerator.GetKernelBands().Count == 0) { return(null); } EllipseRadius maxBlurRadius = null; if ((ellipse.Radius.X < minDiffBetweenStops) && (ellipse.Radius.Y < minDiffBetweenStops)) { maxBlurRadius = new EllipseRadius(minDiffBetweenStops, minDiffBetweenStops); } else { double factor = 0.9; bool widthGtHight = ellipse.Radius.X > ellipse.Radius.Y; if (widthGtHight) { maxBlurRadius = new EllipseRadius(factor, factor * ellipse.Radius.Y / ellipse.Radius.X); } else { maxBlurRadius = new EllipseRadius(factor * ellipse.Radius.X / ellipse.Radius.Y, factor); } } var gradient = new RadialGradient(ellipse.Center, maxBlurRadius); SetGradientStops(gradient, ellipse, maxBlurRadius, kernelGenerator); return(gradient); }
/// <summary> /// Provides a configured LinearGradient that can be used in combination with a GradientImageSource to provide a mask for the LensBlurEffect. /// It will expect the LensBlur will be blurred with 1 kernel when the double is different from None. /// </summary> /// <param name="ellipse">The band that represents the focus area in the image. Pixels within this band won't be blurred. /// Areas outside of the area will be progressively more blurred as the distance from the focus band increases.</param> /// <param name="strength">Strength of the blur.</param> /// <returns>A LinearGradient that can be used in combination with a GradientImageSource to be used by LensBlur.</returns> public static RadialGradient GenerateGradient(FocusEllipse ellipse, KernelGenerator kernelGenerator) { if (kernelGenerator.GetKernelBands().Count == 0) { return null; } EllipseRadius maxBlurRadius = null; if ((ellipse.Radius.X < minDiffBetweenStops) && (ellipse.Radius.Y < minDiffBetweenStops)) { maxBlurRadius = new EllipseRadius(minDiffBetweenStops, minDiffBetweenStops); } else { double factor = 0.9; bool widthGtHight = ellipse.Radius.X > ellipse.Radius.Y; if (widthGtHight) { maxBlurRadius = new EllipseRadius(factor, factor * ellipse.Radius.Y / ellipse.Radius.X); } else { maxBlurRadius = new EllipseRadius(factor * ellipse.Radius.X / ellipse.Radius.Y, factor); } } var gradient = new RadialGradient(ellipse.Center, maxBlurRadius); SetGradientStops(gradient, ellipse, maxBlurRadius, kernelGenerator); return gradient; }
private static void SetGradientStops(LinearGradient gradient, FocusBand focusBand, Size sourceSize, KernelGenerator edge1KernelGenerator, KernelGenerator edge2KernelGenerator, bool applySmallBlurFocusArea) { var blurArea1FirstOffset = GetOffset(gradient, focusBand.Edge1); var blurArea2FirstOffset = GetOffset(gradient, focusBand.Edge2); var focusBandEdge1Pixels = new Point(focusBand.Edge1.X * sourceSize.Width, focusBand.Edge1.Y * sourceSize.Height); var focusBandEdge2Pixels = new Point(focusBand.Edge2.X * sourceSize.Width, focusBand.Edge2.Y * sourceSize.Height); var focusBandWidth = Math.Abs(blurArea1FirstOffset - blurArea2FirstOffset); var focusBandWidthPixels = Distance(focusBandEdge1Pixels, focusBandEdge2Pixels); double blurAreaWidth; if (focusBandWidthPixels > 0) { var scaleFactor = focusBandWidth / focusBandWidthPixels; var blurAreaWidthPixels = (sourceSize.Height - focusBandWidthPixels) / 2 * 0.9; if (blurAreaWidthPixels < 1.0) { gradient.Stops = new[] { new GradientStop() { Offset = 0.5, Color = Color.FromArgb(255, 0, 0, 0) } }; return; } blurAreaWidth = blurAreaWidthPixels * scaleFactor; } else { blurAreaWidth = 0.5; applySmallBlurFocusArea = true; } double blurArea1LastOffset; double blurArea2LastOffset; if (blurArea1FirstOffset > blurArea2FirstOffset) { blurArea1LastOffset = blurArea1FirstOffset + blurAreaWidth; blurArea2LastOffset = blurArea2FirstOffset - blurAreaWidth; } else { blurArea1LastOffset = blurArea1FirstOffset - blurAreaWidth; blurArea2LastOffset = blurArea2FirstOffset + blurAreaWidth; } var stops1 = GetGradientStops(gradient, applySmallBlurFocusArea, edge1KernelGenerator, blurArea1FirstOffset, blurArea1LastOffset); var stops2 = GetGradientStops(gradient, applySmallBlurFocusArea, edge2KernelGenerator, blurArea2FirstOffset, blurArea2LastOffset, (byte)(edge1KernelGenerator.GetKernelBands().Count)); List<GradientStop> stops = new List<GradientStop>(); stops.AddRange(stops1); stops.AddRange(stops2); var validStops = EnsureMinDiffBetweenPoints(stops); gradient.Stops = validStops.ToArray(); }
/// <summary> /// Provides a configured LinearGradient that can be used in combination with a GradientImageSource to provide a mask for the LensBlurEffect. /// Generates a map for BlendEffect. /// </summary> /// <param name="band">The band that represents the focus area in the image. Pixels within this band won't be blurred. /// Areas outside of the area will be progressively more blurred as the distance from the focus band increases.</param> /// <param name="kernelSpanFromEdge1">Strength at Edge1.</param> /// <param name="kernelSpanFromEdge2">Strength at Edge2.</param> /// <returns>A LinearGradient that can be used in combination with a GradientImageSource to be used by LensBlur.</returns> public static LinearGradient GenerateGradient(FocusBand band, Size sourceSize, KernelGenerator edge1KernelGenerator, KernelGenerator edge2KernelGenerator, bool applySmallBlurFocusArea) { var gradient = new LinearGradient(); var lineFunction = GradientLine.CreateFunction(band); SetGradientPoints(gradient, lineFunction); SetGradientStops(gradient, band, sourceSize, edge1KernelGenerator, edge2KernelGenerator, applySmallBlurFocusArea); return gradient; }
private static void SetGradientStops(RadialGradient gradient, FocusEllipse ellipse, EllipseRadius maxBlurRadius, KernelGenerator kernelGenerator) { var stops = new List<GradientStop>(); double firstStopOffset; if (maxBlurRadius.X > minDiffBetweenStops) { firstStopOffset = ellipse.Radius.X / maxBlurRadius.X; //Add the focus area at the center of the ellipse. stops.Add(new GradientStop() { Color = Color.FromArgb(255, 0, 0, 0), Offset = 0 }); stops.Add(new GradientStop() { Color = Color.FromArgb(255, 0, 0, 0), Offset = firstStopOffset }); } else { firstStopOffset = minDiffBetweenStops; } double sumOfBandWidths = kernelGenerator.GetKernelBands().Select(band => band.Width).Sum(); var currentStopOffset = firstStopOffset + minDiffBetweenStops; var kernelBands = kernelGenerator.GetKernelBands(); byte kernelIndex = 0; foreach (var band in kernelBands) { kernelIndex++; stops.Add(new GradientStop() { Color = Color.FromArgb(255, kernelIndex, kernelIndex, kernelIndex), Offset = currentStopOffset }); currentStopOffset = currentStopOffset + (band.Width / sumOfBandWidths) * (1 - firstStopOffset) * FocusToBlurTransitionWidth; } stops.Add(new GradientStop() { Color = Color.FromArgb(255, kernelIndex, kernelIndex, kernelIndex), Offset = currentStopOffset }); var validStops = EnsureMinDiffBetweenPoints(stops); gradient.Stops = validStops.ToArray(); }
private static void SetGradientStops(LinearGradient gradient, FocusBand focusBand, Size sourceSize, KernelGenerator edge1KernelGenerator, KernelGenerator edge2KernelGenerator, bool applySmallBlurFocusArea) { var blurArea1FirstOffset = GetOffset(gradient, focusBand.Edge1); var blurArea2FirstOffset = GetOffset(gradient, focusBand.Edge2); var focusBandEdge1Pixels = new Point(focusBand.Edge1.X * sourceSize.Width, focusBand.Edge1.Y * sourceSize.Height); var focusBandEdge2Pixels = new Point(focusBand.Edge2.X * sourceSize.Width, focusBand.Edge2.Y * sourceSize.Height); var focusBandWidth = Math.Abs(blurArea1FirstOffset - blurArea2FirstOffset); var focusBandWidthPixels = Distance(focusBandEdge1Pixels, focusBandEdge2Pixels); double blurAreaWidth; if (focusBandWidthPixels > 0) { var scaleFactor = focusBandWidth / focusBandWidthPixels; var blurAreaWidthPixels = (sourceSize.Height - focusBandWidthPixels) / 2 * 0.9; if (blurAreaWidthPixels < 1.0) { gradient.Stops = new[] { new GradientStop() { Offset = 0.5, Color = Color.FromArgb(255, 0, 0, 0) } }; return; } blurAreaWidth = blurAreaWidthPixels * scaleFactor; } else { blurAreaWidth = 0.5; applySmallBlurFocusArea = true; } double blurArea1LastOffset; double blurArea2LastOffset; if (blurArea1FirstOffset > blurArea2FirstOffset) { blurArea1LastOffset = blurArea1FirstOffset + blurAreaWidth; blurArea2LastOffset = blurArea2FirstOffset - blurAreaWidth; } else { blurArea1LastOffset = blurArea1FirstOffset - blurAreaWidth; blurArea2LastOffset = blurArea2FirstOffset + blurAreaWidth; } var stops1 = GetGradientStops(gradient, applySmallBlurFocusArea, edge1KernelGenerator, blurArea1FirstOffset, blurArea1LastOffset); var stops2 = GetGradientStops(gradient, applySmallBlurFocusArea, edge2KernelGenerator, blurArea2FirstOffset, blurArea2LastOffset, (byte)(edge1KernelGenerator.GetKernelBands().Count)); List <GradientStop> stops = new List <GradientStop>(); stops.AddRange(stops1); stops.AddRange(stops2); var validStops = EnsureMinDiffBetweenPoints(stops); gradient.Stops = validStops.ToArray(); }
/// <summary> /// Provides a configured LinearGradient that can be used in combination with a GradientImageSource to provide a mask for the LensBlurEffect. /// Generates a map for BlendEffect. /// </summary> /// <param name="band">The band that represents the focus area in the image. Pixels within this band won't be blurred. /// Areas outside of the area will be progressively more blurred as the distance from the focus band increases.</param> /// <param name="kernelSpanFromEdge1">Strength at Edge1.</param> /// <param name="kernelSpanFromEdge2">Strength at Edge2.</param> /// <returns>A LinearGradient that can be used in combination with a GradientImageSource to be used by LensBlur.</returns> public static LinearGradient GenerateGradient(FocusBand band, Size sourceSize, KernelGenerator edge1KernelGenerator, KernelGenerator edge2KernelGenerator, bool applySmallBlurFocusArea) { var gradient = new LinearGradient(); var lineFunction = GradientLine.CreateFunction(band); SetGradientPoints(gradient, lineFunction); SetGradientStops(gradient, band, sourceSize, edge1KernelGenerator, edge2KernelGenerator, applySmallBlurFocusArea); return(gradient); }
private static List <GradientStop> GetGradientStops(LinearGradient gradient, bool applySmallBlurFocusArea, KernelGenerator kernelGenerator, double firstStopOffset, double lastStopOffset, byte firstKernelIndex = 0) { var stops = new List <GradientStop>(); if (kernelGenerator.GetKernelBands().Count > 0) { double sumOfBandWidths = kernelGenerator.GetKernelBands().Select(band => band.Width).Sum(); var focusAreaColor = GetFocusAreaColor(applySmallBlurFocusArea); stops.Add(new GradientStop() { Color = Color.FromArgb(255, focusAreaColor, focusAreaColor, focusAreaColor), Offset = firstStopOffset }); var currentStopOffset = lastStopOffset - firstStopOffset > 0 ? firstStopOffset + minDiffBetweenStops : firstStopOffset - minDiffBetweenStops; var kernelBands = kernelGenerator.GetKernelBands(); byte kernelIndex = firstKernelIndex; foreach (var band in kernelBands) { kernelIndex++; stops.Add(new GradientStop() { Color = Color.FromArgb(255, kernelIndex, kernelIndex, kernelIndex), Offset = currentStopOffset }); currentStopOffset = currentStopOffset + (band.Width / sumOfBandWidths) * (lastStopOffset - firstStopOffset) * FocusToBlurTransitionWidth; } stops.Add(new GradientStop() { Color = Color.FromArgb(255, kernelIndex, kernelIndex, kernelIndex), Offset = currentStopOffset }); stops = EnsureMinDiffBetweenPoints(stops); } return(stops); }
private static void SetGradientStops(RadialGradient gradient, FocusEllipse ellipse, EllipseRadius maxBlurRadius, KernelGenerator kernelGenerator) { var stops = new List <GradientStop>(); double firstStopOffset; if (maxBlurRadius.X > minDiffBetweenStops) { firstStopOffset = ellipse.Radius.X / maxBlurRadius.X; //Add the focus area at the center of the ellipse. stops.Add(new GradientStop() { Color = Color.FromArgb(255, 0, 0, 0), Offset = 0 }); stops.Add(new GradientStop() { Color = Color.FromArgb(255, 0, 0, 0), Offset = firstStopOffset }); } else { firstStopOffset = minDiffBetweenStops; } double sumOfBandWidths = kernelGenerator.GetKernelBands().Select(band => band.Width).Sum(); var currentStopOffset = firstStopOffset + minDiffBetweenStops; var kernelBands = kernelGenerator.GetKernelBands(); byte kernelIndex = 0; foreach (var band in kernelBands) { kernelIndex++; stops.Add(new GradientStop() { Color = Color.FromArgb(255, kernelIndex, kernelIndex, kernelIndex), Offset = currentStopOffset }); currentStopOffset = currentStopOffset + (band.Width / sumOfBandWidths) * (1 - firstStopOffset) * FocusToBlurTransitionWidth; } stops.Add(new GradientStop() { Color = Color.FromArgb(255, kernelIndex, kernelIndex, kernelIndex), Offset = currentStopOffset }); var validStops = EnsureMinDiffBetweenPoints(stops); gradient.Stops = validStops.ToArray(); }
private static List<GradientStop> GetGradientStops(LinearGradient gradient, bool applySmallBlurFocusArea, KernelGenerator kernelGenerator, double firstStopOffset, double lastStopOffset, byte firstKernelIndex = 0) { var stops = new List<GradientStop>(); if (kernelGenerator.GetKernelBands().Count > 0) { double sumOfBandWidths = kernelGenerator.GetKernelBands().Select(band => band.Width).Sum(); var focusAreaColor = GetFocusAreaColor(applySmallBlurFocusArea); stops.Add(new GradientStop() { Color = Color.FromArgb(255, focusAreaColor, focusAreaColor, focusAreaColor), Offset = firstStopOffset }); var currentStopOffset = lastStopOffset - firstStopOffset > 0 ? firstStopOffset + minDiffBetweenStops : firstStopOffset - minDiffBetweenStops; var kernelBands = kernelGenerator.GetKernelBands(); byte kernelIndex = firstKernelIndex; foreach (var band in kernelBands) { kernelIndex++; stops.Add(new GradientStop() { Color = Color.FromArgb(255, kernelIndex, kernelIndex, kernelIndex), Offset = currentStopOffset }); currentStopOffset = currentStopOffset + (band.Width / sumOfBandWidths) * (lastStopOffset - firstStopOffset) * FocusToBlurTransitionWidth; } stops.Add(new GradientStop() { Color = Color.FromArgb(255, kernelIndex, kernelIndex, kernelIndex), Offset = currentStopOffset }); stops = EnsureMinDiffBetweenPoints(stops); } return stops; }