diff --git a/src/ImageSharp/Processing/Effects/Brightness.cs b/src/ImageSharp/Processing/ColorMatrix/Brightness.cs similarity index 62% rename from src/ImageSharp/Processing/Effects/Brightness.cs rename to src/ImageSharp/Processing/ColorMatrix/Brightness.cs index 5c7628785..34b534784 100644 --- a/src/ImageSharp/Processing/Effects/Brightness.cs +++ b/src/ImageSharp/Processing/ColorMatrix/Brightness.cs @@ -16,25 +16,33 @@ namespace SixLabors.ImageSharp /// /// Alters the brightness component of the image. /// + /// + /// A value of 0 will create an image that is completely black. A value of 1 leaves the input unchanged. + /// Other values are linear multipliers on the effect. Values of an amount over 1 are allowed, providing brighter results. + /// /// The pixel format. /// The image this method extends. - /// The new brightness of the image. Must be between -100 and 100. + /// The proportion of the conversion. Must be greater than or equal to 0. /// The . - public static IImageProcessingContext Brightness(this IImageProcessingContext source, int amount) + public static IImageProcessingContext Brightness(this IImageProcessingContext source, float amount) where TPixel : struct, IPixel => source.ApplyProcessor(new BrightnessProcessor(amount)); /// /// Alters the brightness component of the image. /// + /// + /// A value of 0 will create an image that is completely black. A value of 1 leaves the input unchanged. + /// Other values are linear multipliers on the effect. Values of an amount over 1 are allowed, providing brighter results. + /// /// The pixel format. /// The image this method extends. - /// The new brightness of the image. Must be between -100 and 100. + /// The proportion of the conversion. Must be greater than or equal to 0. /// /// The structure that specifies the portion of the image object to alter. /// /// The . - public static IImageProcessingContext Brightness(this IImageProcessingContext source, int amount, Rectangle rectangle) + public static IImageProcessingContext Brightness(this IImageProcessingContext source, float amount, Rectangle rectangle) where TPixel : struct, IPixel => source.ApplyProcessor(new BrightnessProcessor(amount), rectangle); } diff --git a/src/ImageSharp/Processing/Effects/Contrast.cs b/src/ImageSharp/Processing/ColorMatrix/Contrast.cs similarity index 61% rename from src/ImageSharp/Processing/Effects/Contrast.cs rename to src/ImageSharp/Processing/ColorMatrix/Contrast.cs index 562ab54df..e0f388e28 100644 --- a/src/ImageSharp/Processing/Effects/Contrast.cs +++ b/src/ImageSharp/Processing/ColorMatrix/Contrast.cs @@ -1,7 +1,6 @@ // Copyright (c) Six Labors and contributors. // Licensed under the Apache License, Version 2.0. -using System; using SixLabors.ImageSharp.PixelFormats; using SixLabors.ImageSharp.Processing.Processors; using SixLabors.Primitives; @@ -16,26 +15,34 @@ namespace SixLabors.ImageSharp /// /// Alters the contrast component of the image. /// + /// + /// A value of 0 will create an image that is completely gray. A value of 1 leaves the input unchanged. + /// Other values are linear multipliers on the effect. Values of an amount over 1 are allowed, providing results with more contrast. + /// /// The pixel format. /// The image this method extends. - /// The new contrast of the image. Must be between -100 and 100. + /// The proportion of the conversion. Must be greater than or equal to 0. /// The . - public static IImageProcessingContext Contrast(this IImageProcessingContext source, int amount) + public static IImageProcessingContext Contrast(this IImageProcessingContext source, float amount) where TPixel : struct, IPixel => source.ApplyProcessor(new ContrastProcessor(amount)); /// /// Alters the contrast component of the image. /// + /// + /// A value of 0 will create an image that is completely gray. A value of 1 leaves the input unchanged. + /// Other values are linear multipliers on the effect. Values of an amount over 1 are allowed, providing results with more contrast. + /// /// The pixel format. /// The image this method extends. - /// The new contrast of the image. Must be between -100 and 100. + /// The proportion of the conversion. Must be greater than or equal to 0. /// /// The structure that specifies the portion of the image object to alter. /// /// The . - public static IImageProcessingContext Contrast(this IImageProcessingContext source, int amount, Rectangle rectangle) + public static IImageProcessingContext Contrast(this IImageProcessingContext source, float amount, Rectangle rectangle) where TPixel : struct, IPixel => source.ApplyProcessor(new ContrastProcessor(amount), rectangle); } -} +} \ No newline at end of file diff --git a/src/ImageSharp/Processing/ColorMatrix/Grayscale.cs b/src/ImageSharp/Processing/ColorMatrix/Grayscale.cs index bcf48d3e2..4fa80a183 100644 --- a/src/ImageSharp/Processing/ColorMatrix/Grayscale.cs +++ b/src/ImageSharp/Processing/ColorMatrix/Grayscale.cs @@ -21,12 +21,21 @@ namespace SixLabors.ImageSharp /// The . public static IImageProcessingContext Grayscale(this IImageProcessingContext source) where TPixel : struct, IPixel - { - return Grayscale(source, GrayscaleMode.Bt709); - } + => Grayscale(source, GrayscaleMode.Bt709); /// - /// Applies Grayscale toning to the image. + /// Applies Grayscale toning to the image using the given amount. + /// + /// The pixel format. + /// The image this method extends. + /// The proportion of the conversion. Must be between 0 and 1. + /// The . + public static IImageProcessingContext Grayscale(this IImageProcessingContext source, float amount) + where TPixel : struct, IPixel + => Grayscale(source, GrayscaleMode.Bt709, amount); + + /// + /// Applies grayscale toning to the image with the given . /// /// The pixel format. /// The image this method extends. @@ -34,10 +43,22 @@ namespace SixLabors.ImageSharp /// The . public static IImageProcessingContext Grayscale(this IImageProcessingContext source, GrayscaleMode mode) where TPixel : struct, IPixel + => Grayscale(source, mode, 1F); + + /// + /// Applies grayscale toning to the image with the given using the given amount. + /// + /// The pixel format. + /// The image this method extends. + /// The formula to apply to perform the operation. + /// The proportion of the conversion. Must be between 0 and 1. + /// The . + public static IImageProcessingContext Grayscale(this IImageProcessingContext source, GrayscaleMode mode, float amount) + where TPixel : struct, IPixel { IImageProcessor processor = mode == GrayscaleMode.Bt709 - ? (IImageProcessor)new GrayscaleBt709Processor() - : new GrayscaleBt601Processor(); + ? (IImageProcessor)new GrayscaleBt709Processor(amount) + : new GrayscaleBt601Processor(1F); source.ApplyProcessor(processor); return source; @@ -54,9 +75,21 @@ namespace SixLabors.ImageSharp /// The . public static IImageProcessingContext Grayscale(this IImageProcessingContext source, Rectangle rectangle) where TPixel : struct, IPixel - { - return Grayscale(source, GrayscaleMode.Bt709, rectangle); - } + => Grayscale(source, 1F, rectangle); + + /// + /// Applies Grayscale toning to the image using the given amount. + /// + /// The pixel format. + /// The image this method extends. + /// The proportion of the conversion. Must be between 0 and 1. + /// + /// The structure that specifies the portion of the image object to alter. + /// + /// The . + public static IImageProcessingContext Grayscale(this IImageProcessingContext source, float amount, Rectangle rectangle) + where TPixel : struct, IPixel + => Grayscale(source, GrayscaleMode.Bt709, amount, rectangle); /// /// Applies Grayscale toning to the image. @@ -70,13 +103,28 @@ namespace SixLabors.ImageSharp /// The . public static IImageProcessingContext Grayscale(this IImageProcessingContext source, GrayscaleMode mode, Rectangle rectangle) where TPixel : struct, IPixel + => Grayscale(source, GrayscaleMode.Bt709, 1F, rectangle); + + /// + /// Applies Grayscale toning to the image using the given amount. + /// + /// The pixel format. + /// The image this method extends. + /// The formula to apply to perform the operation. + /// The proportion of the conversion. Must be between 0 and 1. + /// + /// The structure that specifies the portion of the image object to alter. + /// + /// The . + public static IImageProcessingContext Grayscale(this IImageProcessingContext source, GrayscaleMode mode, float amount, Rectangle rectangle) + where TPixel : struct, IPixel { IImageProcessor processor = mode == GrayscaleMode.Bt709 - ? (IImageProcessor)new GrayscaleBt709Processor() - : new GrayscaleBt601Processor(); + ? (IImageProcessor)new GrayscaleBt709Processor(amount) + : new GrayscaleBt601Processor(amount); source.ApplyProcessor(processor, rectangle); return source; } } -} +} \ No newline at end of file diff --git a/src/ImageSharp/Processing/ColorMatrix/Hue.cs b/src/ImageSharp/Processing/ColorMatrix/Hue.cs index bfc931977..76af10c36 100644 --- a/src/ImageSharp/Processing/ColorMatrix/Hue.cs +++ b/src/ImageSharp/Processing/ColorMatrix/Hue.cs @@ -19,7 +19,7 @@ namespace SixLabors.ImageSharp /// /// The pixel format. /// The image this method extends. - /// The angle in degrees to adjust the image. + /// The rotation angle in degrees to adjust the hue. /// The . public static IImageProcessingContext Hue(this IImageProcessingContext source, float degrees) where TPixel : struct, IPixel @@ -33,7 +33,7 @@ namespace SixLabors.ImageSharp /// /// The pixel format. /// The image this method extends. - /// The angle in degrees to adjust the image. + /// The rotation angle in degrees to adjust the hue. /// /// The structure that specifies the portion of the image object to alter. /// @@ -45,4 +45,4 @@ namespace SixLabors.ImageSharp return source; } } -} +} \ No newline at end of file diff --git a/src/ImageSharp/Processing/ColorMatrix/Matrix4x4Extensions.cs b/src/ImageSharp/Processing/ColorMatrix/Matrix4x4Extensions.cs new file mode 100644 index 000000000..21c7f05e5 --- /dev/null +++ b/src/ImageSharp/Processing/ColorMatrix/Matrix4x4Extensions.cs @@ -0,0 +1,257 @@ +// Copyright (c) Six Labors and contributors. +// Licensed under the Apache License, Version 2.0. + +using System; +using System.Numerics; + +namespace SixLabors.ImageSharp.Processing +{ + /// + /// Provides extensions methods for the struct + /// + // ReSharper disable once InconsistentNaming + public static class Matrix4x4Extensions + { + /// + /// Create a brightness filter matrix using the given amount. + /// + /// + /// A value of 0 will create an image that is completely black. A value of 1 leaves the input unchanged. + /// Other values are linear multipliers on the effect. Values of an amount over 1 are allowed, providing brighter results. + /// + /// The proportion of the conversion. Must be greater than or equal to 0. + /// The + public static Matrix4x4 CreateBrightnessFilter(float amount) + { + Guard.MustBeGreaterThanOrEqualTo(amount, 0, nameof(amount)); + + // See https://cs.chromium.org/chromium/src/cc/paint/render_surface_filters.cc + return new Matrix4x4 + { + M11 = amount, + M22 = amount, + M33 = amount, + M44 = 1 + }; + } + + /// + /// Create a contrast filter matrix using the given amount. + /// + /// + /// A value of 0 will create an image that is completely gray. A value of 1 leaves the input unchanged. + /// Other values are linear multipliers on the effect. Values of an amount over 1 are allowed, providing results with more contrast. + /// + /// The proportion of the conversion. Must be greater than or equal to 0. + /// The + public static Matrix4x4 CreateContrastFilter(float amount) + { + Guard.MustBeGreaterThanOrEqualTo(amount, 0, nameof(amount)); + + // See https://cs.chromium.org/chromium/src/cc/paint/render_surface_filters.cc + float contrast = (-.5F * amount) + .5F; + + return new Matrix4x4 + { + M11 = amount, + M22 = amount, + M33 = amount, + M41 = contrast, + M42 = contrast, + M43 = contrast, + M44 = 1 + }; + } + + /// + /// Create a greyscale filter matrix using the given amount using the formula as specified by ITU-R Recommendation BT.601. + /// + /// + /// The proportion of the conversion. Must be between 0 and 1. + /// The + public static Matrix4x4 CreateGrayscaleBt601Filter(float amount) + { + Guard.MustBeBetweenOrEqualTo(amount, 0, 1, nameof(amount)); + amount = 1F - amount; + + // https://cs.chromium.org/chromium/src/cc/paint/render_surface_filters.cc + return new Matrix4x4 + { + M11 = .299F + (.701F * amount), + M12 = .299F - (.299F * amount), + M13 = .299F - (.299F * amount), + M21 = .587F - (.587F * amount), + M22 = .587F + (.413F * amount), + M23 = .587F - (.587F * amount), + M31 = .114F - (.114F * amount), + M32 = .114F - (.114F * amount), + M33 = .114F + (.886F * amount), + M44 = 1 + }; + } + + /// + /// Create a greyscale filter matrix using the given amount using the formula as specified by ITU-R Recommendation BT.709. + /// + /// + /// The proportion of the conversion. Must be between 0 and 1. + /// The + public static Matrix4x4 CreateGrayscaleBt709Filter(float amount) + { + Guard.MustBeBetweenOrEqualTo(amount, 0, 1, nameof(amount)); + amount = 1F - amount; + + // https://cs.chromium.org/chromium/src/cc/paint/render_surface_filters.cc + return new Matrix4x4 + { + M11 = .2126F + (.7874F * amount), + M12 = .2126F - (.2126F * amount), + M13 = .2126F - (.2126F * amount), + M21 = .7152F - (.7152F * amount), + M22 = .7152F + (.2848F * amount), + M23 = .7152F - (.7152F * amount), + M31 = .0722F - (.0722F * amount), + M32 = .0722F - (.0722F * amount), + M33 = .0722F + (.9278F * amount), + M44 = 1 + }; + } + + /// + /// Create a hue filter matrix using the given angle in degrees. + /// + /// The angle of rotation in degrees. + /// The + public static Matrix4x4 CreateHueFilter(float degrees) + { + // Wrap the angle round at 360. + degrees = degrees % 360; + + // Make sure it's not negative. + while (degrees < 0) + { + degrees += 360; + } + + float radian = MathFExtensions.DegreeToRadian(degrees); + float cosRadian = MathF.Cos(radian); + float sinRadian = MathF.Sin(radian); + + // The matrix is set up to preserve the luminance of the image. + // See http://graficaobscura.com/matrix/index.html + // Number are taken from https://msdn.microsoft.com/en-us/library/jj192162(v=vs.85).aspx + return new Matrix4x4 + { + M11 = .213F + (cosRadian * .787F) - (sinRadian * .213F), + M12 = .213F - (cosRadian * .213F) - (sinRadian * 0.143F), + M13 = .213F - (cosRadian * .213F) - (sinRadian * .787F), + M21 = .715F - (cosRadian * .715F) - (sinRadian * .715F), + M22 = .715F + (cosRadian * .285F) + (sinRadian * 0.140F), + M23 = .715F - (cosRadian * .715F) + (sinRadian * .715F), + M31 = .072F - (cosRadian * .072F) + (sinRadian * .928F), + M32 = .072F - (cosRadian * .072F) - (sinRadian * 0.283F), + M33 = .072F + (cosRadian * .928F) + (sinRadian * .072F), + M44 = 1 + }; + } + + /// + /// Create an invert filter matrix using the given amount. + /// + /// The proportion of the conversion. Must be between 0 and 1. + /// The + public static Matrix4x4 CreateInvertFilter(float amount) + { + Guard.MustBeBetweenOrEqualTo(amount, 0, 1, nameof(amount)); + + // See https://cs.chromium.org/chromium/src/cc/paint/render_surface_filters.cc + float invert = 1F - (2F * amount); + + return new Matrix4x4 + { + M11 = invert, + M22 = invert, + M33 = invert, + M41 = amount, + M42 = amount, + M43 = amount, + M44 = 1 + }; + } + + /// + /// Create an opacity filter matrix using the given amount. + /// + /// The proportion of the conversion. Must be between 0 and 1. + /// The + public static Matrix4x4 CreateOpacityFilter(float amount) + { + Guard.MustBeBetweenOrEqualTo(amount, 0, 1, nameof(amount)); + + // See https://cs.chromium.org/chromium/src/cc/paint/render_surface_filters.cc + return new Matrix4x4 + { + M11 = 1, + M22 = 1, + M33 = 1, + M44 = amount + }; + } + + /// + /// Create a saturation filter matrix using the given amount. + /// + /// + /// A value of 0 is completely un-saturated. A value of 1 leaves the input unchanged. + /// Other values are linear multipliers on the effect. Values of amount over 1 are allowed, providing super-saturated results + /// + /// The proportion of the conversion. Must be greater than or equal to 0. + /// The + public static Matrix4x4 CreateSaturateFilter(float amount) + { + Guard.MustBeGreaterThanOrEqualTo(amount, 0, nameof(amount)); + + // See https://cs.chromium.org/chromium/src/cc/paint/render_surface_filters.cc + return new Matrix4x4 + { + M11 = .213F + (.787F * amount), + M12 = .213F - (.213F * amount), + M13 = .213F - (.213F * amount), + M21 = .715F - (.715F * amount), + M22 = .715F + (.285F * amount), + M23 = .715F - (.715F * amount), + M31 = 1F - ((.213F + (.787F * amount)) + (.715F - (.715F * amount))), + M32 = 1F - ((.213F - (.213F * amount)) + (.715F + (.285F * amount))), + M33 = 1F - ((.213F - (.213F * amount)) + (.715F - (.715F * amount))), + M44 = 1 + }; + } + + /// + /// Create a sepia filter matrix using the given amount. + /// The formula used matches the svg specification. + /// + /// The proportion of the conversion. Must be between 0 and 1. + /// The + public static Matrix4x4 CreateSepiaFilter(float amount) + { + Guard.MustBeBetweenOrEqualTo(amount, 0, 1, nameof(amount)); + amount = 1F - amount; + + // See https://cs.chromium.org/chromium/src/cc/paint/render_surface_filters.cc + return new Matrix4x4 + { + M11 = .393F + (.607F * amount), + M12 = .349F - (.349F * amount), + M13 = .272F - (.272F * amount), + M21 = .769F - (.769F * amount), + M22 = .686F + (.314F * amount), + M23 = .534F - (.534F * amount), + M31 = .189F - (.189F * amount), + M32 = .168F - (.168F * amount), + M33 = .131F + (.869F * amount), + M44 = 1 + }; + } + } +} \ No newline at end of file diff --git a/src/ImageSharp/Processing/Effects/Alpha.cs b/src/ImageSharp/Processing/ColorMatrix/Opacity.cs similarity index 67% rename from src/ImageSharp/Processing/Effects/Alpha.cs rename to src/ImageSharp/Processing/ColorMatrix/Opacity.cs index 2fac64e1c..b310b4b91 100644 --- a/src/ImageSharp/Processing/Effects/Alpha.cs +++ b/src/ImageSharp/Processing/ColorMatrix/Opacity.cs @@ -18,24 +18,24 @@ namespace SixLabors.ImageSharp /// /// The pixel format. /// The image this method extends. - /// The new opacity of the image. Must be between 0 and 1. + /// The proportion of the conversion. Must be between 0 and 1. /// The . - public static IImageProcessingContext Alpha(this IImageProcessingContext source, float percent) + public static IImageProcessingContext Opacity(this IImageProcessingContext source, float amount) where TPixel : struct, IPixel - => source.ApplyProcessor(new AlphaProcessor(percent)); + => source.ApplyProcessor(new OpacityProcessor(amount)); /// /// Alters the alpha component of the image. /// /// The pixel format. /// The image this method extends. - /// The new opacity of the image. Must be between 0 and 1. + /// The proportion of the conversion. Must be between 0 and 1. /// /// The structure that specifies the portion of the image object to alter. /// /// The . - public static IImageProcessingContext Alpha(this IImageProcessingContext source, float percent, Rectangle rectangle) + public static IImageProcessingContext Opacity(this IImageProcessingContext source, float amount, Rectangle rectangle) where TPixel : struct, IPixel - => source.ApplyProcessor(new AlphaProcessor(percent), rectangle); + => source.ApplyProcessor(new OpacityProcessor(amount), rectangle); } -} +} \ No newline at end of file diff --git a/src/ImageSharp/Processing/ColorMatrix/Saturation.cs b/src/ImageSharp/Processing/ColorMatrix/Saturate.cs similarity index 54% rename from src/ImageSharp/Processing/ColorMatrix/Saturation.cs rename to src/ImageSharp/Processing/ColorMatrix/Saturate.cs index 26ca5ec20..c7dd395aa 100644 --- a/src/ImageSharp/Processing/ColorMatrix/Saturation.cs +++ b/src/ImageSharp/Processing/ColorMatrix/Saturate.cs @@ -1,9 +1,7 @@ // Copyright (c) Six Labors and contributors. // Licensed under the Apache License, Version 2.0. -using System; using SixLabors.ImageSharp.PixelFormats; -using SixLabors.ImageSharp.Processing; using SixLabors.ImageSharp.Processing.Processors; using SixLabors.Primitives; @@ -17,31 +15,39 @@ namespace SixLabors.ImageSharp /// /// Alters the saturation component of the image. /// + /// + /// A value of 0 is completely un-saturated. A value of 1 leaves the input unchanged. + /// Other values are linear multipliers on the effect. Values of amount over 1 are allowed, providing super-saturated results + /// /// The pixel format. /// The image this method extends. - /// The new saturation of the image. Must be between -100 and 100. + /// The proportion of the conversion. Must be greater than or equal to 0. /// The . - public static IImageProcessingContext Saturation(this IImageProcessingContext source, int amount) + public static IImageProcessingContext Saturate(this IImageProcessingContext source, float amount) where TPixel : struct, IPixel { - source.ApplyProcessor(new SaturationProcessor(amount)); + source.ApplyProcessor(new SaturateProcessor(amount)); return source; } /// /// Alters the saturation component of the image. /// + /// + /// A value of 0 is completely un-saturated. A value of 1 leaves the input unchanged. + /// Other values are linear multipliers on the effect. Values of amount over 1 are allowed, providing super-saturated results + /// /// The pixel format. /// The image this method extends. - /// The new saturation of the image. Must be between -100 and 100. + /// The proportion of the conversion. Must be greater than or equal to 0. /// /// The structure that specifies the portion of the image object to alter. /// /// The . - public static IImageProcessingContext Saturation(this IImageProcessingContext source, int amount, Rectangle rectangle) + public static IImageProcessingContext Saturate(this IImageProcessingContext source, float amount, Rectangle rectangle) where TPixel : struct, IPixel { - source.ApplyProcessor(new SaturationProcessor(amount), rectangle); + source.ApplyProcessor(new SaturateProcessor(amount), rectangle); return source; } } diff --git a/src/ImageSharp/Processing/ColorMatrix/Sepia.cs b/src/ImageSharp/Processing/ColorMatrix/Sepia.cs index d1116fac8..0d686f4db 100644 --- a/src/ImageSharp/Processing/ColorMatrix/Sepia.cs +++ b/src/ImageSharp/Processing/ColorMatrix/Sepia.cs @@ -1,9 +1,7 @@ // Copyright (c) Six Labors and contributors. // Licensed under the Apache License, Version 2.0. -using System; using SixLabors.ImageSharp.PixelFormats; -using SixLabors.ImageSharp.Processing; using SixLabors.ImageSharp.Processing.Processors; using SixLabors.Primitives; @@ -22,7 +20,18 @@ namespace SixLabors.ImageSharp /// The . public static IImageProcessingContext Sepia(this IImageProcessingContext source) where TPixel : struct, IPixel - => source.ApplyProcessor(new SepiaProcessor()); + => Sepia(source, 1F); + + /// + /// Applies sepia toning to the image using the given amount. + /// + /// The pixel format. + /// The image this method extends. + /// The proportion of the conversion. Must be between 0 and 1. + /// The . + public static IImageProcessingContext Sepia(this IImageProcessingContext source, float amount) + where TPixel : struct, IPixel + => source.ApplyProcessor(new SepiaProcessor(amount)); /// /// Applies sepia toning to the image. @@ -35,6 +44,20 @@ namespace SixLabors.ImageSharp /// The . public static IImageProcessingContext Sepia(this IImageProcessingContext source, Rectangle rectangle) where TPixel : struct, IPixel - => source.ApplyProcessor(new SepiaProcessor(), rectangle); + => Sepia(source, 1F, rectangle); + + /// + /// Applies sepia toning to the image. + /// + /// The pixel format. + /// The image this method extends. + /// The proportion of the conversion. Must be between 0 and 1. + /// + /// The structure that specifies the portion of the image object to alter. + /// + /// The . + public static IImageProcessingContext Sepia(this IImageProcessingContext source, float amount, Rectangle rectangle) + where TPixel : struct, IPixel + => source.ApplyProcessor(new SepiaProcessor(amount), rectangle); } } \ No newline at end of file diff --git a/src/ImageSharp/Processing/Effects/Invert.cs b/src/ImageSharp/Processing/Effects/Invert.cs index 9c0a7d377..7dd9ed3dd 100644 --- a/src/ImageSharp/Processing/Effects/Invert.cs +++ b/src/ImageSharp/Processing/Effects/Invert.cs @@ -21,7 +21,7 @@ namespace SixLabors.ImageSharp /// The . public static IImageProcessingContext Invert(this IImageProcessingContext source) where TPixel : struct, IPixel - => source.ApplyProcessor(new InvertProcessor()); + => source.ApplyProcessor(new InvertProcessor(1F)); /// /// Inverts the colors of the image. @@ -34,6 +34,6 @@ namespace SixLabors.ImageSharp /// The . public static IImageProcessingContext Invert(this IImageProcessingContext source, Rectangle rectangle) where TPixel : struct, IPixel - => source.ApplyProcessor(new InvertProcessor(), rectangle); + => source.ApplyProcessor(new InvertProcessor(1F), rectangle); } } diff --git a/src/ImageSharp/Processing/Processors/Binarization/BinaryThresholdProcessor.cs b/src/ImageSharp/Processing/Processors/Binarization/BinaryThresholdProcessor.cs index d736b91ee..434ed0269 100644 --- a/src/ImageSharp/Processing/Processors/Binarization/BinaryThresholdProcessor.cs +++ b/src/ImageSharp/Processing/Processors/Binarization/BinaryThresholdProcessor.cs @@ -50,7 +50,7 @@ namespace SixLabors.ImageSharp.Processing.Processors /// protected override void BeforeApply(ImageFrame source, Rectangle sourceRectangle, Configuration configuration) { - new GrayscaleBt709Processor().Apply(source, sourceRectangle, configuration); + new GrayscaleBt709Processor(1F).Apply(source, sourceRectangle, configuration); } /// diff --git a/src/ImageSharp/Processing/Processors/Binarization/ErrorDiffusionDitherProcessor.cs b/src/ImageSharp/Processing/Processors/Binarization/ErrorDiffusionDitherProcessor.cs index 8907770e1..01cba15c4 100644 --- a/src/ImageSharp/Processing/Processors/Binarization/ErrorDiffusionDitherProcessor.cs +++ b/src/ImageSharp/Processing/Processors/Binarization/ErrorDiffusionDitherProcessor.cs @@ -57,7 +57,7 @@ namespace SixLabors.ImageSharp.Processing.Processors /// protected override void BeforeApply(ImageFrame source, Rectangle sourceRectangle, Configuration configuration) { - new GrayscaleBt709Processor().Apply(source, sourceRectangle, configuration); + new GrayscaleBt709Processor(1F).Apply(source, sourceRectangle, configuration); } /// diff --git a/src/ImageSharp/Processing/Processors/Binarization/OrderedDitherProcessor.cs b/src/ImageSharp/Processing/Processors/Binarization/OrderedDitherProcessor.cs index a2fd17c94..a37d12f18 100644 --- a/src/ImageSharp/Processing/Processors/Binarization/OrderedDitherProcessor.cs +++ b/src/ImageSharp/Processing/Processors/Binarization/OrderedDitherProcessor.cs @@ -65,7 +65,7 @@ namespace SixLabors.ImageSharp.Processing.Processors /// protected override void BeforeApply(ImageFrame source, Rectangle sourceRectangle, Configuration configuration) { - new GrayscaleBt709Processor().Apply(source, sourceRectangle, configuration); + new GrayscaleBt709Processor(1F).Apply(source, sourceRectangle, configuration); } /// diff --git a/src/ImageSharp/Processing/Processors/ColorMatrix/BrightnessProcessor.cs b/src/ImageSharp/Processing/Processors/ColorMatrix/BrightnessProcessor.cs new file mode 100644 index 000000000..051a74ba2 --- /dev/null +++ b/src/ImageSharp/Processing/Processors/ColorMatrix/BrightnessProcessor.cs @@ -0,0 +1,34 @@ +// Copyright (c) Six Labors and contributors. +// Licensed under the Apache License, Version 2.0. + +using SixLabors.ImageSharp.PixelFormats; + +namespace SixLabors.ImageSharp.Processing.Processors +{ + /// + /// Applies a brightness filter matrix using the given amount. + /// + /// The pixel format. + internal class BrightnessProcessor : FilterProcessor + where TPixel : struct, IPixel + { + /// + /// Initializes a new instance of the class. + /// + /// + /// A value of 0 will create an image that is completely black. A value of 1 leaves the input unchanged. + /// Other values are linear multipliers on the effect. Values of an amount over 1 are allowed, providing brighter results. + /// + /// The proportion of the conversion. Must be greater than or equal to 0. + public BrightnessProcessor(float amount) + : base(Matrix4x4Extensions.CreateBrightnessFilter(amount)) + { + this.Amount = amount; + } + + /// + /// Gets the proportion of the conversion + /// + public float Amount { get; } + } +} \ No newline at end of file diff --git a/src/ImageSharp/Processing/Processors/ColorMatrix/ContrastProcessor.cs b/src/ImageSharp/Processing/Processors/ColorMatrix/ContrastProcessor.cs new file mode 100644 index 000000000..a46d0c1de --- /dev/null +++ b/src/ImageSharp/Processing/Processors/ColorMatrix/ContrastProcessor.cs @@ -0,0 +1,34 @@ +// Copyright (c) Six Labors and contributors. +// Licensed under the Apache License, Version 2.0. + +using SixLabors.ImageSharp.PixelFormats; + +namespace SixLabors.ImageSharp.Processing.Processors +{ + /// + /// Applies a contrast filter matrix using the given amount. + /// + /// The pixel format. + internal class ContrastProcessor : FilterProcessor + where TPixel : struct, IPixel + { + /// + /// Initializes a new instance of the class. + /// + /// + /// A value of 0 will create an image that is completely gray. A value of 1 leaves the input unchanged. + /// Other values are linear multipliers on the effect. Values of an amount over 1 are allowed, providing results with more contrast. + /// + /// The proportion of the conversion. Must be greater than or equal to 0. + public ContrastProcessor(float amount) + : base(Matrix4x4Extensions.CreateContrastFilter(amount)) + { + this.Amount = amount; + } + + /// + /// Gets the proportion of the conversion + /// + public float Amount { get; } + } +} \ No newline at end of file diff --git a/src/ImageSharp/Processing/Processors/ColorMatrix/FilterProcessor.cs b/src/ImageSharp/Processing/Processors/ColorMatrix/FilterProcessor.cs new file mode 100644 index 000000000..30fe8c6b6 --- /dev/null +++ b/src/ImageSharp/Processing/Processors/ColorMatrix/FilterProcessor.cs @@ -0,0 +1,62 @@ +// Copyright (c) Six Labors and contributors. +// Licensed under the Apache License, Version 2.0. + +using System; +using System.Numerics; +using System.Threading.Tasks; +using SixLabors.ImageSharp.Advanced; +using SixLabors.ImageSharp.Helpers; +using SixLabors.ImageSharp.PixelFormats; +using SixLabors.Primitives; + +namespace SixLabors.ImageSharp.Processing.Processors +{ + /// + /// Provides methods that accept a matrix to apply freeform filters to images. + /// + /// The pixel format. + internal class FilterProcessor : ImageProcessor + where TPixel : struct, IPixel + { + /// + /// Initializes a new instance of the class. + /// + /// The matrix used to apply the image filter + public FilterProcessor(Matrix4x4 matrix) + { + this.Matrix = matrix; + } + + /// + /// Gets the used to apply the image filter. + /// + public Matrix4x4 Matrix { get; } + + /// + protected override void OnApply(ImageFrame source, Rectangle sourceRectangle, Configuration configuration) + { + var interest = Rectangle.Intersect(sourceRectangle, source.Bounds()); + int startY = interest.Y; + int endY = interest.Bottom; + int startX = interest.X; + int endX = interest.Right; + Matrix4x4 matrix = this.Matrix; + + Parallel.For( + startY, + endY, + configuration.ParallelOptions, + y => + { + Span row = source.GetPixelRowSpan(y); + + for (int x = startX; x < endX; x++) + { + ref TPixel pixel = ref row[x]; + var vector = Vector4.Transform(pixel.ToVector4(), matrix); + pixel.PackFromVector4(vector); + } + }); + } + } +} \ No newline at end of file diff --git a/src/ImageSharp/Processing/Processors/ColorMatrix/GrayscaleBt601Processor.cs b/src/ImageSharp/Processing/Processors/ColorMatrix/GrayscaleBt601Processor.cs index 35dfe41a8..fde0665d3 100644 --- a/src/ImageSharp/Processing/Processors/ColorMatrix/GrayscaleBt601Processor.cs +++ b/src/ImageSharp/Processing/Processors/ColorMatrix/GrayscaleBt601Processor.cs @@ -1,32 +1,30 @@ // Copyright (c) Six Labors and contributors. // Licensed under the Apache License, Version 2.0. -using System.Numerics; using SixLabors.ImageSharp.PixelFormats; namespace SixLabors.ImageSharp.Processing.Processors { /// - /// Converts the colors of the image to Grayscale applying the formula as specified by ITU-R Recommendation BT.601 - /// . + /// Applies a greyscale filter matrix using the given amount and the formula as specified by ITU-R Recommendation BT.601 /// /// The pixel format. - internal class GrayscaleBt601Processor : ColorMatrixProcessor - where TPixel : struct, IPixel + internal class GrayscaleBt601Processor : FilterProcessor + where TPixel : struct, IPixel { - /// - public override Matrix4x4 Matrix => new Matrix4x4 + /// + /// Initializes a new instance of the class. + /// + /// The proportion of the conversion. Must be between 0 and 1. + public GrayscaleBt601Processor(float amount) + : base(Matrix4x4Extensions.CreateGrayscaleBt601Filter(amount)) { - M11 = .299F, - M12 = .299F, - M13 = .299F, - M21 = .587F, - M22 = .587F, - M23 = .587F, - M31 = .114F, - M32 = .114F, - M33 = .114F, - M44 = 1 - }; + this.Amount = amount; + } + + /// + /// Gets the proportion of the conversion + /// + public float Amount { get; } } } \ No newline at end of file diff --git a/src/ImageSharp/Processing/Processors/ColorMatrix/GrayscaleBt709Processor.cs b/src/ImageSharp/Processing/Processors/ColorMatrix/GrayscaleBt709Processor.cs index 6bb460ee6..92195a30d 100644 --- a/src/ImageSharp/Processing/Processors/ColorMatrix/GrayscaleBt709Processor.cs +++ b/src/ImageSharp/Processing/Processors/ColorMatrix/GrayscaleBt709Processor.cs @@ -1,32 +1,30 @@ // Copyright (c) Six Labors and contributors. // Licensed under the Apache License, Version 2.0. -using System.Numerics; using SixLabors.ImageSharp.PixelFormats; namespace SixLabors.ImageSharp.Processing.Processors { /// - /// Converts the colors of the image to Grayscale applying the formula as specified by ITU-R Recommendation BT.709 - /// . + /// Applies a greyscale filter matrix using the given amount and the formula as specified by ITU-R Recommendation BT.709 /// /// The pixel format. - internal class GrayscaleBt709Processor : ColorMatrixProcessor - where TPixel : struct, IPixel + internal class GrayscaleBt709Processor : FilterProcessor + where TPixel : struct, IPixel { - /// - public override Matrix4x4 Matrix => new Matrix4x4 + /// + /// Initializes a new instance of the class. + /// + /// The proportion of the conversion. Must be between 0 and 1. + public GrayscaleBt709Processor(float amount) + : base(Matrix4x4Extensions.CreateGrayscaleBt709Filter(amount)) { - M11 = .2126F, - M12 = .2126F, - M13 = .2126F, - M21 = .7152F, - M22 = .7152F, - M23 = .7152F, - M31 = .0722F, - M32 = .0722F, - M33 = .0722F, - M44 = 1 - }; + this.Amount = amount; + } + + /// + /// Gets the proportion of the conversion + /// + public float Amount { get; } } } \ No newline at end of file diff --git a/src/ImageSharp/Processing/Processors/ColorMatrix/HueProcessor.cs b/src/ImageSharp/Processing/Processors/ColorMatrix/HueProcessor.cs index adfdb6a78..edb61855e 100644 --- a/src/ImageSharp/Processing/Processors/ColorMatrix/HueProcessor.cs +++ b/src/ImageSharp/Processing/Processors/ColorMatrix/HueProcessor.cs @@ -1,77 +1,29 @@ // Copyright (c) Six Labors and contributors. // Licensed under the Apache License, Version 2.0. -using System; -using System.Numerics; using SixLabors.ImageSharp.PixelFormats; namespace SixLabors.ImageSharp.Processing.Processors { /// - /// An to change the hue of an . + /// Applies a hue filter matrix using the given angle of rotation in degrees /// - /// The pixel format. - internal class HueProcessor : ColorMatrixProcessor - where TPixel : struct, IPixel + internal class HueProcessor : FilterProcessor + where TPixel : struct, IPixel { /// /// Initializes a new instance of the class. /// - /// The new brightness of the image. Must be between -100 and 100. - public HueProcessor(float angle) + /// The angle of rotation in degrees + public HueProcessor(float degrees) + : base(Matrix4x4Extensions.CreateHueFilter(degrees)) { - // Wrap the angle round at 360. - angle = angle % 360; - - // Make sure it's not negative. - while (angle < 0) - { - angle += 360; - } - - this.Angle = angle; - - float radians = MathFExtensions.DegreeToRadian(angle); - float cosradians = MathF.Cos(radians); - float sinradians = MathF.Sin(radians); - - float lumR = .213F; - float lumG = .715F; - float lumB = .072F; - - float oneMinusLumR = 1 - lumR; - float oneMinusLumG = 1 - lumG; - float oneMinusLumB = 1 - lumB; - - // The matrix is set up to preserve the luminance of the image. - // See http://graficaobscura.com/matrix/index.html - // Number are taken from https://msdn.microsoft.com/en-us/library/jj192162(v=vs.85).aspx - var matrix4X4 = new Matrix4x4 - { - M11 = lumR + (cosradians * oneMinusLumR) - (sinradians * lumR), - M12 = lumR - (cosradians * lumR) - (sinradians * 0.143F), - M13 = lumR - (cosradians * lumR) - (sinradians * oneMinusLumR), - M21 = lumG - (cosradians * lumG) - (sinradians * lumG), - M22 = lumG + (cosradians * oneMinusLumG) + (sinradians * 0.140F), - M23 = lumG - (cosradians * lumG) + (sinradians * lumG), - M31 = lumB - (cosradians * lumB) + (sinradians * oneMinusLumB), - M32 = lumB - (cosradians * lumB) - (sinradians * 0.283F), - M33 = lumB + (cosradians * oneMinusLumB) + (sinradians * lumB), - M44 = 1 - }; - - this.Matrix = matrix4X4; + this.Degrees = degrees; } /// - /// Gets the rotation value. + /// Gets the angle of rotation in degrees /// - public float Angle { get; } - - /// - public override Matrix4x4 Matrix { get; } - - /// - public override bool Compand => false; + public float Degrees { get; } } -} +} \ No newline at end of file diff --git a/src/ImageSharp/Processing/Processors/ColorMatrix/InvertProcessor.cs b/src/ImageSharp/Processing/Processors/ColorMatrix/InvertProcessor.cs new file mode 100644 index 000000000..1a78c22b5 --- /dev/null +++ b/src/ImageSharp/Processing/Processors/ColorMatrix/InvertProcessor.cs @@ -0,0 +1,30 @@ +// Copyright (c) Six Labors and contributors. +// Licensed under the Apache License, Version 2.0. + +using SixLabors.ImageSharp.PixelFormats; + +namespace SixLabors.ImageSharp.Processing.Processors +{ + /// + /// Applies a filter matrix that inverts the colors of an image + /// + /// The pixel format. + internal class InvertProcessor : FilterProcessor + where TPixel : struct, IPixel + { + /// + /// Initializes a new instance of the class. + /// + /// The proportion of the conversion. Must be between 0 and 1. + public InvertProcessor(float amount) + : base(Matrix4x4Extensions.CreateInvertFilter(amount)) + { + this.Amount = amount; + } + + /// + /// Gets the proportion of the conversion + /// + public float Amount { get; } + } +} \ No newline at end of file diff --git a/src/ImageSharp/Processing/Processors/ColorMatrix/OpacityProcessor.cs b/src/ImageSharp/Processing/Processors/ColorMatrix/OpacityProcessor.cs new file mode 100644 index 000000000..7247cec40 --- /dev/null +++ b/src/ImageSharp/Processing/Processors/ColorMatrix/OpacityProcessor.cs @@ -0,0 +1,30 @@ +// Copyright (c) Six Labors and contributors. +// Licensed under the Apache License, Version 2.0. + +using SixLabors.ImageSharp.PixelFormats; + +namespace SixLabors.ImageSharp.Processing.Processors +{ + /// + /// Applies an opacity filter matrix using the given amount. + /// + /// The pixel format. + internal class OpacityProcessor : FilterProcessor + where TPixel : struct, IPixel + { + /// + /// Initializes a new instance of the class. + /// + /// The proportion of the conversion. Must be between 0 and 1. + public OpacityProcessor(float amount) + : base(Matrix4x4Extensions.CreateOpacityFilter(amount)) + { + this.Amount = amount; + } + + /// + /// Gets the proportion of the conversion + /// + public float Amount { get; } + } +} \ No newline at end of file diff --git a/src/ImageSharp/Processing/Processors/ColorMatrix/SaturateProcessor.cs b/src/ImageSharp/Processing/Processors/ColorMatrix/SaturateProcessor.cs new file mode 100644 index 000000000..0a25161a8 --- /dev/null +++ b/src/ImageSharp/Processing/Processors/ColorMatrix/SaturateProcessor.cs @@ -0,0 +1,34 @@ +// Copyright (c) Six Labors and contributors. +// Licensed under the Apache License, Version 2.0. + +using SixLabors.ImageSharp.PixelFormats; + +namespace SixLabors.ImageSharp.Processing.Processors +{ + /// + /// Applies a saturation filter matrix using the given amount. + /// + /// The pixel format. + internal class SaturateProcessor : FilterProcessor + where TPixel : struct, IPixel + { + /// + /// Initializes a new instance of the class. + /// + /// + /// A value of 0 is completely un-saturated. A value of 1 leaves the input unchanged. + /// Other values are linear multipliers on the effect. Values of amount over 1 are allowed, providing super-saturated results + /// + /// The proportion of the conversion. Must be greater than or equal to 0. + public SaturateProcessor(float amount) + : base(Matrix4x4Extensions.CreateSaturateFilter(amount)) + { + this.Amount = amount; + } + + /// + /// Gets the proportion of the conversion + /// + public float Amount { get; } + } +} \ No newline at end of file diff --git a/src/ImageSharp/Processing/Processors/ColorMatrix/SaturationProcessor.cs b/src/ImageSharp/Processing/Processors/ColorMatrix/SaturationProcessor.cs deleted file mode 100644 index 1f01bc85d..000000000 --- a/src/ImageSharp/Processing/Processors/ColorMatrix/SaturationProcessor.cs +++ /dev/null @@ -1,66 +0,0 @@ -// Copyright (c) Six Labors and contributors. -// Licensed under the Apache License, Version 2.0. - -using System.Numerics; -using SixLabors.ImageSharp.PixelFormats; - -namespace SixLabors.ImageSharp.Processing.Processors -{ - /// - /// An to change the saturation of an . - /// - /// The pixel format. - internal class SaturationProcessor : ColorMatrixProcessor - where TPixel : struct, IPixel - { - /// - /// Initializes a new instance of the class. - /// - /// The new saturation of the image. Must be between -100 and 100. - /// - /// is less than -100 or is greater than 100. - /// - public SaturationProcessor(int saturation) - { - this.Amount = saturation; - Guard.MustBeBetweenOrEqualTo(saturation, -100, 100, nameof(saturation)); - float saturationFactor = saturation / 100F; - - // Stop at -1 to prevent inversion. - saturationFactor++; - - // The matrix is set up to "shear" the color space using the following set of values. - // Note that each color component has an effective luminance which contributes to the - // overall brightness of the pixel. - // See http://graficaobscura.com/matrix/index.html - float saturationComplement = 1.0f - saturationFactor; - float saturationComplementR = 0.3086f * saturationComplement; - float saturationComplementG = 0.6094f * saturationComplement; - float saturationComplementB = 0.0820f * saturationComplement; - - var matrix4X4 = new Matrix4x4 - { - M11 = saturationComplementR + saturationFactor, - M12 = saturationComplementR, - M13 = saturationComplementR, - M21 = saturationComplementG, - M22 = saturationComplementG + saturationFactor, - M23 = saturationComplementG, - M31 = saturationComplementB, - M32 = saturationComplementB, - M33 = saturationComplementB + saturationFactor, - M44 = 1 - }; - - this.Matrix = matrix4X4; - } - - /// - /// Gets the amount to apply. - /// - public int Amount { get; } - - /// - public override Matrix4x4 Matrix { get; } - } -} diff --git a/src/ImageSharp/Processing/Processors/ColorMatrix/SepiaProcessor.cs b/src/ImageSharp/Processing/Processors/ColorMatrix/SepiaProcessor.cs index d959ebf52..9cd7c6861 100644 --- a/src/ImageSharp/Processing/Processors/ColorMatrix/SepiaProcessor.cs +++ b/src/ImageSharp/Processing/Processors/ColorMatrix/SepiaProcessor.cs @@ -1,35 +1,30 @@ // Copyright (c) Six Labors and contributors. // Licensed under the Apache License, Version 2.0. -using System.Numerics; using SixLabors.ImageSharp.PixelFormats; namespace SixLabors.ImageSharp.Processing.Processors { /// - /// Converts the colors of the image to their sepia equivalent. - /// The formula used matches the svg specification. + /// Applies a sepia filter matrix using the given amount. /// /// The pixel format. - internal class SepiaProcessor : ColorMatrixProcessor - where TPixel : struct, IPixel + internal class SepiaProcessor : FilterProcessor + where TPixel : struct, IPixel { - /// - public override Matrix4x4 Matrix => new Matrix4x4 + /// + /// Initializes a new instance of the class. + /// + /// The proportion of the conversion. Must be between 0 and 1. + public SepiaProcessor(float amount) + : base(Matrix4x4Extensions.CreateSepiaFilter(amount)) { - M11 = .393F, - M12 = .349F, - M13 = .272F, - M21 = .769F, - M22 = .686F, - M23 = .534F, - M31 = .189F, - M32 = .168F, - M33 = .131F, - M44 = 1 - }; + this.Amount = amount; + } - /// - public override bool Compand => false; + /// + /// Gets the proportion of the conversion + /// + public float Amount { get; } } } \ No newline at end of file diff --git a/src/ImageSharp/Processing/Processors/Convolution/EdgeDetection/EdgeDetector2DProcessor.cs b/src/ImageSharp/Processing/Processors/Convolution/EdgeDetection/EdgeDetector2DProcessor.cs index f93787d12..741a6e308 100644 --- a/src/ImageSharp/Processing/Processors/Convolution/EdgeDetection/EdgeDetector2DProcessor.cs +++ b/src/ImageSharp/Processing/Processors/Convolution/EdgeDetection/EdgeDetector2DProcessor.cs @@ -50,7 +50,7 @@ namespace SixLabors.ImageSharp.Processing.Processors { if (this.Grayscale) { - new GrayscaleBt709Processor().Apply(source, sourceRectangle, configuration); + new GrayscaleBt709Processor(1F).Apply(source, sourceRectangle, configuration); } } } diff --git a/src/ImageSharp/Processing/Processors/Convolution/EdgeDetection/EdgeDetectorCompassProcessor.cs b/src/ImageSharp/Processing/Processors/Convolution/EdgeDetection/EdgeDetectorCompassProcessor.cs index 32c22a8ce..0ffd7d48f 100644 --- a/src/ImageSharp/Processing/Processors/Convolution/EdgeDetection/EdgeDetectorCompassProcessor.cs +++ b/src/ImageSharp/Processing/Processors/Convolution/EdgeDetection/EdgeDetectorCompassProcessor.cs @@ -66,7 +66,7 @@ namespace SixLabors.ImageSharp.Processing.Processors { if (this.Grayscale) { - new GrayscaleBt709Processor().Apply(source, sourceRectangle, configuration); + new GrayscaleBt709Processor(1F).Apply(source, sourceRectangle, configuration); } } diff --git a/src/ImageSharp/Processing/Processors/Convolution/EdgeDetection/EdgeDetectorProcessor.cs b/src/ImageSharp/Processing/Processors/Convolution/EdgeDetection/EdgeDetectorProcessor.cs index 3b98b77fc..e5c517971 100644 --- a/src/ImageSharp/Processing/Processors/Convolution/EdgeDetection/EdgeDetectorProcessor.cs +++ b/src/ImageSharp/Processing/Processors/Convolution/EdgeDetection/EdgeDetectorProcessor.cs @@ -37,7 +37,7 @@ namespace SixLabors.ImageSharp.Processing.Processors { if (this.Grayscale) { - new GrayscaleBt709Processor().Apply(source, sourceRectangle, configuration); + new GrayscaleBt709Processor(1F).Apply(source, sourceRectangle, configuration); } } diff --git a/src/ImageSharp/Processing/Processors/Effects/AlphaProcessor.cs b/src/ImageSharp/Processing/Processors/Effects/AlphaProcessor.cs deleted file mode 100644 index 7e5bd02ab..000000000 --- a/src/ImageSharp/Processing/Processors/Effects/AlphaProcessor.cs +++ /dev/null @@ -1,81 +0,0 @@ -// Copyright (c) Six Labors and contributors. -// Licensed under the Apache License, Version 2.0. - -using System; -using System.Numerics; -using System.Threading.Tasks; -using SixLabors.ImageSharp.Advanced; -using SixLabors.ImageSharp.PixelFormats; -using SixLabors.Primitives; - -namespace SixLabors.ImageSharp.Processing.Processors -{ - /// - /// An to change the alpha component of an . - /// - /// The pixel format. - internal class AlphaProcessor : ImageProcessor - where TPixel : struct, IPixel - { - /// - /// Initializes a new instance of the class. - /// - /// The percentage to adjust the opacity of the image. Must be between 0 and 1. - /// - /// is less than 0 or is greater than 1. - /// - public AlphaProcessor(float percent) - { - Guard.MustBeBetweenOrEqualTo(percent, 0, 1, nameof(percent)); - this.Value = percent; - } - - /// - /// Gets the alpha value. - /// - public float Value { get; } - - /// - protected override void OnApply(ImageFrame source, Rectangle sourceRectangle, Configuration configuration) - { - int startY = sourceRectangle.Y; - int endY = sourceRectangle.Bottom; - int startX = sourceRectangle.X; - int endX = sourceRectangle.Right; - - // Align start/end positions. - int minX = Math.Max(0, startX); - int maxX = Math.Min(source.Width, endX); - int minY = Math.Max(0, startY); - int maxY = Math.Min(source.Height, endY); - - // Reset offset if necessary. - if (minX > 0) - { - startX = 0; - } - - if (minY > 0) - { - startY = 0; - } - - var alphaVector = new Vector4(1, 1, 1, this.Value); - - Parallel.For( - minY, - maxY, - configuration.ParallelOptions, - y => - { - Span row = source.GetPixelRowSpan(y - startY); - - for (int x = minX; x < maxX; x++) - { - ref TPixel pixel = ref row[x - startX]; - pixel.PackFromVector4(pixel.ToVector4() * alphaVector); - } - }); - } - } -} diff --git a/src/ImageSharp/Processing/Processors/Effects/BrightnessProcessor.cs b/src/ImageSharp/Processing/Processors/Effects/BrightnessProcessor.cs deleted file mode 100644 index c864330c9..000000000 --- a/src/ImageSharp/Processing/Processors/Effects/BrightnessProcessor.cs +++ /dev/null @@ -1,87 +0,0 @@ -// Copyright (c) Six Labors and contributors. -// Licensed under the Apache License, Version 2.0. - -using System; -using System.Numerics; -using System.Threading.Tasks; -using SixLabors.ImageSharp.Advanced; -using SixLabors.ImageSharp.PixelFormats; -using SixLabors.Primitives; - -namespace SixLabors.ImageSharp.Processing.Processors -{ - /// - /// An to change the brightness of an . - /// - /// The pixel format. - internal class BrightnessProcessor : ImageProcessor - where TPixel : struct, IPixel - { - /// - /// Initializes a new instance of the class. - /// - /// The new brightness of the image. Must be between -100 and 100. - /// - /// is less than -100 or is greater than 100. - /// - public BrightnessProcessor(int brightness) - { - Guard.MustBeBetweenOrEqualTo(brightness, -100, 100, nameof(brightness)); - this.Value = brightness; - } - - /// - /// Gets the brightness value. - /// - public int Value { get; } - - /// - protected override void OnApply(ImageFrame source, Rectangle sourceRectangle, Configuration configuration) - { - float brightness = this.Value / 100F; - - int startY = sourceRectangle.Y; - int endY = sourceRectangle.Bottom; - int startX = sourceRectangle.X; - int endX = sourceRectangle.Right; - - // Align start/end positions. - int minX = Math.Max(0, startX); - int maxX = Math.Min(source.Width, endX); - int minY = Math.Max(0, startY); - int maxY = Math.Min(source.Height, endY); - - // Reset offset if necessary. - if (minX > 0) - { - startX = 0; - } - - if (minY > 0) - { - startY = 0; - } - - Parallel.For( - minY, - maxY, - configuration.ParallelOptions, - y => - { - Span row = source.GetPixelRowSpan(y - startY); - - for (int x = minX; x < maxX; x++) - { - ref TPixel pixel = ref row[x - startX]; - - // TODO: Check this with other formats. - Vector4 vector = pixel.ToVector4().Expand(); - Vector3 transformed = new Vector3(vector.X, vector.Y, vector.Z) + new Vector3(brightness); - vector = new Vector4(transformed, vector.W); - - pixel.PackFromVector4(vector.Compress()); - } - }); - } - } -} \ No newline at end of file diff --git a/src/ImageSharp/Processing/Processors/Effects/ContrastProcessor.cs b/src/ImageSharp/Processing/Processors/Effects/ContrastProcessor.cs deleted file mode 100644 index 5ab266211..000000000 --- a/src/ImageSharp/Processing/Processors/Effects/ContrastProcessor.cs +++ /dev/null @@ -1,89 +0,0 @@ -// Copyright (c) Six Labors and contributors. -// Licensed under the Apache License, Version 2.0. - -using System; -using System.Numerics; -using System.Threading.Tasks; -using SixLabors.ImageSharp.Advanced; -using SixLabors.ImageSharp.PixelFormats; -using SixLabors.Primitives; - -namespace SixLabors.ImageSharp.Processing.Processors -{ - /// - /// An to change the contrast of an . - /// - /// The pixel format. - internal class ContrastProcessor : ImageProcessor - where TPixel : struct, IPixel - { - /// - /// Initializes a new instance of the class. - /// - /// The new contrast of the image. Must be between -100 and 100. - /// - /// is less than -100 or is greater than 100. - /// - public ContrastProcessor(int contrast) - { - Guard.MustBeBetweenOrEqualTo(contrast, -100, 100, nameof(contrast)); - this.Value = contrast; - } - - /// - /// Gets the contrast value. - /// - public int Value { get; } - - /// - protected override void OnApply(ImageFrame source, Rectangle sourceRectangle, Configuration configuration) - { - float contrast = (100F + this.Value) / 100F; - - int startY = sourceRectangle.Y; - int endY = sourceRectangle.Bottom; - int startX = sourceRectangle.X; - int endX = sourceRectangle.Right; - var contrastVector = new Vector4(contrast, contrast, contrast, 1); - var shiftVector = new Vector4(.5F, .5F, .5F, 1); - - // Align start/end positions. - int minX = Math.Max(0, startX); - int maxX = Math.Min(source.Width, endX); - int minY = Math.Max(0, startY); - int maxY = Math.Min(source.Height, endY); - - // Reset offset if necessary. - if (minX > 0) - { - startX = 0; - } - - if (minY > 0) - { - startY = 0; - } - - Parallel.For( - minY, - maxY, - configuration.ParallelOptions, - y => - { - Span row = source.GetPixelRowSpan(y - startY); - - for (int x = minX; x < maxX; x++) - { - ref TPixel pixel = ref row[x - startX]; - - Vector4 vector = pixel.ToVector4().Expand(); - vector -= shiftVector; - vector *= contrastVector; - vector += shiftVector; - - pixel.PackFromVector4(vector.Compress()); - } - }); - } - } -} \ No newline at end of file diff --git a/src/ImageSharp/Processing/Processors/Effects/InvertProcessor.cs b/src/ImageSharp/Processing/Processors/Effects/InvertProcessor.cs deleted file mode 100644 index 448025f70..000000000 --- a/src/ImageSharp/Processing/Processors/Effects/InvertProcessor.cs +++ /dev/null @@ -1,66 +0,0 @@ -// Copyright (c) Six Labors and contributors. -// Licensed under the Apache License, Version 2.0. - -using System; -using System.Numerics; -using System.Threading.Tasks; -using SixLabors.ImageSharp.Advanced; -using SixLabors.ImageSharp.PixelFormats; -using SixLabors.Primitives; - -namespace SixLabors.ImageSharp.Processing.Processors -{ - /// - /// An to invert the colors of an . - /// - /// The pixel format. - internal class InvertProcessor : ImageProcessor - where TPixel : struct, IPixel - { - /// - protected override void OnApply(ImageFrame source, Rectangle sourceRectangle, Configuration configuration) - { - int startY = sourceRectangle.Y; - int endY = sourceRectangle.Bottom; - int startX = sourceRectangle.X; - int endX = sourceRectangle.Right; - Vector3 inverseVector = Vector3.One; - - // Align start/end positions. - int minX = Math.Max(0, startX); - int maxX = Math.Min(source.Width, endX); - int minY = Math.Max(0, startY); - int maxY = Math.Min(source.Height, endY); - - // Reset offset if necessary. - if (minX > 0) - { - startX = 0; - } - - if (minY > 0) - { - startY = 0; - } - - Parallel.For( - minY, - maxY, - configuration.ParallelOptions, - y => - { - Span row = source.GetPixelRowSpan(y - startY); - - for (int x = minX; x < maxX; x++) - { - ref TPixel pixel = ref row[x - startX]; - - var vector = pixel.ToVector4(); - Vector3 vector3 = inverseVector - new Vector3(vector.X, vector.Y, vector.Z); - - pixel.PackFromVector4(new Vector4(vector3, vector.W)); - } - }); - } - } -} \ No newline at end of file diff --git a/tests/ImageSharp.Tests/Formats/GeneralFormatTests.cs b/tests/ImageSharp.Tests/Formats/GeneralFormatTests.cs index 473bc2b52..eb1ae8fa3 100644 --- a/tests/ImageSharp.Tests/Formats/GeneralFormatTests.cs +++ b/tests/ImageSharp.Tests/Formats/GeneralFormatTests.cs @@ -47,6 +47,8 @@ namespace SixLabors.ImageSharp.Tests { using (Image image = file.CreateImage()) { + image.Mutate(x => x.Saturate(1.5F, new Primitives.Rectangle(image.Width / 4, image.Height / 4, image.Width / 2, image.Height / 2))); + image.Save($"{path}/{file.FileName}"); } } diff --git a/tests/ImageSharp.Tests/Processing/Effects/BrightnessTest.cs b/tests/ImageSharp.Tests/Processing/ColorMatrix/BrightnessTest.cs similarity index 59% rename from tests/ImageSharp.Tests/Processing/Effects/BrightnessTest.cs rename to tests/ImageSharp.Tests/Processing/ColorMatrix/BrightnessTest.cs index d057f9233..05605767f 100644 --- a/tests/ImageSharp.Tests/Processing/Effects/BrightnessTest.cs +++ b/tests/ImageSharp.Tests/Processing/ColorMatrix/BrightnessTest.cs @@ -13,19 +13,19 @@ namespace SixLabors.ImageSharp.Tests.Processing.Effects [Fact] public void Brightness_amount_BrightnessProcessorDefaultsSet() { - this.operations.Brightness(23); - var processor = this.Verify>(); + this.operations.Brightness(1.5F); + BrightnessProcessor processor = this.Verify>(); - Assert.Equal(23, processor.Value); + Assert.Equal(1.5F, processor.Amount); } [Fact] public void Brightness_amount_rect_BrightnessProcessorDefaultsSet() { - this.operations.Brightness(23, this.rect); - var processor = this.Verify>(this.rect); + this.operations.Brightness(1.5F, this.rect); + BrightnessProcessor processor = this.Verify>(this.rect); - Assert.Equal(23, processor.Value); + Assert.Equal(1.5F, processor.Amount); } } } \ No newline at end of file diff --git a/tests/ImageSharp.Tests/Processing/Effects/ContrastTest.cs b/tests/ImageSharp.Tests/Processing/ColorMatrix/ContrastTest.cs similarity index 55% rename from tests/ImageSharp.Tests/Processing/Effects/ContrastTest.cs rename to tests/ImageSharp.Tests/Processing/ColorMatrix/ContrastTest.cs index 374937ea3..4aec24dad 100644 --- a/tests/ImageSharp.Tests/Processing/Effects/ContrastTest.cs +++ b/tests/ImageSharp.Tests/Processing/ColorMatrix/ContrastTest.cs @@ -1,9 +1,7 @@ // Copyright (c) Six Labors and contributors. // Licensed under the Apache License, Version 2.0. -using SixLabors.ImageSharp.PixelFormats; using SixLabors.ImageSharp.Processing.Processors; -using SixLabors.Primitives; using Xunit; namespace SixLabors.ImageSharp.Tests.Processing.Effects @@ -13,19 +11,19 @@ namespace SixLabors.ImageSharp.Tests.Processing.Effects [Fact] public void Contrast_amount_ContrastProcessorDefaultsSet() { - this.operations.Contrast(23); - var processor = this.Verify>(); + this.operations.Contrast(1.5F); + ContrastProcessor processor = this.Verify>(); - Assert.Equal(23, processor.Value); + Assert.Equal(1.5F, processor.Amount); } [Fact] public void Contrast_amount_rect_ContrastProcessorDefaultsSet() { - this.operations.Contrast(23, this.rect); - var processor = this.Verify>(this.rect); + this.operations.Contrast(1.5F, this.rect); + ContrastProcessor processor = this.Verify>(this.rect); - Assert.Equal(23, processor.Value); + Assert.Equal(1.5F, processor.Amount); } } } \ No newline at end of file diff --git a/tests/ImageSharp.Tests/Processing/ColorMatrix/HueTest.cs b/tests/ImageSharp.Tests/Processing/ColorMatrix/HueTest.cs index 0ec03dfdd..b8da495ca 100644 --- a/tests/ImageSharp.Tests/Processing/ColorMatrix/HueTest.cs +++ b/tests/ImageSharp.Tests/Processing/ColorMatrix/HueTest.cs @@ -16,7 +16,7 @@ namespace SixLabors.ImageSharp.Tests.Processing.ColorMatrix this.operations.Hue(34f); var processor = this.Verify>(); - Assert.Equal(34f, processor.Angle); + Assert.Equal(34f, processor.Degrees); } [Fact] @@ -25,7 +25,7 @@ namespace SixLabors.ImageSharp.Tests.Processing.ColorMatrix this.operations.Hue(5f, this.rect); var processor = this.Verify>(this.rect); - Assert.Equal(5f, processor.Angle); + Assert.Equal(5f, processor.Degrees); } } } \ No newline at end of file diff --git a/tests/ImageSharp.Tests/Processing/Effects/InvertTest.cs b/tests/ImageSharp.Tests/Processing/ColorMatrix/InvertTest.cs similarity index 100% rename from tests/ImageSharp.Tests/Processing/Effects/InvertTest.cs rename to tests/ImageSharp.Tests/Processing/ColorMatrix/InvertTest.cs diff --git a/tests/ImageSharp.Tests/Processing/ColorMatrix/OpacityTest.cs b/tests/ImageSharp.Tests/Processing/ColorMatrix/OpacityTest.cs new file mode 100644 index 000000000..4108cbdda --- /dev/null +++ b/tests/ImageSharp.Tests/Processing/ColorMatrix/OpacityTest.cs @@ -0,0 +1,29 @@ +// Copyright (c) Six Labors and contributors. +// Licensed under the Apache License, Version 2.0. + +using SixLabors.ImageSharp.Processing.Processors; +using Xunit; + +namespace SixLabors.ImageSharp.Tests.Processing.Effects +{ + public class OpacityTest : BaseImageOperationsExtensionTest + { + [Fact] + public void Alpha_amount_AlphaProcessorDefaultsSet() + { + this.operations.Opacity(0.2f); + OpacityProcessor processor = this.Verify>(); + + Assert.Equal(.2f, processor.Amount); + } + + [Fact] + public void Alpha_amount_rect_AlphaProcessorDefaultsSet() + { + this.operations.Opacity(0.6f, this.rect); + OpacityProcessor processor = this.Verify>(this.rect); + + Assert.Equal(.6f, processor.Amount); + } + } +} \ No newline at end of file diff --git a/tests/ImageSharp.Tests/Processing/ColorMatrix/SaturationTest.cs b/tests/ImageSharp.Tests/Processing/ColorMatrix/SaturateTest.cs similarity index 58% rename from tests/ImageSharp.Tests/Processing/ColorMatrix/SaturationTest.cs rename to tests/ImageSharp.Tests/Processing/ColorMatrix/SaturateTest.cs index 5a4402329..abac9fc1c 100644 --- a/tests/ImageSharp.Tests/Processing/ColorMatrix/SaturationTest.cs +++ b/tests/ImageSharp.Tests/Processing/ColorMatrix/SaturateTest.cs @@ -1,21 +1,19 @@ // Copyright (c) Six Labors and contributors. // Licensed under the Apache License, Version 2.0. -using SixLabors.ImageSharp.PixelFormats; using SixLabors.ImageSharp.Processing.Processors; -using SixLabors.Primitives; using Xunit; namespace SixLabors.ImageSharp.Tests.Processing.ColorMatrix { - public class SaturationTest : BaseImageOperationsExtensionTest + public class SaturateTest : BaseImageOperationsExtensionTest { [Fact] public void Saturation_amount_SaturationProcessorDefaultsSet() { - this.operations.Saturation(34); - var processor = this.Verify>(); + this.operations.Saturate(34); + SaturateProcessor processor = this.Verify>(); Assert.Equal(34, processor.Amount); } @@ -23,8 +21,8 @@ namespace SixLabors.ImageSharp.Tests.Processing.ColorMatrix [Fact] public void Saturation_amount_rect_SaturationProcessorDefaultsSet() { - this.operations.Saturation(5, this.rect); - var processor = this.Verify>(this.rect); + this.operations.Saturate(5, this.rect); + SaturateProcessor processor = this.Verify>(this.rect); Assert.Equal(5, processor.Amount); } diff --git a/tests/ImageSharp.Tests/Processing/Effects/AlphaTest.cs b/tests/ImageSharp.Tests/Processing/Effects/AlphaTest.cs deleted file mode 100644 index 9840d71c7..000000000 --- a/tests/ImageSharp.Tests/Processing/Effects/AlphaTest.cs +++ /dev/null @@ -1,31 +0,0 @@ -// Copyright (c) Six Labors and contributors. -// Licensed under the Apache License, Version 2.0. - -using SixLabors.ImageSharp.PixelFormats; -using SixLabors.ImageSharp.Processing.Processors; -using SixLabors.Primitives; -using Xunit; - -namespace SixLabors.ImageSharp.Tests.Processing.Effects -{ - public class AlphaTest : BaseImageOperationsExtensionTest - { - [Fact] - public void Alpha_amount_AlphaProcessorDefaultsSet() - { - this.operations.Alpha(0.2f); - var processor = this.Verify>(); - - Assert.Equal(.2f, processor.Value); - } - - [Fact] - public void Alpha_amount_rect_AlphaProcessorDefaultsSet() - { - this.operations.Alpha(0.6f, this.rect); - var processor = this.Verify>(this.rect); - - Assert.Equal(.6f, processor.Value); - } - } -} \ No newline at end of file diff --git a/tests/ImageSharp.Tests/Processing/Processors/Effects/BrightnessTest.cs b/tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/BrightnessTest.cs similarity index 83% rename from tests/ImageSharp.Tests/Processing/Processors/Effects/BrightnessTest.cs rename to tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/BrightnessTest.cs index 9bfed05b9..44804d0b2 100644 --- a/tests/ImageSharp.Tests/Processing/Processors/Effects/BrightnessTest.cs +++ b/tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/BrightnessTest.cs @@ -11,16 +11,16 @@ namespace SixLabors.ImageSharp.Tests.Processing.Processors.Effects { public class BrightnessTest : FileTestBase { - public static readonly TheoryData BrightnessValues - = new TheoryData + public static readonly TheoryData BrightnessValues + = new TheoryData { - 50, - -50 + .5F, + 1.5F }; [Theory] [WithFileCollection(nameof(DefaultFiles), nameof(BrightnessValues), DefaultPixelType)] - public void ImageShouldApplyBrightnessFilter(TestImageProvider provider, int value) + public void ImageShouldApplyBrightnessFilter(TestImageProvider provider, float value) where TPixel : struct, IPixel { using (Image image = provider.GetImage()) @@ -32,11 +32,11 @@ namespace SixLabors.ImageSharp.Tests.Processing.Processors.Effects [Theory] [WithFileCollection(nameof(DefaultFiles), nameof(BrightnessValues), DefaultPixelType)] - public void ImageShouldApplyBrightnessFilterInBox(TestImageProvider provider, int value) + public void ImageShouldApplyBrightnessFilterInBox(TestImageProvider provider, float value) where TPixel : struct, IPixel { using (Image source = provider.GetImage()) - using (var image = source.Clone()) + using (Image image = source.Clone()) { var bounds = new Rectangle(10, 10, image.Width / 2, image.Height / 2); diff --git a/tests/ImageSharp.Tests/Processing/Processors/Effects/ContrastTest.cs b/tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/ContrastTest.cs similarity index 83% rename from tests/ImageSharp.Tests/Processing/Processors/Effects/ContrastTest.cs rename to tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/ContrastTest.cs index f1e33db88..9117ff1b9 100644 --- a/tests/ImageSharp.Tests/Processing/Processors/Effects/ContrastTest.cs +++ b/tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/ContrastTest.cs @@ -11,16 +11,16 @@ namespace SixLabors.ImageSharp.Tests.Processing.Processors.Effects { public class ContrastTest : FileTestBase { - public static readonly TheoryData ContrastValues - = new TheoryData + public static readonly TheoryData ContrastValues + = new TheoryData { - 50, - -50 + .5F, + 1.5F }; [Theory] [WithFileCollection(nameof(DefaultFiles), nameof(ContrastValues), DefaultPixelType)] - public void ImageShouldApplyContrastFilter(TestImageProvider provider, int value) + public void ImageShouldApplyContrastFilter(TestImageProvider provider, float value) where TPixel : struct, IPixel { using (Image image = provider.GetImage()) @@ -32,11 +32,11 @@ namespace SixLabors.ImageSharp.Tests.Processing.Processors.Effects [Theory] [WithFileCollection(nameof(DefaultFiles), nameof(ContrastValues), DefaultPixelType)] - public void ImageShouldApplyContrastFilterInBox(TestImageProvider provider, int value) + public void ImageShouldApplyContrastFilterInBox(TestImageProvider provider, float value) where TPixel : struct, IPixel { using (Image source = provider.GetImage()) - using (var image = source.Clone()) + using (Image image = source.Clone()) { var bounds = new Rectangle(10, 10, image.Width / 2, image.Height / 2); diff --git a/tests/ImageSharp.Tests/Processing/Processors/Effects/InvertTest.cs b/tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/InvertTest.cs similarity index 96% rename from tests/ImageSharp.Tests/Processing/Processors/Effects/InvertTest.cs rename to tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/InvertTest.cs index 593023677..9536b36f1 100644 --- a/tests/ImageSharp.Tests/Processing/Processors/Effects/InvertTest.cs +++ b/tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/InvertTest.cs @@ -29,7 +29,7 @@ namespace SixLabors.ImageSharp.Tests.Processing.Processors.Effects where TPixel : struct, IPixel { using (Image source = provider.GetImage()) - using (var image = source.Clone()) + using (Image image = source.Clone()) { var bounds = new Rectangle(10, 10, image.Width / 2, image.Height / 2); diff --git a/tests/ImageSharp.Tests/Processing/Processors/Effects/AlphaTest.cs b/tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/OpacityTest.cs similarity index 87% rename from tests/ImageSharp.Tests/Processing/Processors/Effects/AlphaTest.cs rename to tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/OpacityTest.cs index 7f2840f2c..2815233f2 100644 --- a/tests/ImageSharp.Tests/Processing/Processors/Effects/AlphaTest.cs +++ b/tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/OpacityTest.cs @@ -9,7 +9,7 @@ using Xunit; namespace SixLabors.ImageSharp.Tests.Processing.Processors.Effects { - public class AlphaTest : FileTestBase + public class OpacityTest : FileTestBase { public static readonly TheoryData AlphaValues = new TheoryData @@ -25,7 +25,7 @@ namespace SixLabors.ImageSharp.Tests.Processing.Processors.Effects { using (Image image = provider.GetImage()) { - image.Mutate(x => x.Alpha(value)); + image.Mutate(x => x.Opacity(value)); image.DebugSave(provider, value); } } @@ -36,11 +36,11 @@ namespace SixLabors.ImageSharp.Tests.Processing.Processors.Effects where TPixel : struct, IPixel { using (Image source = provider.GetImage()) - using (var image = source.Clone()) + using (Image image = source.Clone()) { var bounds = new Rectangle(10, 10, image.Width / 2, image.Height / 2); - image.Mutate(x => x.Alpha(value, bounds)); + image.Mutate(x => x.Opacity(value, bounds)); image.DebugSave(provider, value); ImageComparer.Tolerant().VerifySimilarityIgnoreRegion(source, image, bounds); diff --git a/tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/SaturationTest.cs b/tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/SaturateTest.cs similarity index 74% rename from tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/SaturationTest.cs rename to tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/SaturateTest.cs index 2532a7fe7..4ef39a8ab 100644 --- a/tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/SaturationTest.cs +++ b/tests/ImageSharp.Tests/Processing/Processors/ColorMatrix/SaturateTest.cs @@ -9,38 +9,38 @@ using Xunit; namespace SixLabors.ImageSharp.Tests.Processing.Processors.ColorMatrix { - public class SaturationTest : FileTestBase + public class SaturateTest : FileTestBase { - public static readonly TheoryData SaturationValues - = new TheoryData + public static readonly TheoryData SaturationValues + = new TheoryData { - 50 , - -50 , + .5f, + 1.5F, }; [Theory] [WithFileCollection(nameof(DefaultFiles), nameof(SaturationValues), DefaultPixelType)] - public void ImageShouldApplySaturationFilter(TestImageProvider provider, int value) + public void ImageShouldApplySaturationFilter(TestImageProvider provider, float value) where TPixel : struct, IPixel { using (Image image = provider.GetImage()) { - image.Mutate(x => x.Saturation(value)); + image.Mutate(x => x.Saturate(value)); image.DebugSave(provider, value); } } [Theory] [WithFileCollection(nameof(DefaultFiles), nameof(SaturationValues), DefaultPixelType)] - public void ImageShouldApplySaturationFilterInBox(TestImageProvider provider, int value) + public void ImageShouldApplySaturationFilterInBox(TestImageProvider provider, float value) where TPixel : struct, IPixel { using (Image source = provider.GetImage()) - using (var image = source.Clone()) + using (Image image = source.Clone()) { var bounds = new Rectangle(10, 10, image.Width / 2, image.Height / 2); - image.Mutate(x => x.Saturation(value, bounds)); + image.Mutate(x => x.Saturate(value, bounds)); image.DebugSave(provider, value); ImageComparer.Tolerant().VerifySimilarityIgnoreRegion(source, image, bounds); diff --git a/tests/ImageSharp.Tests/TestUtilities/Tests/ReferenceCodecTests.cs b/tests/ImageSharp.Tests/TestUtilities/Tests/ReferenceCodecTests.cs index 0a550a3c1..dde34fcc4 100644 --- a/tests/ImageSharp.Tests/TestUtilities/Tests/ReferenceCodecTests.cs +++ b/tests/ImageSharp.Tests/TestUtilities/Tests/ReferenceCodecTests.cs @@ -56,7 +56,7 @@ namespace SixLabors.ImageSharp.Tests { if (pngColorType != PngColorType.RgbWithAlpha) { - sourceImage.Mutate(c => c.Alpha(1)); + sourceImage.Mutate(c => c.Opacity(1)); } var encoder = new PngEncoder() { PngColorType = pngColorType }; @@ -93,12 +93,12 @@ namespace SixLabors.ImageSharp.Tests using (Image original = provider.GetImage()) { - original.Mutate(c => c.Alpha(1)); + original.Mutate(c => c.Opacity(1)); using (var sdBitmap = new System.Drawing.Bitmap(path)) { using (Image resaved = SystemDrawingBridge.FromFromRgb24SystemDrawingBitmap(sdBitmap)) { - resaved.Mutate(c => c.Alpha(1)); + resaved.Mutate(c => c.Opacity(1)); ImageComparer comparer = ImageComparer.Exact; comparer.VerifySimilarity(original, resaved); }