diff --git a/.editorconfig b/.editorconfig
index c28089d72..f579ff5d3 100644
--- a/.editorconfig
+++ b/.editorconfig
@@ -104,8 +104,8 @@ dotnet_style_parentheses_in_relational_binary_operators = always_for_clarity:war
dotnet_style_parentheses_in_other_binary_operators = always_for_clarity:warning
dotnet_style_parentheses_in_other_operators = always_for_clarity:suggestion
# Expression-level preferences
-dotnet_style_object_initializer = true:warning
-dotnet_style_collection_initializer = true:warning
+dotnet_style_object_initializer = true:error
+dotnet_style_collection_initializer = true:error
dotnet_style_explicit_tuple_names = true:warning
dotnet_style_prefer_inferred_tuple_names = true:warning
dotnet_style_prefer_inferred_anonymous_type_member_names = true:warning
@@ -135,9 +135,9 @@ csharp_style_prefer_null_check_over_type_check = true:warning
# https://docs.microsoft.com/dotnet/fundamentals/code-analysis/style-rules/language-rules#c-style-rules
[*.{cs,csx,cake}]
# 'var' preferences
-csharp_style_var_for_built_in_types = false:warning
-csharp_style_var_when_type_is_apparent = false:warning
-csharp_style_var_elsewhere = false:warning
+csharp_style_var_for_built_in_types = false:error
+csharp_style_var_when_type_is_apparent = false:error
+csharp_style_var_elsewhere = false:error
# Expression-bodied members
csharp_style_expression_bodied_methods = true:warning
csharp_style_expression_bodied_constructors = true:warning
@@ -160,7 +160,10 @@ csharp_style_pattern_local_over_anonymous_function = true:warning
csharp_style_deconstructed_variable_declaration = true:warning
csharp_style_prefer_index_operator = true:warning
csharp_style_prefer_range_operator = true:warning
-csharp_style_implicit_object_creation_when_type_is_apparent = true:warning
+csharp_style_implicit_object_creation_when_type_is_apparent = true:error
+# ReSharper inspection severities
+resharper_arrange_object_creation_when_type_evident_highlighting = error
+resharper_arrange_object_creation_when_type_not_evident_highlighting = error
# "Null" checking preferences
csharp_style_throw_expression = true:warning
csharp_style_conditional_delegate_call = true:warning
@@ -174,6 +177,9 @@ csharp_using_directive_placement = outside_namespace:warning
csharp_prefer_static_local_function = true:warning
# Primary constructor preferences
csharp_style_prefer_primary_constructors = false:none
+# Collection preferences
+dotnet_style_prefer_collection_expression = true:error
+resharper_use_collection_expression_highlighting =true:error
##########################################
# Unnecessary Code Rules
diff --git a/.gitattributes b/.gitattributes
index b5f742ab4..f7bd4d061 100644
--- a/.gitattributes
+++ b/.gitattributes
@@ -136,3 +136,10 @@
*.ico filter=lfs diff=lfs merge=lfs -text
*.cur filter=lfs diff=lfs merge=lfs -text
*.ani filter=lfs diff=lfs merge=lfs -text
+*.heic filter=lfs diff=lfs merge=lfs -text
+*.hif filter=lfs diff=lfs merge=lfs -text
+*.avif filter=lfs diff=lfs merge=lfs -text
+###############################################################################
+# Handle ICC files by git lfs
+###############################################################################
+*.icc filter=lfs diff=lfs merge=lfs -text
diff --git a/.github/workflows/build-and-test.yml b/.github/workflows/build-and-test.yml
index 435c629bc..ff3d5c7b0 100644
--- a/.github/workflows/build-and-test.yml
+++ b/.github/workflows/build-and-test.yml
@@ -11,35 +11,79 @@ on:
branches:
- main
- release/*
- types: [ labeled, opened, synchronize, reopened ]
+ types: [ opened, synchronize, reopened ]
+
jobs:
+ # Prime a single LFS cache and expose the exact key for the matrix
+ WarmLFS:
+ runs-on: ubuntu-latest
+ outputs:
+ lfs_key: ${{ steps.expose-key.outputs.lfs_key }}
+ steps:
+ - name: Git Config
+ shell: bash
+ run: |
+ git config --global core.autocrlf false
+ git config --global core.longpaths true
+
+ - name: Git Checkout
+ uses: actions/checkout@v4
+ with:
+ fetch-depth: 0
+ submodules: recursive
+
+ # Deterministic list of LFS object IDs, then compute a portable key:
+ # - `git lfs ls-files -l` lists all tracked LFS objects with their SHA-256
+ # - `awk '{print $1}'` extracts just the SHA field
+ # - `sort` sorts in byte order (hex hashes sort the same everywhere)
+ # This ensures the file content is identical regardless of OS or locale
+ - name: Git Create LFS id list
+ shell: bash
+ run: git lfs ls-files -l | awk '{print $1}' | sort > .lfs-assets-id
+
+ - name: Git Expose LFS cache key
+ id: expose-key
+ shell: bash
+ env:
+ LFS_KEY: lfs-${{ hashFiles('.lfs-assets-id') }}-v1
+ run: echo "lfs_key=$LFS_KEY" >> "$GITHUB_OUTPUT"
+
+ - name: Git Setup LFS Cache
+ uses: actions/cache@v4
+ with:
+ path: .git/lfs
+ key: ${{ steps.expose-key.outputs.lfs_key }}
+
+ - name: Git Pull LFS
+ shell: bash
+ run: git lfs pull
+
Build:
+ needs: WarmLFS
strategy:
matrix:
- isARM:
- - ${{ contains(github.event.pull_request.labels.*.name, 'arch:arm32') || contains(github.event.pull_request.labels.*.name, 'arch:arm64') }}
options:
- os: ubuntu-latest
- framework: net9.0
- sdk: 9.0.x
+ framework: net10.0
+ sdk: 10.0.x
sdk-preview: true
runtime: -x64
codecov: false
- - os: macos-13 # macos-latest runs on arm64 runners where libgdiplus is unavailable
- framework: net9.0
- sdk: 9.0.x
+ - os: macos-26
+ framework: net10.0
+ sdk: 10.0.x
sdk-preview: true
runtime: -x64
codecov: false
- os: windows-latest
- framework: net9.0
- sdk: 9.0.x
+ framework: net10.0
+ sdk: 10.0.x
sdk-preview: true
runtime: -x64
codecov: false
- - os: buildjet-4vcpu-ubuntu-2204-arm
- framework: net9.0
- sdk: 9.0.x
+ - os: ubuntu-22.04-arm
+ framework: net10.0
+ sdk: 10.0.x
sdk-preview: true
runtime: -x64
codecov: false
@@ -49,7 +93,7 @@ jobs:
sdk: 8.0.x
runtime: -x64
codecov: false
- - os: macos-13 # macos-latest runs on arm64 runners where libgdiplus is unavailable
+ - os: macos-26
framework: net8.0
sdk: 8.0.x
runtime: -x64
@@ -59,22 +103,32 @@ jobs:
sdk: 8.0.x
runtime: -x64
codecov: false
- - os: buildjet-4vcpu-ubuntu-2204-arm
+ - os: ubuntu-22.04-arm
framework: net8.0
sdk: 8.0.x
runtime: -x64
codecov: false
- exclude:
- - isARM: false
- options:
- os: buildjet-4vcpu-ubuntu-2204-arm
- runs-on: ${{matrix.options.os}}
+ runs-on: ${{ matrix.options.os }}
steps:
- name: Install libgdi+, which is required for tests running on ubuntu
- if: ${{ matrix.options.os == 'buildjet-4vcpu-ubuntu-2204-arm' }}
- run: sudo apt-get -y install libgdiplus libgif-dev libglib2.0-dev libcairo2-dev libtiff-dev libexif-dev
+ if: ${{ contains(matrix.options.os, 'ubuntu') }}
+ run: |
+ sudo apt-get update
+ sudo apt-get -y install libgdiplus libgif-dev libglib2.0-dev libcairo2-dev libtiff-dev libexif-dev
+
+ - name: Install libgdi+, which is required for tests running on macos
+ if: ${{ contains(matrix.options.os, 'macos-26') }}
+ run: |
+ brew update
+ brew install mono-libgdiplus
+ # Create symlinks to make libgdiplus discoverable
+ sudo mkdir -p /usr/local/lib
+ sudo ln -sf $(brew --prefix)/lib/libgdiplus.dylib /usr/local/lib/libgdiplus.dylib
+ # Verify installation
+ ls -la $(brew --prefix)/lib/libgdiplus* || echo "libgdiplus not found in brew prefix"
+ ls -la /usr/local/lib/libgdiplus* || echo "libgdiplus not found in /usr/local/lib"
- name: Git Config
shell: bash
@@ -88,18 +142,15 @@ jobs:
fetch-depth: 0
submodules: recursive
- # See https://github.com/actions/checkout/issues/165#issuecomment-657673315
- - name: Git Create LFS FileList
- run: git lfs ls-files -l | cut -d' ' -f1 | sort > .lfs-assets-id
-
+ # Use the warmed key from WarmLFS. Do not recompute or recreate .lfs-assets-id here.
- name: Git Setup LFS Cache
uses: actions/cache@v4
- id: lfs-cache
with:
path: .git/lfs
- key: ${{ runner.os }}-lfs-${{ hashFiles('.lfs-assets-id') }}-v1
+ key: ${{ needs.WarmLFS.outputs.lfs_key }}
- name: Git Pull LFS
+ shell: bash
run: git lfs pull
- name: NuGet Install
@@ -125,7 +176,7 @@ jobs:
uses: actions/setup-dotnet@v4
with:
dotnet-version: |
- 9.0.x
+ 10.0.x
- name: DotNet Build
if: ${{ matrix.options.sdk-preview != true }}
@@ -166,11 +217,8 @@ jobs:
Publish:
needs: [Build]
-
runs-on: ubuntu-latest
-
if: (github.event_name == 'push')
-
steps:
- name: Git Config
shell: bash
@@ -211,4 +259,3 @@ jobs:
run: |
dotnet nuget push .\artifacts\*.nupkg -k ${{secrets.NUGET_TOKEN}} -s https://api.nuget.org/v3/index.json --skip-duplicate
dotnet nuget push .\artifacts\*.snupkg -k ${{secrets.NUGET_TOKEN}} -s https://api.nuget.org/v3/index.json --skip-duplicate
-
diff --git a/.github/workflows/code-coverage.yml b/.github/workflows/code-coverage.yml
index bda6b3961..07ce0408f 100644
--- a/.github/workflows/code-coverage.yml
+++ b/.github/workflows/code-coverage.yml
@@ -4,6 +4,7 @@ on:
schedule:
# 2AM every Tuesday/Thursday
- cron: "0 2 * * 2,4"
+
jobs:
Build:
strategy:
@@ -14,9 +15,15 @@ jobs:
runtime: -x64
codecov: true
- runs-on: ${{matrix.options.os}}
+ runs-on: ${{ matrix.options.os }}
steps:
+ - name: Install libgdi+, which is required for tests running on ubuntu
+ if: ${{ contains(matrix.options.os, 'ubuntu') }}
+ run: |
+ sudo apt-get update
+ sudo apt-get -y install libgdiplus libgif-dev libglib2.0-dev libcairo2-dev libtiff-dev libexif-dev
+
- name: Git Config
shell: bash
run: |
@@ -29,16 +36,21 @@ jobs:
fetch-depth: 0
submodules: recursive
- # See https://github.com/actions/checkout/issues/165#issuecomment-657673315
- - name: Git Create LFS FileList
- run: git lfs ls-files -l | cut -d' ' -f1 | sort > .lfs-assets-id
+ # Deterministic list of LFS object IDs, then compute a portable key:
+ # - `git lfs ls-files -l` lists all tracked LFS objects with their SHA-256
+ # - `awk '{print $1}'` extracts just the SHA field
+ # - `sort` sorts in byte order (hex hashes sort the same everywhere)
+ # This ensures the file content is identical regardless of OS or locale
+ - name: Git Create LFS id list
+ shell: bash
+ run: git lfs ls-files -l | awk '{print $1}' | sort > .lfs-assets-id
- name: Git Setup LFS Cache
uses: actions/cache@v4
id: lfs-cache
with:
path: .git/lfs
- key: ${{ runner.os }}-lfs-${{ hashFiles('.lfs-assets-id') }}-v1
+ key: lfs-${{ hashFiles('.lfs-assets-id') }}-v1
- name: Git Pull LFS
run: git lfs pull
@@ -62,13 +74,13 @@ jobs:
- name: DotNet Build
shell: pwsh
- run: ./ci-build.ps1 "${{matrix.options.framework}}"
+ run: ./ci-build.ps1 "${{ matrix.options.framework }}"
env:
SIXLABORS_TESTING: True
- name: DotNet Test
shell: pwsh
- run: ./ci-test.ps1 "${{matrix.options.os}}" "${{matrix.options.framework}}" "${{matrix.options.runtime}}" "${{matrix.options.codecov}}"
+ run: ./ci-test.ps1 "${{ matrix.options.os }}" "${{ matrix.options.framework }}" "${{ matrix.options.runtime }}" "${{ matrix.options.codecov }}"
env:
SIXLABORS_TESTING: True
XUNIT_PATH: .\tests\ImageSharp.Tests # Required for xunit
diff --git a/Directory.Build.props b/Directory.Build.props
index 26b3cc5af..9bda76f88 100644
--- a/Directory.Build.props
+++ b/Directory.Build.props
@@ -21,9 +21,12 @@
-
-
- preview
+
+ 12.0
+
+
+
+ 14.0
-
-
-
+
+
+
+
+
-
-
-
-
-
+
+
+
+
+
-
+
diff --git a/tests/ImageSharp.Benchmarks/Bulk/FromRgba32Bytes.cs b/tests/ImageSharp.Benchmarks/Bulk/FromRgba32Bytes.cs
index 6cae20853..92d5bcdbf 100644
--- a/tests/ImageSharp.Benchmarks/Bulk/FromRgba32Bytes.cs
+++ b/tests/ImageSharp.Benchmarks/Bulk/FromRgba32Bytes.cs
@@ -62,9 +62,7 @@ public abstract class FromRgba32Bytes
=> PixelOperations.Instance.FromRgba32Bytes(this.configuration, this.source.GetSpan(), this.destination.GetSpan(), this.Count);
}
-public class FromRgba32Bytes_ToRgba32 : FromRgba32Bytes
-{
-}
+public class FromRgba32Bytes_ToRgba32 : FromRgba32Bytes;
public class FromRgba32Bytes_ToBgra32 : FromRgba32Bytes
{
diff --git a/tests/ImageSharp.Benchmarks/Bulk/FromVector4.cs b/tests/ImageSharp.Benchmarks/Bulk/FromVector4.cs
index 53c26a57e..80b096344 100644
--- a/tests/ImageSharp.Benchmarks/Bulk/FromVector4.cs
+++ b/tests/ImageSharp.Benchmarks/Bulk/FromVector4.cs
@@ -73,7 +73,8 @@ public class FromVector4Rgba32 : FromVector4
SimdUtils.HwIntrinsics.NormalizedFloatToByteSaturate(sBytes, dFloats);
}
- private static ReadOnlySpan PermuteMaskDeinterleave8x32 => new byte[] { 0, 0, 0, 0, 4, 0, 0, 0, 1, 0, 0, 0, 5, 0, 0, 0, 2, 0, 0, 0, 6, 0, 0, 0, 3, 0, 0, 0, 7, 0, 0, 0 };
+ private static ReadOnlySpan PermuteMaskDeinterleave8x32 => [0, 0, 0, 0, 4, 0, 0, 0, 1, 0, 0, 0, 5, 0, 0, 0, 2, 0, 0, 0, 6, 0, 0, 0, 3, 0, 0, 0, 7, 0, 0, 0
+ ];
[Benchmark]
public void UseAvx2_Grouped()
diff --git a/tests/ImageSharp.Benchmarks/Bulk/Vector4Factory.cs b/tests/ImageSharp.Benchmarks/Bulk/Vector4Factory.cs
index aa555f5c4..0842a6845 100644
--- a/tests/ImageSharp.Benchmarks/Bulk/Vector4Factory.cs
+++ b/tests/ImageSharp.Benchmarks/Bulk/Vector4Factory.cs
@@ -30,5 +30,5 @@ internal static class Vector4Factory
}
private static float GetRandomFloat(Random rnd, float minVal, float maxVal)
- => (float)rnd.NextDouble() * (maxVal - minVal) + minVal;
+ => ((float)rnd.NextDouble() * (maxVal - minVal)) + minVal;
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Bmp/DecodeBmp.cs b/tests/ImageSharp.Benchmarks/Codecs/Bmp/DecodeBmp.cs
index eb5b3c49d..eec926a23 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Bmp/DecodeBmp.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Bmp/DecodeBmp.cs
@@ -19,12 +19,7 @@ public class DecodeBmp
[GlobalSetup]
public void ReadImages()
- {
- if (this.bmpBytes == null)
- {
- this.bmpBytes = File.ReadAllBytes(this.TestImageFullPath);
- }
- }
+ => this.bmpBytes ??= File.ReadAllBytes(this.TestImageFullPath);
[Params(TestImages.Bmp.Car)]
public string TestImage { get; set; }
@@ -32,16 +27,16 @@ public class DecodeBmp
[Benchmark(Baseline = true, Description = "System.Drawing Bmp")]
public SDSize BmpSystemDrawing()
{
- using var memoryStream = new MemoryStream(this.bmpBytes);
- using var image = SDImage.FromStream(memoryStream);
+ using MemoryStream memoryStream = new(this.bmpBytes);
+ using SDImage image = SDImage.FromStream(memoryStream);
return image.Size;
}
[Benchmark(Description = "ImageSharp Bmp")]
public Size BmpImageSharp()
{
- using var memoryStream = new MemoryStream(this.bmpBytes);
- using var image = Image.Load(memoryStream);
+ using MemoryStream memoryStream = new(this.bmpBytes);
+ using Image image = Image.Load(memoryStream);
return new Size(image.Width, image.Height);
}
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Bmp/EncodeBmp.cs b/tests/ImageSharp.Benchmarks/Codecs/Bmp/EncodeBmp.cs
index 3e6cfa51b..4c0a6c47b 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Bmp/EncodeBmp.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Bmp/EncodeBmp.cs
@@ -12,7 +12,7 @@ namespace SixLabors.ImageSharp.Benchmarks.Codecs;
[Config(typeof(Config.Short))]
public class EncodeBmp
{
- private Stream bmpStream;
+ private FileStream bmpStream;
private SDImage bmpDrawing;
private Image bmpCore;
@@ -40,14 +40,14 @@ public class EncodeBmp
[Benchmark(Baseline = true, Description = "System.Drawing Bmp")]
public void BmpSystemDrawing()
{
- using var memoryStream = new MemoryStream();
+ using MemoryStream memoryStream = new();
this.bmpDrawing.Save(memoryStream, ImageFormat.Bmp);
}
[Benchmark(Description = "ImageSharp Bmp")]
public void BmpImageSharp()
{
- using var memoryStream = new MemoryStream();
+ using MemoryStream memoryStream = new();
this.bmpCore.SaveAsBmp(memoryStream);
}
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Bmp/EncodeBmpMultiple.cs b/tests/ImageSharp.Benchmarks/Codecs/Bmp/EncodeBmpMultiple.cs
index fdef1b2bf..ce54c133b 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Bmp/EncodeBmpMultiple.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Bmp/EncodeBmpMultiple.cs
@@ -10,7 +10,7 @@ namespace SixLabors.ImageSharp.Benchmarks.Codecs;
[Config(typeof(Config.Short))]
public class EncodeBmpMultiple : MultiImageBenchmarkBase.WithImagesPreloaded
{
- protected override IEnumerable InputImageSubfoldersOrFiles => new[] { "Bmp/", "Jpg/baseline" };
+ protected override IEnumerable InputImageSubfoldersOrFiles => ["Bmp/", "Jpg/baseline"];
[Benchmark(Description = "EncodeBmpMultiple - ImageSharp")]
public void EncodeBmpImageSharp()
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Gif/DecodeEncodeGif.cs b/tests/ImageSharp.Benchmarks/Codecs/Gif/DecodeEncodeGif.cs
new file mode 100644
index 000000000..3238e8dac
--- /dev/null
+++ b/tests/ImageSharp.Benchmarks/Codecs/Gif/DecodeEncodeGif.cs
@@ -0,0 +1,59 @@
+// Copyright (c) Six Labors.
+// Licensed under the Six Labors Split License.
+
+using System.Drawing.Imaging;
+using BenchmarkDotNet.Attributes;
+using SixLabors.ImageSharp.Formats.Gif;
+using SixLabors.ImageSharp.Processing;
+using SixLabors.ImageSharp.Processing.Processors.Quantization;
+using SixLabors.ImageSharp.Tests;
+using SDImage = System.Drawing.Image;
+
+namespace SixLabors.ImageSharp.Benchmarks.Codecs;
+
+public abstract class DecodeEncodeGif
+{
+ private MemoryStream outputStream;
+
+ protected abstract GifEncoder Encoder { get; }
+
+ [Params(TestImages.Gif.Leo, TestImages.Gif.Cheers)]
+ public string TestImage { get; set; }
+
+ private string TestImageFullPath => Path.Combine(TestEnvironment.InputImagesDirectoryFullPath, this.TestImage);
+
+ [GlobalSetup]
+ public void Setup() => this.outputStream = new MemoryStream();
+
+ [GlobalCleanup]
+ public void Cleanup() => this.outputStream.Close();
+
+ [Benchmark(Baseline = true)]
+ public void SystemDrawing()
+ {
+ this.outputStream.Position = 0;
+ using SDImage image = SDImage.FromFile(this.TestImageFullPath);
+ image.Save(this.outputStream, ImageFormat.Gif);
+ }
+
+ [Benchmark]
+ public void ImageSharp()
+ {
+ this.outputStream.Position = 0;
+ using Image image = Image.Load(this.TestImageFullPath);
+ image.SaveAsGif(this.outputStream, this.Encoder);
+ }
+}
+
+public class DecodeEncodeGif_DefaultEncoder : DecodeEncodeGif
+{
+ protected override GifEncoder Encoder => new();
+}
+
+public class DecodeEncodeGif_CoarsePaletteEncoder : DecodeEncodeGif
+{
+ protected override GifEncoder Encoder => new()
+ {
+ Quantizer = new WebSafePaletteQuantizer(new QuantizerOptions { Dither = KnownDitherings.Bayer4x4, ColorMatchingMode = ColorMatchingMode.Coarse })
+ };
+}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Gif/DecodeGif.cs b/tests/ImageSharp.Benchmarks/Codecs/Gif/DecodeGif.cs
index 525e9f5e5..117cdd25b 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Gif/DecodeGif.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Gif/DecodeGif.cs
@@ -18,30 +18,24 @@ public class DecodeGif
=> Path.Combine(TestEnvironment.InputImagesDirectoryFullPath, this.TestImage);
[GlobalSetup]
- public void ReadImages()
- {
- if (this.gifBytes == null)
- {
- this.gifBytes = File.ReadAllBytes(this.TestImageFullPath);
- }
- }
+ public void ReadImages() => this.gifBytes ??= File.ReadAllBytes(this.TestImageFullPath);
- [Params(TestImages.Gif.Rings)]
+ [Params(TestImages.Gif.Cheers)]
public string TestImage { get; set; }
[Benchmark(Baseline = true, Description = "System.Drawing Gif")]
public SDSize GifSystemDrawing()
{
- using var memoryStream = new MemoryStream(this.gifBytes);
- using var image = SDImage.FromStream(memoryStream);
+ using MemoryStream memoryStream = new(this.gifBytes);
+ using SDImage image = SDImage.FromStream(memoryStream);
return image.Size;
}
[Benchmark(Description = "ImageSharp Gif")]
public Size GifImageSharp()
{
- using var memoryStream = new MemoryStream(this.gifBytes);
- using var image = Image.Load(memoryStream);
+ using MemoryStream memoryStream = new(this.gifBytes);
+ using Image image = Image.Load(memoryStream);
return new Size(image.Width, image.Height);
}
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Gif/EncodeGif.cs b/tests/ImageSharp.Benchmarks/Codecs/Gif/EncodeGif.cs
index c3644221e..b8f8f7851 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Gif/EncodeGif.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Gif/EncodeGif.cs
@@ -3,6 +3,7 @@
using System.Drawing.Imaging;
using BenchmarkDotNet.Attributes;
+using ImageMagick;
using SixLabors.ImageSharp.Formats.Gif;
using SixLabors.ImageSharp.PixelFormats;
using SixLabors.ImageSharp.Processing;
@@ -12,21 +13,17 @@ using SDImage = System.Drawing.Image;
namespace SixLabors.ImageSharp.Benchmarks.Codecs;
-[Config(typeof(Config.Short))]
-public class EncodeGif
+public abstract class EncodeGif
{
// System.Drawing needs this.
- private Stream bmpStream;
+ private FileStream bmpStream;
private SDImage bmpDrawing;
private Image bmpCore;
+ private MagickImageCollection magickImage;
- // Try to get as close to System.Drawing's output as possible
- private readonly GifEncoder encoder = new GifEncoder
- {
- Quantizer = new WebSafePaletteQuantizer(new QuantizerOptions { Dither = KnownDitherings.Bayer4x4 })
- };
+ protected abstract GifEncoder Encoder { get; }
- [Params(TestImages.Bmp.Car, TestImages.Png.Rgb48Bpp)]
+ [Params(TestImages.Gif.Leo, TestImages.Gif.Cheers)]
public string TestImage { get; set; }
[GlobalSetup]
@@ -34,10 +31,14 @@ public class EncodeGif
{
if (this.bmpStream == null)
{
- this.bmpStream = File.OpenRead(Path.Combine(TestEnvironment.InputImagesDirectoryFullPath, this.TestImage));
+ string filePath = Path.Combine(TestEnvironment.InputImagesDirectoryFullPath, this.TestImage);
+ this.bmpStream = File.OpenRead(filePath);
this.bmpCore = Image.Load(this.bmpStream);
this.bmpStream.Position = 0;
this.bmpDrawing = SDImage.FromStream(this.bmpStream);
+
+ this.bmpStream.Position = 0;
+ this.magickImage = new MagickImageCollection(this.bmpStream);
}
}
@@ -48,19 +49,40 @@ public class EncodeGif
this.bmpStream = null;
this.bmpCore.Dispose();
this.bmpDrawing.Dispose();
+ this.magickImage.Dispose();
}
[Benchmark(Baseline = true, Description = "System.Drawing Gif")]
public void GifSystemDrawing()
{
- using var memoryStream = new MemoryStream();
+ using MemoryStream memoryStream = new();
this.bmpDrawing.Save(memoryStream, ImageFormat.Gif);
}
[Benchmark(Description = "ImageSharp Gif")]
public void GifImageSharp()
{
- using var memoryStream = new MemoryStream();
- this.bmpCore.SaveAsGif(memoryStream, this.encoder);
+ using MemoryStream memoryStream = new();
+ this.bmpCore.SaveAsGif(memoryStream, this.Encoder);
}
+
+ [Benchmark(Description = "Magick.NET Gif")]
+ public void GifMagickNet()
+ {
+ using MemoryStream ms = new();
+ this.magickImage.Write(ms, MagickFormat.Gif);
+ }
+}
+
+public class EncodeGif_DefaultEncoder : EncodeGif
+{
+ protected override GifEncoder Encoder => new();
+}
+
+public class EncodeGif_CoarsePaletteEncoder : EncodeGif
+{
+ protected override GifEncoder Encoder => new()
+ {
+ Quantizer = new WebSafePaletteQuantizer(new QuantizerOptions { Dither = KnownDitherings.Bayer4x4, ColorMatchingMode = ColorMatchingMode.Coarse })
+ };
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Gif/EncodeGifMultiple.cs b/tests/ImageSharp.Benchmarks/Codecs/Gif/EncodeGifMultiple.cs
index 9557f616c..1eca07ec7 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Gif/EncodeGifMultiple.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Gif/EncodeGifMultiple.cs
@@ -15,14 +15,14 @@ public class EncodeGifMultiple : MultiImageBenchmarkBase.WithImagesPreloaded
[Params(InputImageCategory.AllImages)]
public override InputImageCategory InputCategory { get; set; }
- protected override IEnumerable InputImageSubfoldersOrFiles => new[] { "Gif/" };
+ protected override IEnumerable InputImageSubfoldersOrFiles => ["Gif/"];
[Benchmark(Description = "EncodeGifMultiple - ImageSharp")]
public void EncodeGifImageSharp()
=> this.ForEachImageSharpImage((img, ms) =>
{
// Try to get as close to System.Drawing's output as possible
- var options = new GifEncoder
+ GifEncoder options = new()
{
Quantizer = new WebSafePaletteQuantizer(new QuantizerOptions { Dither = KnownDitherings.Bayer4x4 })
};
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_CopyTo2x2.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_CopyTo2x2.cs
index 72b6bb72e..4ea0a92f1 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_CopyTo2x2.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_CopyTo2x2.cs
@@ -185,15 +185,15 @@ public class Block8x8F_CopyTo2x2
ref Vector2 dBottomLeft = ref Unsafe.Add(ref dTopLeft, (uint)destStride);
ref Vector2 dBottomRight = ref Unsafe.Add(ref dBottomLeft, 4);
- var xLeft = new Vector2(sLeft.X);
- var yLeft = new Vector2(sLeft.Y);
- var zLeft = new Vector2(sLeft.Z);
- var wLeft = new Vector2(sLeft.W);
+ Vector2 xLeft = new(sLeft.X);
+ Vector2 yLeft = new(sLeft.Y);
+ Vector2 zLeft = new(sLeft.Z);
+ Vector2 wLeft = new(sLeft.W);
- var xRight = new Vector2(sRight.X);
- var yRight = new Vector2(sRight.Y);
- var zRight = new Vector2(sRight.Z);
- var wRight = new Vector2(sRight.W);
+ Vector2 xRight = new(sRight.X);
+ Vector2 yRight = new(sRight.Y);
+ Vector2 zRight = new(sRight.Z);
+ Vector2 wRight = new(sRight.W);
dTopLeft = xLeft;
Unsafe.Add(ref dTopLeft, 1) = yLeft;
@@ -245,15 +245,15 @@ public class Block8x8F_CopyTo2x2
ref Vector2 dBottomLeft = ref Unsafe.Add(ref dTopLeft, (uint)destStride);
ref Vector2 dBottomRight = ref Unsafe.Add(ref dBottomLeft, 4);
- var xLeft = new Vector4(sLeft.X);
- var yLeft = new Vector4(sLeft.Y);
- var zLeft = new Vector4(sLeft.Z);
- var wLeft = new Vector4(sLeft.W);
+ Vector4 xLeft = new(sLeft.X);
+ Vector4 yLeft = new(sLeft.Y);
+ Vector4 zLeft = new(sLeft.Z);
+ Vector4 wLeft = new(sLeft.W);
- var xRight = new Vector4(sRight.X);
- var yRight = new Vector4(sRight.Y);
- var zRight = new Vector4(sRight.Z);
- var wRight = new Vector4(sRight.W);
+ Vector4 xRight = new(sRight.X);
+ Vector4 yRight = new(sRight.Y);
+ Vector4 zRight = new(sRight.Z);
+ Vector4 wRight = new(sRight.W);
Unsafe.As(ref dTopLeft) = xLeft;
Unsafe.As(ref Unsafe.Add(ref dTopLeft, 1)) = yLeft;
@@ -303,15 +303,15 @@ public class Block8x8F_CopyTo2x2
ref Vector2 dTopLeft = ref Unsafe.Add(ref destBase, (uint)(2 * row * destStride));
ref Vector2 dBottomLeft = ref Unsafe.Add(ref dTopLeft, (uint)destStride);
- var xLeft = new Vector4(sLeft.X);
- var yLeft = new Vector4(sLeft.Y);
- var zLeft = new Vector4(sLeft.Z);
- var wLeft = new Vector4(sLeft.W);
+ Vector4 xLeft = new(sLeft.X);
+ Vector4 yLeft = new(sLeft.Y);
+ Vector4 zLeft = new(sLeft.Z);
+ Vector4 wLeft = new(sLeft.W);
- var xRight = new Vector4(sRight.X);
- var yRight = new Vector4(sRight.Y);
- var zRight = new Vector4(sRight.Z);
- var wRight = new Vector2(sRight.W);
+ Vector4 xRight = new(sRight.X);
+ Vector4 yRight = new(sRight.Y);
+ Vector4 zRight = new(sRight.Z);
+ Vector2 wRight = new(sRight.W);
Unsafe.As(ref dTopLeft) = xLeft;
Unsafe.As(ref Unsafe.Add(ref dTopLeft, 1)) = yLeft;
@@ -362,25 +362,25 @@ public class Block8x8F_CopyTo2x2
ref Vector4 dTopLeft = ref Unsafe.As(ref Unsafe.Add(ref destBase, (uint)offset));
ref Vector4 dBottomLeft = ref Unsafe.As(ref Unsafe.Add(ref destBase, (uint)(offset + destStride)));
- var xyLeft = new Vector4(sLeft.X)
+ Vector4 xyLeft = new(sLeft.X)
{
Z = sLeft.Y,
W = sLeft.Y
};
- var zwLeft = new Vector4(sLeft.Z)
+ Vector4 zwLeft = new(sLeft.Z)
{
Z = sLeft.W,
W = sLeft.W
};
- var xyRight = new Vector4(sRight.X)
+ Vector4 xyRight = new(sRight.X)
{
Z = sRight.Y,
W = sRight.Y
};
- var zwRight = new Vector4(sRight.Z)
+ Vector4 zwRight = new(sRight.Z)
{
Z = sRight.W,
W = sRight.W
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_DivideRound.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_DivideRound.cs
index efc347586..45c6f63b9 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_DivideRound.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_DivideRound.cs
@@ -19,8 +19,8 @@ namespace SixLabors.ImageSharp.Benchmarks.Codecs.Jpeg.BlockOperations;
public unsafe class Block8x8F_DivideRound
{
private const int ExecutionCount = 5; // Added this to reduce the effect of copying the blocks
- private static readonly Vector4 MinusOne = new Vector4(-1);
- private static readonly Vector4 Half = new Vector4(0.5f);
+ private static readonly Vector4 MinusOne = new(-1);
+ private static readonly Vector4 Half = new(0.5f);
private Block8x8F inputDividend;
private Block8x8F inputDivisor;
@@ -140,7 +140,7 @@ public unsafe class Block8x8F_DivideRound
[MethodImpl(MethodImplOptions.AggressiveInlining)]
private static Vector4 DivideRound(Vector4 dividend, Vector4 divisor)
{
- var sign = Vector4.Min(dividend, Vector4.One);
+ Vector4 sign = Vector4.Min(dividend, Vector4.One);
sign = Vector4.Max(sign, MinusOne);
return (dividend / divisor) + (sign * Half);
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_LoadFromInt16.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_LoadFromInt16.cs
index 91255c946..25b5e973e 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_LoadFromInt16.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_LoadFromInt16.cs
@@ -12,8 +12,7 @@ namespace SixLabors.ImageSharp.Benchmarks.Codecs.Jpeg.BlockOperations;
public class Block8x8F_LoadFromInt16
{
private Block8x8 source;
-
- private Block8x8F dest = default;
+ private Block8x8F destination;
[GlobalSetup]
public void Setup()
@@ -30,16 +29,10 @@ public class Block8x8F_LoadFromInt16
}
[Benchmark(Baseline = true)]
- public void Scalar()
- {
- this.dest.LoadFromInt16Scalar(ref this.source);
- }
+ public void Scalar() => this.destination.LoadFromInt16Scalar(ref this.source);
[Benchmark]
- public void ExtendedAvx2()
- {
- this.dest.LoadFromInt16ExtendedAvx2(ref this.source);
- }
+ public void ExtendedAvx2() => this.destination.LoadFromInt16ExtendedVector256(ref this.source);
// RESULT:
// Method | Mean | Error | StdDev | Scaled |
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_MultiplyInPlaceBlock.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_MultiplyInPlaceBlock.cs
index 722b09587..3c03f3e05 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_MultiplyInPlaceBlock.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_MultiplyInPlaceBlock.cs
@@ -20,7 +20,7 @@ public class Block8x8F_MultiplyInPlaceBlock
private static Block8x8F Create8x8FloatData()
{
- var result = new float[64];
+ float[] result = new float[64];
for (int i = 0; i < 8; i++)
{
for (int j = 0; j < 8; j++)
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_Quantize.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_Quantize.cs
index b1718759e..88b8877e5 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_Quantize.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_Quantize.cs
@@ -11,7 +11,7 @@ public class Block8x8F_Quantize
{
private Block8x8F block = CreateFromScalar(1);
private Block8x8F quant = CreateFromScalar(1);
- private Block8x8 result = default;
+ private Block8x8 result;
[Benchmark]
public short Quantize()
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_Round.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_Round.cs
index 8a520b22d..1d8385168 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_Round.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_Round.cs
@@ -36,7 +36,7 @@ public unsafe class Block8x8F_Round
if (ptr % 16 != 0)
{
- throw new Exception("ptr is unaligned");
+ throw new InvalidOperationException("ptr is unaligned");
}
this.alignedPtr = (float*)ptr;
@@ -67,21 +67,21 @@ public unsafe class Block8x8F_Round
ref Block8x8F b = ref this.block;
ref Vector row0 = ref Unsafe.As>(ref b.V0L);
- row0 = SimdUtils.FastRound(row0);
+ row0 = row0.FastRound();
ref Vector row1 = ref Unsafe.As>(ref b.V1L);
- row1 = SimdUtils.FastRound(row1);
+ row1 = row1.FastRound();
ref Vector row2 = ref Unsafe.As>(ref b.V2L);
- row2 = SimdUtils.FastRound(row2);
+ row2 = row2.FastRound();
ref Vector row3 = ref Unsafe.As>(ref b.V3L);
- row3 = SimdUtils.FastRound(row3);
+ row3 = row3.FastRound();
ref Vector row4 = ref Unsafe.As>(ref b.V4L);
- row4 = SimdUtils.FastRound(row4);
+ row4 = row4.FastRound();
ref Vector row5 = ref Unsafe.As>(ref b.V5L);
- row5 = SimdUtils.FastRound(row5);
+ row5 = row5.FastRound();
ref Vector row6 = ref Unsafe.As>(ref b.V6L);
- row6 = SimdUtils.FastRound(row6);
+ row6 = row6.FastRound();
ref Vector row7 = ref Unsafe.As>(ref b.V7L);
- row7 = SimdUtils.FastRound(row7);
+ row7 = row7.FastRound();
}
[Benchmark]
@@ -90,21 +90,21 @@ public unsafe class Block8x8F_Round
ref Block8x8F b = ref Unsafe.AsRef(this.alignedPtr);
ref Vector row0 = ref Unsafe.As>(ref b.V0L);
- row0 = SimdUtils.FastRound(row0);
+ row0 = row0.FastRound();
ref Vector row1 = ref Unsafe.As>(ref b.V1L);
- row1 = SimdUtils.FastRound(row1);
+ row1 = row1.FastRound();
ref Vector row2 = ref Unsafe.As>(ref b.V2L);
- row2 = SimdUtils.FastRound(row2);
+ row2 = row2.FastRound();
ref Vector row3 = ref Unsafe.As>(ref b.V3L);
- row3 = SimdUtils.FastRound(row3);
+ row3 = row3.FastRound();
ref Vector row4 = ref Unsafe.As>(ref b.V4L);
- row4 = SimdUtils.FastRound(row4);
+ row4 = row4.FastRound();
ref Vector row5 = ref Unsafe.As>(ref b.V5L);
- row5 = SimdUtils.FastRound(row5);
+ row5 = row5.FastRound();
ref Vector row6 = ref Unsafe.As>(ref b.V6L);
- row6 = SimdUtils.FastRound(row6);
+ row6 = row6.FastRound();
ref Vector row7 = ref Unsafe.As>(ref b.V7L);
- row7 = SimdUtils.FastRound(row7);
+ row7 = row7.FastRound();
}
[Benchmark]
@@ -117,20 +117,20 @@ public unsafe class Block8x8F_Round
ref Vector row2 = ref Unsafe.As>(ref b.V2L);
ref Vector row3 = ref Unsafe.As>(ref b.V3L);
- row0 = SimdUtils.FastRound(row0);
- row1 = SimdUtils.FastRound(row1);
- row2 = SimdUtils.FastRound(row2);
- row3 = SimdUtils.FastRound(row3);
+ row0 = row0.FastRound();
+ row1 = row1.FastRound();
+ row2 = row2.FastRound();
+ row3 = row3.FastRound();
row0 = ref Unsafe.As>(ref b.V4L);
row1 = ref Unsafe.As>(ref b.V5L);
row2 = ref Unsafe.As>(ref b.V6L);
row3 = ref Unsafe.As>(ref b.V7L);
- row0 = SimdUtils.FastRound(row0);
- row1 = SimdUtils.FastRound(row1);
- row2 = SimdUtils.FastRound(row2);
- row3 = SimdUtils.FastRound(row3);
+ row0 = row0.FastRound();
+ row1 = row1.FastRound();
+ row2 = row2.FastRound();
+ row3 = row3.FastRound();
}
[Benchmark]
@@ -174,7 +174,7 @@ public unsafe class Block8x8F_Round
}
[Benchmark]
- public unsafe void Sse41_V2()
+ public void Sse41_V2()
{
ref Vector128 p = ref Unsafe.As>(ref this.block);
p = Sse41.RoundToNearestInteger(p);
@@ -214,7 +214,7 @@ public unsafe class Block8x8F_Round
}
[Benchmark]
- public unsafe void Sse41_V3()
+ public void Sse41_V3()
{
ref Vector128 p = ref Unsafe.As>(ref this.block);
p = Sse41.RoundToNearestInteger(p);
@@ -228,7 +228,7 @@ public unsafe class Block8x8F_Round
}
[Benchmark]
- public unsafe void Sse41_V4()
+ public void Sse41_V4()
{
ref Vector128 p = ref Unsafe.As>(ref this.block);
nuint offset = (uint)sizeof(Vector128);
@@ -271,7 +271,7 @@ public unsafe class Block8x8F_Round
}
[Benchmark]
- public unsafe void Sse41_V5_Unaligned()
+ public void Sse41_V5_Unaligned()
{
float* p = this.alignedPtr + 1;
@@ -356,7 +356,7 @@ public unsafe class Block8x8F_Round
}
[Benchmark]
- public unsafe void Sse41_V5_Aligned()
+ public void Sse41_V5_Aligned()
{
float* p = this.alignedPtr;
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_Transpose.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_Transpose.cs
index 07907f21d..caca630bc 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_Transpose.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/BlockOperations/Block8x8F_Transpose.cs
@@ -14,7 +14,7 @@ public class Block8x8F_Transpose
[Benchmark]
public float TransposeInplace()
{
- this.source.TransposeInplace();
+ this.source.TransposeInPlace();
return this.source[0];
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/CmykColorConversion.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/CmykColorConversion.cs
index 9189bec37..a1ba3fb8d 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/CmykColorConversion.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/CmykColorConversion.cs
@@ -17,32 +17,32 @@ public class CmykColorConversion : ColorConversionBenchmark
[Benchmark(Baseline = true)]
public void Scalar()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.CmykScalar(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.CmykScalar(8).ConvertToRgbInPlace(values);
}
[Benchmark]
- public void SimdVector8()
+ public void SimdVector128()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.CmykVector(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.CmykVector128(8).ConvertToRgbInPlace(values);
}
[Benchmark]
- public void SimdVectorAvx()
+ public void SimdVector256()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.CmykAvx(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.CmykVector256(8).ConvertToRgbInPlace(values);
}
[Benchmark]
- public void SimdVectorArm64()
+ public void SimdVector512()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.CmykArm64(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.CmykVector512(8).ConvertToRgbInPlace(values);
}
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/ColorConversionBenchmark.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/ColorConversionBenchmark.cs
index 8964667b7..436aa9bcd 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/ColorConversionBenchmark.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/ColorConversionBenchmark.cs
@@ -38,11 +38,11 @@ public abstract class ColorConversionBenchmark
float minVal = 0f,
float maxVal = 255f)
{
- var rnd = new Random(42);
- var buffers = new Buffer2D[componentCount];
+ Random rnd = new(42);
+ Buffer2D[] buffers = new Buffer2D[componentCount];
for (int i = 0; i < componentCount; i++)
{
- var values = new float[inputBufferLength];
+ float[] values = new float[inputBufferLength];
for (int j = 0; j < inputBufferLength; j++)
{
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/GrayscaleColorConversion.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/GrayscaleColorConversion.cs
index a1d85ef46..3ade4279f 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/GrayscaleColorConversion.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/GrayscaleColorConversion.cs
@@ -7,9 +7,9 @@ using SixLabors.ImageSharp.Formats.Jpeg.Components;
namespace SixLabors.ImageSharp.Benchmarks.Codecs.Jpeg;
[Config(typeof(Config.Short))]
-public class GrayscaleColorConversion : ColorConversionBenchmark
+public class GrayScaleColorConversion : ColorConversionBenchmark
{
- public GrayscaleColorConversion()
+ public GrayScaleColorConversion()
: base(1)
{
}
@@ -17,24 +17,32 @@ public class GrayscaleColorConversion : ColorConversionBenchmark
[Benchmark(Baseline = true)]
public void Scalar()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.GrayscaleScalar(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.GrayScaleScalar(8).ConvertToRgbInPlace(values);
}
[Benchmark]
- public void SimdVectorAvx()
+ public void SimdVector128()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.GrayscaleAvx(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.GrayScaleVector128(8).ConvertToRgbInPlace(values);
}
[Benchmark]
- public void SimdVectorArm()
+ public void SimdVector256()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.GrayscaleArm(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.GrayScaleVector256(8).ConvertToRgbInPlace(values);
+ }
+
+ [Benchmark]
+ public void SimdVector512()
+ {
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
+
+ new JpegColorConverterBase.GrayScaleVector512(8).ConvertToRgbInPlace(values);
}
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/RgbColorConversion.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/RgbColorConversion.cs
index 5e2b6fe86..2916dcdce 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/RgbColorConversion.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/RgbColorConversion.cs
@@ -17,32 +17,32 @@ public class RgbColorConversion : ColorConversionBenchmark
[Benchmark(Baseline = true)]
public void Scalar()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.RgbScalar(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.RgbScalar(8).ConvertToRgbInPlace(values);
}
[Benchmark]
- public void SimdVector8()
+ public void SimdVector128()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.RgbVector(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.RgbVector128(8).ConvertToRgbInPlace(values);
}
[Benchmark]
- public void SimdVectorAvx()
+ public void SimdVector256()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.RgbAvx(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.RgbVector256(8).ConvertToRgbInPlace(values);
}
[Benchmark]
- public void SimdVectorArm()
+ public void SimdVector512()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.RgbArm(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.RgbVector512(8).ConvertToRgbInPlace(values);
}
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/YCbCrColorConversion.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/YCbCrColorConversion.cs
index f8621c250..fbd762af4 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/YCbCrColorConversion.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/YCbCrColorConversion.cs
@@ -17,32 +17,32 @@ public class YCbCrColorConversion : ColorConversionBenchmark
[Benchmark]
public void Scalar()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.YCbCrScalar(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.YCbCrScalar(8).ConvertToRgbInPlace(values);
}
[Benchmark]
- public void SimdVector8()
+ public void SimdVector128()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.YCbCrVector(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.YCbCrVector128(8).ConvertToRgbInPlace(values);
}
[Benchmark]
- public void SimdVectorAvx()
+ public void SimdVector256()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.YCbCrAvx(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.YCbCrVector256(8).ConvertToRgbInPlace(values);
}
[Benchmark]
- public void SimdVectorArm()
+ public void SimdVector512()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.YCbCrArm(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.YCbCrVector512(8).ConvertToRgbInPlace(values);
}
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/YccKColorConverter.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/YccKColorConverter.cs
index a414b6ed4..e6b04c152 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/YccKColorConverter.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/ColorConversion/YccKColorConverter.cs
@@ -17,32 +17,32 @@ public class YccKColorConverter : ColorConversionBenchmark
[Benchmark(Baseline = true)]
public void Scalar()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.YccKScalar(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.YccKScalar(8).ConvertToRgbInPlace(values);
}
[Benchmark]
- public void SimdVector8()
+ public void SimdVector128()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.YccKVector(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.YccKVector128(8).ConvertToRgbInPlace(values);
}
[Benchmark]
- public void SimdVectorAvx2()
+ public void SimdVector256()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.YccKAvx(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.YccKVector256(8).ConvertToRgbInPlace(values);
}
[Benchmark]
- public void SimdVectorArm64()
+ public void SimdVector512()
{
- var values = new JpegColorConverterBase.ComponentValues(this.Input, 0);
+ JpegColorConverterBase.ComponentValues values = new(this.Input, 0);
- new JpegColorConverterBase.YccKArm64(8).ConvertToRgbInplace(values);
+ new JpegColorConverterBase.YccKVector512(8).ConvertToRgbInPlace(values);
}
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpeg.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpeg.cs
index 0dc6d26bc..dbd255722 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpeg.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpeg.cs
@@ -8,6 +8,7 @@ using SixLabors.ImageSharp.Tests;
namespace SixLabors.ImageSharp.Benchmarks.Codecs.Jpeg;
+[Config(typeof(Config.HwIntrinsics_SSE_AVX))]
public class DecodeJpeg
{
private JpegDecoder decoder;
@@ -21,7 +22,7 @@ public class DecodeJpeg
this.preloadedImageStream = new MemoryStream(bytes);
}
- private void GenericBechmark()
+ private void GenericBenchmark()
{
this.preloadedImageStream.Position = 0;
using Image img = this.decoder.Decode(DecoderOptions.Default, this.preloadedImageStream);
@@ -51,16 +52,16 @@ public class DecodeJpeg
}
[Benchmark(Description = "Baseline 4:4:4 Interleaved")]
- public void JpegBaselineInterleaved444() => this.GenericBechmark();
+ public void JpegBaselineInterleaved444() => this.GenericBenchmark();
[Benchmark(Description = "Baseline 4:2:0 Interleaved")]
- public void JpegBaselineInterleaved420() => this.GenericBechmark();
+ public void JpegBaselineInterleaved420() => this.GenericBenchmark();
[Benchmark(Description = "Baseline 4:0:0 (grayscale)")]
- public void JpegBaseline400() => this.GenericBechmark();
+ public void JpegBaseline400() => this.GenericBenchmark();
[Benchmark(Description = "Progressive 4:2:0 Non-Interleaved")]
- public void JpegProgressiveNonInterleaved420() => this.GenericBechmark();
+ public void JpegProgressiveNonInterleaved420() => this.GenericBenchmark();
}
/*
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpegParseStreamOnly.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpegParseStreamOnly.cs
index f5178390f..e7b66576d 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpegParseStreamOnly.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpegParseStreamOnly.cs
@@ -2,9 +2,11 @@
// Licensed under the Six Labors Split License.
using BenchmarkDotNet.Attributes;
+using SixLabors.ImageSharp.Formats;
using SixLabors.ImageSharp.Formats.Jpeg;
using SixLabors.ImageSharp.Formats.Jpeg.Components.Decoder;
using SixLabors.ImageSharp.IO;
+using SixLabors.ImageSharp.Metadata.Profiles.Icc;
using SixLabors.ImageSharp.Tests;
using SDSize = System.Drawing.Size;
@@ -27,20 +29,20 @@ public class DecodeJpegParseStreamOnly
[Benchmark(Baseline = true, Description = "System.Drawing FULL")]
public SDSize JpegSystemDrawing()
{
- using var memoryStream = new MemoryStream(this.jpegBytes);
- using var image = System.Drawing.Image.FromStream(memoryStream);
+ using MemoryStream memoryStream = new(this.jpegBytes);
+ using System.Drawing.Image image = System.Drawing.Image.FromStream(memoryStream);
return image.Size;
}
[Benchmark(Description = "JpegDecoderCore.ParseStream")]
public void ParseStream()
{
- using var memoryStream = new MemoryStream(this.jpegBytes);
- using var bufferedStream = new BufferedReadStream(Configuration.Default, memoryStream);
- var options = new JpegDecoderOptions() { GeneralOptions = new() { SkipMetadata = true } };
+ using MemoryStream memoryStream = new(this.jpegBytes);
+ using BufferedReadStream bufferedStream = new(Configuration.Default, memoryStream);
+ JpegDecoderOptions options = new() { GeneralOptions = new DecoderOptions { SkipMetadata = true } };
- using var decoder = new JpegDecoderCore(options);
- var spectralConverter = new NoopSpectralConverter();
+ using JpegDecoderCore decoder = new(options);
+ NoopSpectralConverter spectralConverter = new();
decoder.ParseStream(bufferedStream, spectralConverter, cancellationToken: default);
}
@@ -48,9 +50,9 @@ public class DecodeJpegParseStreamOnly
// Nor we need to allocate final pixel buffer
// Note: this still introduces virtual method call overhead for baseline interleaved images
// There's no way to eliminate it as spectral conversion is built into the scan decoding loop for memory footprint reduction
- private class NoopSpectralConverter : SpectralConverter
+ private sealed class NoopSpectralConverter : SpectralConverter
{
- public override void ConvertStrideBaseline()
+ public override void ConvertStrideBaseline(IccProfile iccProfile)
{
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpeg_Aggregate.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpeg_Aggregate.cs
index 389fec88b..9f69f613e 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpeg_Aggregate.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpeg_Aggregate.cs
@@ -17,21 +17,21 @@ namespace SixLabors.ImageSharp.Benchmarks.Codecs.Jpeg;
public class DecodeJpeg_Aggregate : MultiImageBenchmarkBase
{
protected override IEnumerable InputImageSubfoldersOrFiles
- => new[]
- {
+ =>
+ [
TestImages.Jpeg.BenchmarkSuite.Jpeg400_SmallMonochrome,
TestImages.Jpeg.BenchmarkSuite.Jpeg420Exif_MidSizeYCbCr,
TestImages.Jpeg.BenchmarkSuite.Lake_Small444YCbCr,
TestImages.Jpeg.BenchmarkSuite.MissingFF00ProgressiveBedroom159_MidSize420YCbCr,
TestImages.Jpeg.BenchmarkSuite.ExifGetString750Transform_Huge420YCbCr,
- };
+ ];
[Params(InputImageCategory.AllImages)]
public override InputImageCategory InputCategory { get; set; }
[Benchmark]
public void ImageSharp()
- => this.ForEachStream(ms => Image.Load(ms));
+ => this.ForEachStream(Image.Load);
[Benchmark(Baseline = true)]
public void SystemDrawing()
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpeg_ImageSpecific.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpeg_ImageSpecific.cs
index 08df2580d..9a4ee3967 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpeg_ImageSpecific.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/DecodeJpeg_ImageSpecific.cs
@@ -35,26 +35,21 @@ public class DecodeJpeg_ImageSpecific
[GlobalSetup]
public void ReadImages()
- {
- if (this.jpegBytes == null)
- {
- this.jpegBytes = File.ReadAllBytes(this.TestImageFullPath);
- }
- }
+ => this.jpegBytes ??= File.ReadAllBytes(this.TestImageFullPath);
[Benchmark(Baseline = true)]
public SDSize SystemDrawing()
{
- using var memoryStream = new MemoryStream(this.jpegBytes);
- using var image = SDImage.FromStream(memoryStream);
+ using MemoryStream memoryStream = new(this.jpegBytes);
+ using SDImage image = SDImage.FromStream(memoryStream);
return image.Size;
}
[Benchmark]
public Size ImageSharp()
{
- using var memoryStream = new MemoryStream(this.jpegBytes);
- using var image = Image.Load(new DecoderOptions() { SkipMetadata = true }, memoryStream);
+ using MemoryStream memoryStream = new(this.jpegBytes);
+ using Image image = Image.Load(new DecoderOptions { SkipMetadata = true }, memoryStream);
return new Size(image.Width, image.Height);
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/EncodeJpegComparison.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/EncodeJpegComparison.cs
index deb3125b3..c7cecd1a5 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/EncodeJpegComparison.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/EncodeJpegComparison.cs
@@ -19,11 +19,6 @@ public class EncodeJpegComparison
{
// Big enough, 4:4:4 chroma sampling
private const string TestImage = TestImages.Jpeg.Baseline.Calliphora;
-
- // Change/add parameters for extra benchmarks
- [Params(75, 90, 100)]
- public int Quality;
-
private MemoryStream destinationStream;
// ImageSharp
@@ -33,6 +28,10 @@ public class EncodeJpegComparison
// SkiaSharp
private SKBitmap imageSkiaSharp;
+ // Change/add parameters for extra benchmarks
+ [Params(75, 90, 100)]
+ public int Quality { get; set; }
+
[GlobalSetup(Target = nameof(BenchmarkImageSharp))]
public void SetupImageSharp()
{
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/EncodeJpegFeatures.cs b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/EncodeJpegFeatures.cs
index 0692c5a3b..858917995 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Jpeg/EncodeJpegFeatures.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Jpeg/EncodeJpegFeatures.cs
@@ -20,19 +20,19 @@ public class EncodeJpegFeatures
// No metadata
private const string TestImage = TestImages.Jpeg.Baseline.Calliphora;
- public static IEnumerable ColorSpaceValues => new[]
- {
+ public static IEnumerable ColorSpaceValues =>
+ [
JpegColorType.Luminance,
JpegColorType.Rgb,
JpegColorType.YCbCrRatio420,
JpegColorType.YCbCrRatio444,
- };
+ ];
[Params(75, 90, 100)]
- public int Quality;
+ public int Quality { get; set; }
[ParamsSource(nameof(ColorSpaceValues), Priority = -100)]
- public JpegColorType TargetColorSpace;
+ public JpegColorType TargetColorSpace { get; set; }
private Image bmpCore;
private JpegEncoder encoder;
diff --git a/tests/ImageSharp.Benchmarks/Codecs/MultiImageBenchmarkBase.cs b/tests/ImageSharp.Benchmarks/Codecs/MultiImageBenchmarkBase.cs
index b75d012f9..0adc52441 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/MultiImageBenchmarkBase.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/MultiImageBenchmarkBase.cs
@@ -11,11 +11,11 @@ namespace SixLabors.ImageSharp.Benchmarks.Codecs;
public abstract class MultiImageBenchmarkBase
{
- protected Dictionary FileNamesToBytes { get; set; } = new Dictionary();
+ protected Dictionary FileNamesToBytes { get; set; } = [];
- protected Dictionary> FileNamesToImageSharpImages { get; set; } = new Dictionary>();
+ protected Dictionary> FileNamesToImageSharpImages { get; set; } = [];
- protected Dictionary FileNamesToSystemDrawingImages { get; set; } = new Dictionary();
+ protected Dictionary FileNamesToSystemDrawingImages { get; set; } = [];
///
/// The values of this enum separate input files into categories.
@@ -43,12 +43,12 @@ public abstract class MultiImageBenchmarkBase
protected virtual string BaseFolder => TestEnvironment.InputImagesDirectoryFullPath;
- protected virtual IEnumerable SearchPatterns => new[] { "*.*" };
+ protected virtual IEnumerable SearchPatterns => ["*.*"];
///
/// Gets the file names containing these strings are substrings are not processed by the benchmark.
///
- protected virtual IEnumerable ExcludeSubstringsInFileNames => new[] { "badeof", "BadEof", "CriticalEOF" };
+ protected virtual IEnumerable ExcludeSubstringsInFileNames => ["badeof", "BadEof", "CriticalEOF"];
///
/// Gets folders containing files OR files to be processed by the benchmark.
@@ -70,7 +70,7 @@ public abstract class MultiImageBenchmarkBase
InputImageCategory.AllImages => input,
InputImageCategory.SmallImagesOnly => input.Where(kv => checkIfSmall(kv.Value)),
InputImageCategory.LargeImagesOnly => input.Where(kv => !checkIfSmall(kv.Value)),
- _ => throw new ArgumentOutOfRangeException(),
+ _ => throw new ArgumentOutOfRangeException(nameof(input), "Invalid input category")
};
protected IEnumerable> FileNames2Bytes
@@ -86,7 +86,7 @@ public abstract class MultiImageBenchmarkBase
{
if (!Vector.IsHardwareAccelerated)
{
- throw new Exception("Vector.IsHardwareAccelerated == false! Check your build settings!");
+ throw new InvalidOperationException("Vector.IsHardwareAccelerated == false! Check your build settings!");
}
// Console.WriteLine("Vector.IsHardwareAccelerated: " + Vector.IsHardwareAccelerated);
@@ -103,13 +103,13 @@ public abstract class MultiImageBenchmarkBase
continue;
}
- string[] excludeStrings = this.ExcludeSubstringsInFileNames.Select(s => s.ToLower()).ToArray();
+ string[] excludeStrings = this.ExcludeSubstringsInFileNames.ToArray();
string[] allFiles =
this.SearchPatterns.SelectMany(
f =>
Directory.EnumerateFiles(path, f, SearchOption.AllDirectories)
- .Where(fn => !excludeStrings.Any(excludeStr => fn.ToLower().Contains(excludeStr)))).ToArray();
+ .Where(fn => !excludeStrings.Any(excludeStr => fn.Contains(excludeStr, StringComparison.OrdinalIgnoreCase)))).ToArray();
foreach (string fn in allFiles)
{
@@ -126,7 +126,7 @@ public abstract class MultiImageBenchmarkBase
{
foreach (KeyValuePair kv in this.FileNames2Bytes)
{
- using var memoryStream = new MemoryStream(kv.Value);
+ using MemoryStream memoryStream = new(kv.Value);
try
{
object obj = operation(memoryStream);
@@ -150,7 +150,7 @@ public abstract class MultiImageBenchmarkBase
byte[] bytes = kv.Value;
string fn = kv.Key;
- using (var ms1 = new MemoryStream(bytes))
+ using (MemoryStream ms1 = new(bytes))
{
this.FileNamesToImageSharpImages[fn] = Image.Load(ms1);
}
@@ -191,7 +191,7 @@ public abstract class MultiImageBenchmarkBase
protected void ForEachImageSharpImage(Func, MemoryStream, object> operation)
{
- using var workStream = new MemoryStream();
+ using MemoryStream workStream = new();
this.ForEachImageSharpImage(
img =>
{
@@ -222,7 +222,7 @@ public abstract class MultiImageBenchmarkBase
protected void ForEachSystemDrawingImage(Func operation)
{
- using var workStream = new MemoryStream();
+ using MemoryStream workStream = new();
this.ForEachSystemDrawingImage(
img =>
{
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Png/EncodeIndexedPng.cs b/tests/ImageSharp.Benchmarks/Codecs/Png/EncodeIndexedPng.cs
index a45e7aea9..125b42680 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Png/EncodeIndexedPng.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Png/EncodeIndexedPng.cs
@@ -18,7 +18,7 @@ namespace SixLabors.ImageSharp.Benchmarks.Codecs;
public class EncodeIndexedPng
{
// System.Drawing needs this.
- private Stream bmpStream;
+ private FileStream bmpStream;
private Image bmpCore;
[GlobalSetup]
@@ -43,48 +43,48 @@ public class EncodeIndexedPng
[Benchmark(Baseline = true, Description = "ImageSharp Octree Png")]
public void PngCoreOctree()
{
- using var memoryStream = new MemoryStream();
- var options = new PngEncoder { Quantizer = KnownQuantizers.Octree };
+ using MemoryStream memoryStream = new();
+ PngEncoder options = new() { Quantizer = KnownQuantizers.Octree };
this.bmpCore.SaveAsPng(memoryStream, options);
}
[Benchmark(Description = "ImageSharp Octree NoDither Png")]
public void PngCoreOctreeNoDither()
{
- using var memoryStream = new MemoryStream();
- var options = new PngEncoder { Quantizer = new OctreeQuantizer(new QuantizerOptions { Dither = null }) };
+ using MemoryStream memoryStream = new();
+ PngEncoder options = new() { Quantizer = new OctreeQuantizer(new QuantizerOptions { Dither = null }) };
this.bmpCore.SaveAsPng(memoryStream, options);
}
[Benchmark(Description = "ImageSharp Palette Png")]
public void PngCorePalette()
{
- using var memoryStream = new MemoryStream();
- var options = new PngEncoder { Quantizer = KnownQuantizers.WebSafe };
+ using MemoryStream memoryStream = new();
+ PngEncoder options = new() { Quantizer = KnownQuantizers.WebSafe };
this.bmpCore.SaveAsPng(memoryStream, options);
}
[Benchmark(Description = "ImageSharp Palette NoDither Png")]
public void PngCorePaletteNoDither()
{
- using var memoryStream = new MemoryStream();
- var options = new PngEncoder { Quantizer = new WebSafePaletteQuantizer(new QuantizerOptions { Dither = null }) };
+ using MemoryStream memoryStream = new();
+ PngEncoder options = new() { Quantizer = new WebSafePaletteQuantizer(new QuantizerOptions { Dither = null }) };
this.bmpCore.SaveAsPng(memoryStream, options);
}
[Benchmark(Description = "ImageSharp Wu Png")]
public void PngCoreWu()
{
- using var memoryStream = new MemoryStream();
- var options = new PngEncoder { Quantizer = KnownQuantizers.Wu };
+ using MemoryStream memoryStream = new();
+ PngEncoder options = new() { Quantizer = KnownQuantizers.Wu };
this.bmpCore.SaveAsPng(memoryStream, options);
}
[Benchmark(Description = "ImageSharp Wu NoDither Png")]
public void PngCoreWuNoDither()
{
- using var memoryStream = new MemoryStream();
- var options = new PngEncoder { Quantizer = new WuQuantizer(new QuantizerOptions { Dither = null }), ColorType = PngColorType.Palette };
+ using MemoryStream memoryStream = new();
+ PngEncoder options = new() { Quantizer = new WuQuantizer(new QuantizerOptions { Dither = null }), ColorType = PngColorType.Palette };
this.bmpCore.SaveAsPng(memoryStream, options);
}
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Png/EncodePng.cs b/tests/ImageSharp.Benchmarks/Codecs/Png/EncodePng.cs
index 428791478..30a10af09 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Png/EncodePng.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Png/EncodePng.cs
@@ -14,7 +14,7 @@ namespace SixLabors.ImageSharp.Benchmarks.Codecs;
public class EncodePng
{
// System.Drawing needs this.
- private Stream bmpStream;
+ private FileStream bmpStream;
private SDImage bmpDrawing;
private Image bmpCore;
@@ -46,15 +46,15 @@ public class EncodePng
[Benchmark(Baseline = true, Description = "System.Drawing Png")]
public void PngSystemDrawing()
{
- using var memoryStream = new MemoryStream();
+ using MemoryStream memoryStream = new();
this.bmpDrawing.Save(memoryStream, ImageFormat.Png);
}
[Benchmark(Description = "ImageSharp Png")]
public void PngCore()
{
- using var memoryStream = new MemoryStream();
- var encoder = new PngEncoder { FilterMethod = PngFilterMethod.None };
+ using MemoryStream memoryStream = new();
+ PngEncoder encoder = new() { FilterMethod = PngFilterMethod.None };
this.bmpCore.SaveAsPng(memoryStream, encoder);
}
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Tga/DecodeTga.cs b/tests/ImageSharp.Benchmarks/Codecs/Tga/DecodeTga.cs
index 2ebab5e00..d6a6cf1fb 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Tga/DecodeTga.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Tga/DecodeTga.cs
@@ -29,26 +29,26 @@ public class DecodeTga
[Benchmark(Baseline = true, Description = "ImageMagick Tga")]
public int TgaImageMagick()
{
- var settings = new MagickReadSettings { Format = MagickFormat.Tga };
- using var image = new MagickImage(new MemoryStream(this.data), settings);
+ MagickReadSettings settings = new() { Format = MagickFormat.Tga };
+ using MagickImage image = new(new MemoryStream(this.data), settings);
return image.Width;
}
[Benchmark(Description = "ImageSharp Tga")]
public int TgaImageSharp()
{
- using var image = Image.Load(this.data);
+ using Image image = Image.Load(this.data);
return image.Width;
}
[Benchmark(Description = "Pfim Tga")]
public int TgaPfim()
{
- using var image = Targa.Create(this.data, this.pfimConfig);
+ using Targa image = Targa.Create(this.data, this.pfimConfig);
return image.Width;
}
- private class PfimAllocator : IImageAllocator
+ private sealed class PfimAllocator : IImageAllocator
{
private int rented;
private readonly ArrayPool shared = ArrayPool.Shared;
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Tga/EncodeTga.cs b/tests/ImageSharp.Benchmarks/Codecs/Tga/EncodeTga.cs
index a7f5e3589..169a44d91 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Tga/EncodeTga.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Tga/EncodeTga.cs
@@ -41,14 +41,14 @@ public class EncodeTga
[Benchmark(Baseline = true, Description = "Magick Tga")]
public void MagickTga()
{
- using var memoryStream = new MemoryStream();
+ using MemoryStream memoryStream = new();
this.tgaMagick.Write(memoryStream, MagickFormat.Tga);
}
[Benchmark(Description = "ImageSharp Tga")]
public void ImageSharpTga()
{
- using var memoryStream = new MemoryStream();
+ using MemoryStream memoryStream = new();
this.tga.SaveAsTga(memoryStream);
}
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Tiff/EncodeTiff.cs b/tests/ImageSharp.Benchmarks/Codecs/Tiff/EncodeTiff.cs
index d3e394405..6fa6a15ed 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Tiff/EncodeTiff.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Tiff/EncodeTiff.cs
@@ -17,7 +17,7 @@ namespace SixLabors.ImageSharp.Benchmarks.Codecs;
[Config(typeof(Config.Short))]
public class EncodeTiff
{
- private Stream stream;
+ private FileStream stream;
private SDImage drawing;
private Image core;
@@ -60,12 +60,12 @@ public class EncodeTiff
public void SystemDrawing()
{
ImageCodecInfo codec = FindCodecForType("image/tiff");
- using var parameters = new EncoderParameters(1)
+ using EncoderParameters parameters = new(1)
{
Param = { [0] = new EncoderParameter(Encoder.Compression, (long)Cast(this.Compression)) }
};
- using var memoryStream = new MemoryStream();
+ using MemoryStream memoryStream = new();
this.drawing.Save(memoryStream, codec, parameters);
}
@@ -77,8 +77,8 @@ public class EncodeTiff
TiffPhotometricInterpretation.WhiteIsZero :
TiffPhotometricInterpretation.Rgb;
- var encoder = new TiffEncoder() { Compression = this.Compression, PhotometricInterpretation = photometricInterpretation };
- using var memoryStream = new MemoryStream();
+ TiffEncoder encoder = new() { Compression = this.Compression, PhotometricInterpretation = photometricInterpretation };
+ using MemoryStream memoryStream = new();
this.core.SaveAsTiff(memoryStream, encoder);
}
@@ -98,33 +98,15 @@ public class EncodeTiff
}
private static EncoderValue Cast(TiffCompression compression)
- {
- switch (compression)
+ => compression switch
{
- case TiffCompression.None:
- return EncoderValue.CompressionNone;
-
- case TiffCompression.CcittGroup3Fax:
- return EncoderValue.CompressionCCITT3;
-
- case TiffCompression.Ccitt1D:
- return EncoderValue.CompressionRle;
-
- case TiffCompression.Lzw:
- return EncoderValue.CompressionLZW;
-
- default:
- throw new NotSupportedException(compression.ToString());
- }
- }
+ TiffCompression.None => EncoderValue.CompressionNone,
+ TiffCompression.CcittGroup3Fax => EncoderValue.CompressionCCITT3,
+ TiffCompression.Ccitt1D => EncoderValue.CompressionRle,
+ TiffCompression.Lzw => EncoderValue.CompressionLZW,
+ _ => throw new NotSupportedException(compression.ToString()),
+ };
public static bool IsOneBitCompression(TiffCompression compression)
- {
- if (compression is TiffCompression.Ccitt1D or TiffCompression.CcittGroup3Fax or TiffCompression.CcittGroup4Fax)
- {
- return true;
- }
-
- return false;
- }
+ => compression is TiffCompression.Ccitt1D or TiffCompression.CcittGroup3Fax or TiffCompression.CcittGroup4Fax;
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Webp/DecodeWebp.cs b/tests/ImageSharp.Benchmarks/Codecs/Webp/DecodeWebp.cs
index 6c71a62b5..bba1bc187 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Webp/DecodeWebp.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Webp/DecodeWebp.cs
@@ -44,34 +44,35 @@ public class DecodeWebp
[Benchmark(Description = "Magick Lossy Webp")]
public int WebpLossyMagick()
{
- var settings = new MagickReadSettings { Format = MagickFormat.WebP };
- using var memoryStream = new MemoryStream(this.webpLossyBytes);
- using var image = new MagickImage(memoryStream, settings);
+ MagickReadSettings settings = new() { Format = MagickFormat.WebP };
+ using MemoryStream memoryStream = new(this.webpLossyBytes);
+ using MagickImage image = new(memoryStream, settings);
return image.Width;
}
[Benchmark(Description = "ImageSharp Lossy Webp")]
public int WebpLossy()
{
- using var memoryStream = new MemoryStream(this.webpLossyBytes);
- using var image = Image.Load(memoryStream);
+ using MemoryStream memoryStream = new(this.webpLossyBytes);
+ using Image image = Image.Load(memoryStream);
return image.Height;
}
[Benchmark(Description = "Magick Lossless Webp")]
public int WebpLosslessMagick()
{
- var settings = new MagickReadSettings { Format = MagickFormat.WebP };
- using var memoryStream = new MemoryStream(this.webpLossyBytes);
- using var image = new MagickImage(memoryStream, settings);
+ MagickReadSettings settings = new()
+ { Format = MagickFormat.WebP };
+ using MemoryStream memoryStream = new(this.webpLossyBytes);
+ using MagickImage image = new(memoryStream, settings);
return image.Width;
}
[Benchmark(Description = "ImageSharp Lossless Webp")]
public int WebpLossless()
{
- using var memoryStream = new MemoryStream(this.webpLosslessBytes);
- using var image = Image.Load(memoryStream);
+ using MemoryStream memoryStream = new(this.webpLosslessBytes);
+ using Image image = Image.Load(memoryStream);
return image.Height;
}
diff --git a/tests/ImageSharp.Benchmarks/Codecs/Webp/EncodeWebp.cs b/tests/ImageSharp.Benchmarks/Codecs/Webp/EncodeWebp.cs
index 5be46a222..3b9058498 100644
--- a/tests/ImageSharp.Benchmarks/Codecs/Webp/EncodeWebp.cs
+++ b/tests/ImageSharp.Benchmarks/Codecs/Webp/EncodeWebp.cs
@@ -4,6 +4,7 @@
using BenchmarkDotNet.Attributes;
using ImageMagick;
using ImageMagick.Formats;
+using SixLabors.ImageSharp.Formats;
using SixLabors.ImageSharp.Formats.Webp;
using SixLabors.ImageSharp.PixelFormats;
using SixLabors.ImageSharp.Tests;
@@ -52,10 +53,7 @@ public class EncodeWebp
AlphaCompression = WebPAlphaCompression.None,
FilterStrength = 60,
SnsStrength = 50,
- Pass = 1,
-
- // 100 means off.
- NearLossless = 100
+ Pass = 1
};
this.webpMagick.Quality = 75;
@@ -85,9 +83,6 @@ public class EncodeWebp
{
Lossless = true,
Method = 4,
-
- // 100 means off.
- NearLossless = 100
};
this.webpMagick.Quality = 75;
@@ -106,7 +101,7 @@ public class EncodeWebp
Quality = 75,
// This is equal to exact = false in libwebp, which is the default.
- TransparentColorMode = WebpTransparentColorMode.Clear
+ TransparentColorMode = TransparentColorMode.Clear
});
}
diff --git a/tests/ImageSharp.Benchmarks/Color/RgbWorkingSpaceAdapt.cs b/tests/ImageSharp.Benchmarks/Color/RgbWorkingSpaceAdapt.cs
index 6cd8df3fc..b847e3ac5 100644
--- a/tests/ImageSharp.Benchmarks/Color/RgbWorkingSpaceAdapt.cs
+++ b/tests/ImageSharp.Benchmarks/Color/RgbWorkingSpaceAdapt.cs
@@ -13,7 +13,7 @@ public class RgbWorkingSpaceAdapt
private static readonly RGBColor RGBColor = new(0.206162, 0.260277, 0.746717);
- private static readonly ColorProfileConverter ColorProfileConverter = new(new ColorConversionOptions { RgbWorkingSpace = KnownRgbWorkingSpaces.WideGamutRgb, TargetRgbWorkingSpace = KnownRgbWorkingSpaces.SRgb });
+ private static readonly ColorProfileConverter ColorProfileConverter = new(new ColorConversionOptions { SourceRgbWorkingSpace = KnownRgbWorkingSpaces.WideGamutRgb, TargetRgbWorkingSpace = KnownRgbWorkingSpaces.SRgb });
private static readonly IColorConverter ColourfulConverter = new ConverterBuilder().FromRGB(RGBWorkingSpaces.WideGamutRGB).ToRGB(RGBWorkingSpaces.sRGB).Build();
diff --git a/tests/ImageSharp.Benchmarks/Config.HwIntrinsics.cs b/tests/ImageSharp.Benchmarks/Config.HwIntrinsics.cs
index e21d0c76d..9fd48301e 100644
--- a/tests/ImageSharp.Benchmarks/Config.HwIntrinsics.cs
+++ b/tests/ImageSharp.Benchmarks/Config.HwIntrinsics.cs
@@ -34,6 +34,7 @@ public partial class Config
// like `LZCNT`, `BMI1`, or `BMI2`
// `EnableSSE3_4` is a legacy switch that exists for compat and is basically the same as `EnableSSE3`
private const string EnableAES = "DOTNET_EnableAES";
+ private const string EnableAVX512F = "DOTNET_EnableAVX512F";
private const string EnableAVX = "DOTNET_EnableAVX";
private const string EnableAVX2 = "DOTNET_EnableAVX2";
private const string EnableBMI1 = "DOTNET_EnableBMI1";
@@ -76,4 +77,36 @@ public partial class Config
}
}
}
+
+ public class HwIntrinsics_SSE_AVX_AVX512F : Config
+ {
+ public HwIntrinsics_SSE_AVX_AVX512F()
+ {
+ this.AddJob(Job.Default.WithRuntime(CoreRuntime.Core80)
+ .WithEnvironmentVariables(
+ new EnvironmentVariable(EnableHWIntrinsic, Off),
+ new EnvironmentVariable(FeatureSIMD, Off))
+ .WithId("1. No HwIntrinsics").AsBaseline());
+
+ if (Sse.IsSupported)
+ {
+ this.AddJob(Job.Default.WithRuntime(CoreRuntime.Core80)
+ .WithEnvironmentVariables(new EnvironmentVariable(EnableAVX, Off))
+ .WithId("2. SSE"));
+ }
+
+ if (Avx.IsSupported)
+ {
+ this.AddJob(Job.Default.WithRuntime(CoreRuntime.Core80)
+ .WithEnvironmentVariables(new EnvironmentVariable(EnableAVX512F, Off))
+ .WithId("3. AVX"));
+ }
+
+ if (Avx512F.IsSupported)
+ {
+ this.AddJob(Job.Default.WithRuntime(CoreRuntime.Core80)
+ .WithId("3. AVX512F"));
+ }
+ }
+ }
}
diff --git a/tests/ImageSharp.Benchmarks/Config.cs b/tests/ImageSharp.Benchmarks/Config.cs
index 06e857484..9231fc8b4 100644
--- a/tests/ImageSharp.Benchmarks/Config.cs
+++ b/tests/ImageSharp.Benchmarks/Config.cs
@@ -10,6 +10,7 @@ using BenchmarkDotNet.Diagnosers;
using BenchmarkDotNet.Environments;
using BenchmarkDotNet.Jobs;
using BenchmarkDotNet.Reports;
+using BenchmarkDotNet.Toolchains.InProcess.Emit;
namespace SixLabors.ImageSharp.Benchmarks;
@@ -32,7 +33,7 @@ public partial class Config : ManualConfig
public class Standard : Config
{
public Standard() => this.AddJob(
- Job.Default.WithRuntime(CoreRuntime.Core80).WithArguments(new Argument[] { new MsBuildArgument("/p:DebugType=portable") }));
+ Job.Default.WithRuntime(CoreRuntime.Core80).WithArguments([new MsBuildArgument("/p:DebugType=portable")]));
}
public class Short : Config
@@ -42,12 +43,19 @@ public partial class Config : ManualConfig
.WithLaunchCount(1)
.WithWarmupCount(3)
.WithIterationCount(3)
- .WithArguments(new Argument[] { new MsBuildArgument("/p:DebugType=portable") }));
+ .WithArguments([new MsBuildArgument("/p:DebugType=portable")]));
+ }
+
+ public class StandardInProcess : Config
+ {
+ public StandardInProcess() => this.AddJob(
+ Job.Default
+ .WithRuntime(CoreRuntime.Core80)
+ .WithToolchain(InProcessEmitToolchain.Instance)
+ .WithArguments([new MsBuildArgument("/p:DebugType=portable")]));
}
#if OS_WINDOWS
-#pragma warning disable CA1416 // Validate platform compatibility
private bool IsElevated => new WindowsPrincipal(WindowsIdentity.GetCurrent()).IsInRole(WindowsBuiltInRole.Administrator);
-#pragma warning restore CA1416 // Validate platform compatibility
#endif
}
diff --git a/tests/ImageSharp.Benchmarks/General/Adler32Benchmark.cs b/tests/ImageSharp.Benchmarks/General/Adler32Benchmark.cs
index 30023feca..64a8092c6 100644
--- a/tests/ImageSharp.Benchmarks/General/Adler32Benchmark.cs
+++ b/tests/ImageSharp.Benchmarks/General/Adler32Benchmark.cs
@@ -11,7 +11,7 @@ namespace SixLabors.ImageSharp.Benchmarks.General;
public class Adler32Benchmark
{
private byte[] data;
- private readonly SharpAdler32 adler = new SharpAdler32();
+ private readonly SharpAdler32 adler = new();
[Params(1024, 2048, 4096)]
public int Count { get; set; }
diff --git a/tests/ImageSharp.Benchmarks/General/BasicMath/ClampFloat.cs b/tests/ImageSharp.Benchmarks/General/BasicMath/ClampFloat.cs
index dd0bc2878..317295144 100644
--- a/tests/ImageSharp.Benchmarks/General/BasicMath/ClampFloat.cs
+++ b/tests/ImageSharp.Benchmarks/General/BasicMath/ClampFloat.cs
@@ -10,7 +10,7 @@ public class ClampFloat
{
private readonly float min = -1.5f;
private readonly float max = 2.5f;
- private static readonly float[] Values = { -10, -5, -3, -1.5f, -0.5f, 0f, 1f, 1.5f, 2.5f, 3, 10 };
+ private static readonly float[] Values = [-10, -5, -3, -1.5f, -0.5f, 0f, 1f, 1.5f, 2.5f, 3, 10];
[Benchmark(Baseline = true)]
public float UsingMathF()
diff --git a/tests/ImageSharp.Benchmarks/General/BasicMath/ClampSpan.cs b/tests/ImageSharp.Benchmarks/General/BasicMath/ClampSpan.cs
index d47fcb687..b61ba27ff 100644
--- a/tests/ImageSharp.Benchmarks/General/BasicMath/ClampSpan.cs
+++ b/tests/ImageSharp.Benchmarks/General/BasicMath/ClampSpan.cs
@@ -12,7 +12,7 @@ public class ClampSpan
public void Setup()
{
- var r = new Random();
+ Random r = new();
for (int i = 0; i < A.Length; i++)
{
diff --git a/tests/ImageSharp.Benchmarks/General/BasicMath/ClampVector4.cs b/tests/ImageSharp.Benchmarks/General/BasicMath/ClampVector4.cs
index 186f88bb7..4969c3ef7 100644
--- a/tests/ImageSharp.Benchmarks/General/BasicMath/ClampVector4.cs
+++ b/tests/ImageSharp.Benchmarks/General/BasicMath/ClampVector4.cs
@@ -11,7 +11,7 @@ public class ClampVector4
{
private readonly float min = -1.5f;
private readonly float max = 2.5f;
- private static readonly float[] Values = { -10, -5, -3, -1.5f, -0.5f, 0f, 1f, 1.5f, 2.5f, 3, 10 };
+ private static readonly float[] Values = [-10, -5, -3, -1.5f, -0.5f, 0f, 1f, 1.5f, 2.5f, 3, 10];
[Benchmark(Baseline = true)]
public Vector4 UsingVectorClamp()
diff --git a/tests/ImageSharp.Benchmarks/General/GetSetPixel.cs b/tests/ImageSharp.Benchmarks/General/GetSetPixel.cs
index 5ba7809e1..41e6bdec2 100644
--- a/tests/ImageSharp.Benchmarks/General/GetSetPixel.cs
+++ b/tests/ImageSharp.Benchmarks/General/GetSetPixel.cs
@@ -1,6 +1,7 @@
// Copyright (c) Six Labors.
// Licensed under the Six Labors Split License.
+#if OS_WINDOWS
using System.Drawing;
using BenchmarkDotNet.Attributes;
using SixLabors.ImageSharp.PixelFormats;
@@ -25,3 +26,4 @@ public class GetSetPixel
return image[200, 200];
}
}
+#endif
diff --git a/tests/ImageSharp.Benchmarks/General/IO/BufferedStreams.cs b/tests/ImageSharp.Benchmarks/General/IO/BufferedStreams.cs
index 9560d6ee7..d32e1fdd0 100644
--- a/tests/ImageSharp.Benchmarks/General/IO/BufferedStreams.cs
+++ b/tests/ImageSharp.Benchmarks/General/IO/BufferedStreams.cs
@@ -78,7 +78,7 @@ public class BufferedStreams
public int StandardStreamRead()
{
int r = 0;
- Stream stream = this.stream1;
+ MemoryStream stream = this.stream1;
byte[] b = this.chunk1;
for (int i = 0; i < stream.Length / 2; i++)
@@ -138,7 +138,7 @@ public class BufferedStreams
public int StandardStreamReadByte()
{
int r = 0;
- Stream stream = this.stream2;
+ MemoryStream stream = this.stream2;
for (int i = 0; i < stream.Length; i++)
{
@@ -205,8 +205,8 @@ public class BufferedStreams
private static byte[] CreateTestBytes()
{
- var buffer = new byte[Configuration.Default.StreamProcessingBufferSize * 3];
- var random = new Random();
+ byte[] buffer = new byte[Configuration.Default.StreamProcessingBufferSize * 3];
+ Random random = new();
random.NextBytes(buffer);
return buffer;
diff --git a/tests/ImageSharp.Benchmarks/General/PixelConversion/PixelConversion_ConvertFromRgba32.cs b/tests/ImageSharp.Benchmarks/General/PixelConversion/PixelConversion_ConvertFromRgba32.cs
index 1d83b94dc..c864e26c6 100644
--- a/tests/ImageSharp.Benchmarks/General/PixelConversion/PixelConversion_ConvertFromRgba32.cs
+++ b/tests/ImageSharp.Benchmarks/General/PixelConversion/PixelConversion_ConvertFromRgba32.cs
@@ -184,14 +184,16 @@ public class PixelConversion_ConvertFromRgba32_Permuted_RgbaToArgb : PixelConver
}
}
- [Benchmark]
- public void PixelConverter_Rgba32_ToArgb32()
- {
- Span source = MemoryMarshal.Cast(this.PermutedRunnerRgbaToArgb.Source);
- Span dest = MemoryMarshal.Cast(this.PermutedRunnerRgbaToArgb.Destination);
-
- PixelConverter.FromRgba32.ToArgb32(source, dest);
- }
+ // Commenting this out because for some reason MSBuild is showing error CS0029: Cannot implicitly convert type 'System.ReadOnlySpan' to 'System.Span'
+ // when trying to build via BenchmarkDotnet. (╯‵□′)╯︵┻â”â”»
+ // [Benchmark]
+ // public void PixelConverter_Rgba32_ToArgb32()
+ // {
+ // ReadOnlySpan source = MemoryMarshal.Cast(this.PermutedRunnerRgbaToArgb.Source);
+ // Span destination = MemoryMarshal.Cast(this.PermutedRunnerRgbaToArgb.Destination);
+ //
+ // PixelConverter.FromRgba32.ToArgb32(source, destination);
+ // }
/*
BenchmarkDotNet v0.13.10, Windows 11 (10.0.22631.3007/23H2/2023Update/SunValley3)
diff --git a/tests/ImageSharp.Benchmarks/General/PixelConversion/PixelConversion_PackFromRgbPlanes.cs b/tests/ImageSharp.Benchmarks/General/PixelConversion/PixelConversion_PackFromRgbPlanes.cs
index a42c6c253..226dcc777 100644
--- a/tests/ImageSharp.Benchmarks/General/PixelConversion/PixelConversion_PackFromRgbPlanes.cs
+++ b/tests/ImageSharp.Benchmarks/General/PixelConversion/PixelConversion_PackFromRgbPlanes.cs
@@ -209,7 +209,7 @@ public unsafe class PixelConversion_PackFromRgbPlanes
Vector256 vcontrol = SimdUtils.HwIntrinsics.PermuteMaskEvenOdd8x32().AsInt32();
- var va = Vector256.Create(1F);
+ Vector256 va = Vector256.Create(1F);
for (nuint i = 0; i < count; i++)
{
diff --git a/tests/ImageSharp.Benchmarks/General/PixelConversion/PixelConversion_Rgba32_To_Bgra32.cs b/tests/ImageSharp.Benchmarks/General/PixelConversion/PixelConversion_Rgba32_To_Bgra32.cs
index f4fb9e420..232d8b3e2 100644
--- a/tests/ImageSharp.Benchmarks/General/PixelConversion/PixelConversion_Rgba32_To_Bgra32.cs
+++ b/tests/ImageSharp.Benchmarks/General/PixelConversion/PixelConversion_Rgba32_To_Bgra32.cs
@@ -252,8 +252,8 @@ public class PixelConversion_Rgba32_To_Bgra32
private static void BitopsSimdImpl(ref Octet s, ref Octet d)
{
Vector sVec = Unsafe.As, Vector>(ref s);
- var aMask = new Vector(0xFF00FF00);
- var bMask = new Vector(0x00FF00FF);
+ Vector aMask = new(0xFF00FF00);
+ Vector bMask = new(0x00FF00FF);
Vector aa = sVec & aMask;
Vector bb = sVec & bMask;
diff --git a/tests/ImageSharp.Benchmarks/General/PixelConversion/TestArgb.cs b/tests/ImageSharp.Benchmarks/General/PixelConversion/TestArgb.cs
index 21bef5a15..8698f8223 100644
--- a/tests/ImageSharp.Benchmarks/General/PixelConversion/TestArgb.cs
+++ b/tests/ImageSharp.Benchmarks/General/PixelConversion/TestArgb.cs
@@ -103,6 +103,6 @@ public struct TestArgb : ITestPixel
vector = Numerics.Clamp(vector, Vector4.Zero, MaxBytes);
Vector128 result = Vector128.ConvertToInt32(vector.AsVector128()).AsByte();
- return new(result.GetElement(0), result.GetElement(4), result.GetElement(8), result.GetElement(12));
+ return new TestArgb(result.GetElement(0), result.GetElement(4), result.GetElement(8), result.GetElement(12));
}
}
diff --git a/tests/ImageSharp.Benchmarks/General/PixelConversion/TestRgba.cs b/tests/ImageSharp.Benchmarks/General/PixelConversion/TestRgba.cs
index 1499fb7d3..751cd68b4 100644
--- a/tests/ImageSharp.Benchmarks/General/PixelConversion/TestRgba.cs
+++ b/tests/ImageSharp.Benchmarks/General/PixelConversion/TestRgba.cs
@@ -79,6 +79,6 @@ public struct TestRgba : ITestPixel
vector = Numerics.Clamp(vector, Vector4.Zero, MaxBytes);
Vector128 result = Vector128.ConvertToInt32(vector.AsVector128()).AsByte();
- return new(result.GetElement(0), result.GetElement(4), result.GetElement(8), result.GetElement(12));
+ return new TestRgba(result.GetElement(0), result.GetElement(4), result.GetElement(8), result.GetElement(12));
}
}
diff --git a/tests/ImageSharp.Benchmarks/General/StructCasting.cs b/tests/ImageSharp.Benchmarks/General/StructCasting.cs
index f8432112e..3f3767d42 100644
--- a/tests/ImageSharp.Benchmarks/General/StructCasting.cs
+++ b/tests/ImageSharp.Benchmarks/General/StructCasting.cs
@@ -11,7 +11,7 @@ public class StructCasting
[Benchmark(Baseline = true)]
public short ExplicitCast()
{
- int x = 5 * 2;
+ const int x = 5 * 2;
return (short)x;
}
@@ -25,6 +25,7 @@ public class StructCasting
[Benchmark]
public short UnsafeCastRef()
{
- return Unsafe.As(ref Unsafe.AsRef(5 * 2));
+ int x = 5 * 2;
+ return Unsafe.As(ref Unsafe.AsRef(ref x));
}
}
diff --git a/tests/ImageSharp.Benchmarks/General/Vector4Constants.cs b/tests/ImageSharp.Benchmarks/General/Vector4Constants.cs
index 2cd6a5a52..5919137bf 100644
--- a/tests/ImageSharp.Benchmarks/General/Vector4Constants.cs
+++ b/tests/ImageSharp.Benchmarks/General/Vector4Constants.cs
@@ -12,10 +12,10 @@ namespace SixLabors.ImageSharp.Benchmarks.General;
///
public class Vector4Constants
{
- private static readonly Vector4 A = new Vector4(1.2f);
- private static readonly Vector4 B = new Vector4(3.4f);
- private static readonly Vector4 C = new Vector4(5.6f);
- private static readonly Vector4 D = new Vector4(7.8f);
+ private static readonly Vector4 A = new(1.2f);
+ private static readonly Vector4 B = new(3.4f);
+ private static readonly Vector4 C = new(5.6f);
+ private static readonly Vector4 D = new(7.8f);
private Random random;
@@ -39,8 +39,8 @@ public class Vector4Constants
Vector4 x = (p * A / B) + (p * C / D);
Vector4 y = (p / A * B) + (p / C * D);
- var z = Vector4.Min(p, A);
- var w = Vector4.Max(p, B);
+ Vector4 z = Vector4.Min(p, A);
+ Vector4 w = Vector4.Max(p, B);
return x + y + z + w;
}
@@ -51,8 +51,8 @@ public class Vector4Constants
Vector4 x = (p * new Vector4(1.2f) / new Vector4(2.3f)) + (p * new Vector4(4.5f) / new Vector4(6.7f));
Vector4 y = (p / new Vector4(1.2f) * new Vector4(2.3f)) + (p / new Vector4(4.5f) * new Vector4(6.7f));
- var z = Vector4.Min(p, new Vector4(1.2f));
- var w = Vector4.Max(p, new Vector4(2.3f));
+ Vector4 z = Vector4.Min(p, new Vector4(1.2f));
+ Vector4 w = Vector4.Max(p, new Vector4(2.3f));
return x + y + z + w;
}
diff --git a/tests/ImageSharp.Benchmarks/General/Vectorization/BitwiseOrUint32.cs b/tests/ImageSharp.Benchmarks/General/Vectorization/BitwiseOrUint32.cs
index 4d8d9b1ed..2f9b02b59 100644
--- a/tests/ImageSharp.Benchmarks/General/Vectorization/BitwiseOrUint32.cs
+++ b/tests/ImageSharp.Benchmarks/General/Vectorization/BitwiseOrUint32.cs
@@ -43,11 +43,11 @@ public class BitwiseOrUInt32
[Benchmark]
public void Simd()
{
- var v = new Vector(this.testValue);
+ Vector v = new(this.testValue);
for (int i = 0; i < this.input.Length; i += Vector.Count)
{
- var a = new Vector(this.input, i);
+ Vector a = new(this.input, i);
a = Vector.BitwiseOr(a, v);
a.CopyTo(this.result, i);
}
diff --git a/tests/ImageSharp.Benchmarks/General/Vectorization/DivFloat.cs b/tests/ImageSharp.Benchmarks/General/Vectorization/DivFloat.cs
index 1b2c56ab9..fd243638b 100644
--- a/tests/ImageSharp.Benchmarks/General/Vectorization/DivFloat.cs
+++ b/tests/ImageSharp.Benchmarks/General/Vectorization/DivFloat.cs
@@ -43,11 +43,11 @@ public class DivFloat
[Benchmark]
public void Simd()
{
- var v = new Vector(this.testValue);
+ Vector v = new(this.testValue);
for (int i = 0; i < this.input.Length; i += Vector.Count)
{
- var a = new Vector(this.input, i);
+ Vector a = new(this.input, i);
a = a / v;
a.CopyTo(this.result, i);
}
diff --git a/tests/ImageSharp.Benchmarks/General/Vectorization/DivUInt32.cs b/tests/ImageSharp.Benchmarks/General/Vectorization/DivUInt32.cs
index d102164e2..0d2923b61 100644
--- a/tests/ImageSharp.Benchmarks/General/Vectorization/DivUInt32.cs
+++ b/tests/ImageSharp.Benchmarks/General/Vectorization/DivUInt32.cs
@@ -44,11 +44,11 @@ public class DivUInt32
[Benchmark]
public void Simd()
{
- var v = new Vector(this.testValue);
+ Vector v = new(this.testValue);
for (int i = 0; i < this.input.Length; i += Vector.Count)
{
- var a = new Vector(this.input, i);
+ Vector a = new(this.input, i);
a = a / v;
a.CopyTo(this.result, i);
diff --git a/tests/ImageSharp.Benchmarks/General/Vectorization/Divide.cs b/tests/ImageSharp.Benchmarks/General/Vectorization/Divide.cs
index 9c95c22e0..61ff9466e 100644
--- a/tests/ImageSharp.Benchmarks/General/Vectorization/Divide.cs
+++ b/tests/ImageSharp.Benchmarks/General/Vectorization/Divide.cs
@@ -15,10 +15,10 @@ public class DivFloat : SIMDBenchmarkBase.Divide
[Benchmark(Baseline = true)]
public void Standard()
{
- float v = this.testValue;
- for (int i = 0; i < this.input.Length; i++)
+ float v = this.TestValue;
+ for (int i = 0; i < this.Input.Length; i++)
{
- this.result[i] = this.input[i] / v;
+ this.Result[i] = this.Input[i] / v;
}
}
}
@@ -30,10 +30,10 @@ public class Divide : SIMDBenchmarkBase.Divide
[Benchmark(Baseline = true)]
public void Standard()
{
- uint v = this.testValue;
- for (int i = 0; i < this.input.Length; i++)
+ uint v = this.TestValue;
+ for (int i = 0; i < this.Input.Length; i++)
{
- this.result[i] = this.input[i] / v;
+ this.Result[i] = this.Input[i] / v;
}
}
}
@@ -45,10 +45,10 @@ public class DivInt32 : SIMDBenchmarkBase.Divide
[Benchmark(Baseline = true)]
public void Standard()
{
- int v = this.testValue;
- for (int i = 0; i < this.input.Length; i++)
+ int v = this.TestValue;
+ for (int i = 0; i < this.Input.Length; i++)
{
- this.result[i] = this.input[i] / v;
+ this.Result[i] = this.Input[i] / v;
}
}
}
@@ -57,15 +57,15 @@ public class DivInt16 : SIMDBenchmarkBase.Divide
{
protected override short GetTestValue() => 42;
- protected override Vector GetTestVector() => new Vector(new short[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17 });
+ protected override Vector GetTestVector() => new(new short[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17 });
[Benchmark(Baseline = true)]
public void Standard()
{
- short v = this.testValue;
- for (int i = 0; i < this.input.Length; i++)
+ short v = this.TestValue;
+ for (int i = 0; i < this.Input.Length; i++)
{
- this.result[i] = (short)(this.input[i] / v);
+ this.Result[i] = (short)(this.Input[i] / v);
}
}
}
diff --git a/tests/ImageSharp.Benchmarks/General/Vectorization/MulFloat.cs b/tests/ImageSharp.Benchmarks/General/Vectorization/MulFloat.cs
index a2eb8d417..801b0e161 100644
--- a/tests/ImageSharp.Benchmarks/General/Vectorization/MulFloat.cs
+++ b/tests/ImageSharp.Benchmarks/General/Vectorization/MulFloat.cs
@@ -43,11 +43,11 @@ public class MulFloat
[Benchmark]
public void SimdMultiplyByVector()
{
- var v = new Vector(this.testValue);
+ Vector v = new(this.testValue);
for (int i = 0; i < this.input.Length; i += Vector.Count)
{
- var a = new Vector(this.input, i);
+ Vector a = new(this.input, i);
a = a * v;
a.CopyTo(this.result, i);
}
@@ -60,7 +60,7 @@ public class MulFloat
for (int i = 0; i < this.input.Length; i += Vector.Count)
{
- var a = new Vector(this.input, i);
+ Vector a = new(this.input, i);
a = a * v;
a.CopyTo(this.result, i);
}
diff --git a/tests/ImageSharp.Benchmarks/General/Vectorization/MulUInt32.cs b/tests/ImageSharp.Benchmarks/General/Vectorization/MulUInt32.cs
index a234970a5..db64486ad 100644
--- a/tests/ImageSharp.Benchmarks/General/Vectorization/MulUInt32.cs
+++ b/tests/ImageSharp.Benchmarks/General/Vectorization/MulUInt32.cs
@@ -43,11 +43,11 @@ public class MulUInt32
[Benchmark]
public void Simd()
{
- var v = new Vector(this.testValue);
+ Vector v = new(this.testValue);
for (int i = 0; i < this.input.Length; i += Vector.Count)
{
- var a = new Vector(this.input, i);
+ Vector a = new(this.input, i);
a = a * v;
a.CopyTo(this.result, i);
}
diff --git a/tests/ImageSharp.Benchmarks/General/Vectorization/Multiply.cs b/tests/ImageSharp.Benchmarks/General/Vectorization/Multiply.cs
index fe48c3301..d9542bc3f 100644
--- a/tests/ImageSharp.Benchmarks/General/Vectorization/Multiply.cs
+++ b/tests/ImageSharp.Benchmarks/General/Vectorization/Multiply.cs
@@ -15,10 +15,10 @@ public class MulUInt32 : SIMDBenchmarkBase.Multiply
[Benchmark(Baseline = true)]
public void Standard()
{
- uint v = this.testValue;
- for (int i = 0; i < this.input.Length; i++)
+ uint v = this.TestValue;
+ for (int i = 0; i < this.Input.Length; i++)
{
- this.result[i] = this.input[i] * v;
+ this.Result[i] = this.Input[i] * v;
}
}
}
@@ -28,10 +28,10 @@ public class MulInt32 : SIMDBenchmarkBase.Multiply
[Benchmark(Baseline = true)]
public void Standard()
{
- int v = this.testValue;
- for (int i = 0; i < this.input.Length; i++)
+ int v = this.TestValue;
+ for (int i = 0; i < this.Input.Length; i++)
{
- this.result[i] = this.input[i] * v;
+ this.Result[i] = this.Input[i] * v;
}
}
}
@@ -40,15 +40,15 @@ public class MulInt16 : SIMDBenchmarkBase.Multiply
{
protected override short GetTestValue() => 42;
- protected override Vector GetTestVector() => new Vector(new short[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17 });
+ protected override Vector GetTestVector() => new(new short[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17 });
[Benchmark(Baseline = true)]
public void Standard()
{
- short v = this.testValue;
- for (int i = 0; i < this.input.Length; i++)
+ short v = this.TestValue;
+ for (int i = 0; i < this.Input.Length; i++)
{
- this.result[i] = (short)(this.input[i] * v);
+ this.Result[i] = (short)(this.Input[i] * v);
}
}
}
diff --git a/tests/ImageSharp.Benchmarks/General/Vectorization/Premultiply.cs b/tests/ImageSharp.Benchmarks/General/Vectorization/Premultiply.cs
index 29b90accc..f99b141b4 100644
--- a/tests/ImageSharp.Benchmarks/General/Vectorization/Premultiply.cs
+++ b/tests/ImageSharp.Benchmarks/General/Vectorization/Premultiply.cs
@@ -12,14 +12,14 @@ public class Premultiply
[Benchmark(Baseline = true)]
public Vector4 PremultiplyByVal()
{
- var input = new Vector4(.5F);
+ Vector4 input = new(.5F);
return Vector4Utils.Premultiply(input);
}
[Benchmark]
public Vector4 PremultiplyByRef()
{
- var input = new Vector4(.5F);
+ Vector4 input = new(.5F);
Vector4Utils.PremultiplyRef(ref input);
return input;
}
@@ -27,7 +27,7 @@ public class Premultiply
[Benchmark]
public Vector4 PremultiplyRefWithPropertyAssign()
{
- var input = new Vector4(.5F);
+ Vector4 input = new(.5F);
Vector4Utils.PremultiplyRefWithPropertyAssign(ref input);
return input;
}
diff --git a/tests/ImageSharp.Benchmarks/General/Vectorization/ReinterpretUInt32AsFloat.cs b/tests/ImageSharp.Benchmarks/General/Vectorization/ReinterpretUInt32AsFloat.cs
index 7d626d785..557d8ff38 100644
--- a/tests/ImageSharp.Benchmarks/General/Vectorization/ReinterpretUInt32AsFloat.cs
+++ b/tests/ImageSharp.Benchmarks/General/Vectorization/ReinterpretUInt32AsFloat.cs
@@ -53,8 +53,8 @@ public class ReinterpretUInt32AsFloat
{
for (int i = 0; i < this.input.Length; i += Vector.Count)
{
- var a = new Vector(this.input, i);
- var b = Vector.AsVectorSingle(a);
+ Vector a = new(this.input, i);
+ Vector b = Vector.AsVectorSingle(a);
b.CopyTo(this.result, i);
}
}
diff --git a/tests/ImageSharp.Benchmarks/General/Vectorization/SIMDBenchmarkBase.cs b/tests/ImageSharp.Benchmarks/General/Vectorization/SIMDBenchmarkBase.cs
index 90d81a058..0d856df61 100644
--- a/tests/ImageSharp.Benchmarks/General/Vectorization/SIMDBenchmarkBase.cs
+++ b/tests/ImageSharp.Benchmarks/General/Vectorization/SIMDBenchmarkBase.cs
@@ -10,28 +10,28 @@ namespace ImageSharp.Benchmarks.General.Vectorization;
public abstract class SIMDBenchmarkBase
where T : struct
{
- protected T[] input;
+ protected virtual T GetTestValue() => default;
- protected T[] result;
+ protected virtual Vector GetTestVector() => new(this.GetTestValue());
- protected T testValue;
+ [Params(32)]
+ public int InputSize { get; set; }
- protected Vector testVector;
+ protected T[] Input { get; set; }
- protected virtual T GetTestValue() => default;
+ protected T[] Result { get; set; }
- protected virtual Vector GetTestVector() => new Vector(this.GetTestValue());
+ protected T TestValue { get; set; }
- [Params(32)]
- public int InputSize { get; set; }
+ protected Vector TestVector { get; set; }
[GlobalSetup]
public virtual void Setup()
{
- this.input = new T[this.InputSize];
- this.result = new T[this.InputSize];
- this.testValue = this.GetTestValue();
- this.testVector = this.GetTestVector();
+ this.Input = new T[this.InputSize];
+ this.Result = new T[this.InputSize];
+ this.TestValue = this.GetTestValue();
+ this.TestVector = this.GetTestVector();
}
public abstract class Multiply : SIMDBenchmarkBase
@@ -39,13 +39,13 @@ public abstract class SIMDBenchmarkBase
[Benchmark]
public void Simd()
{
- Vector v = this.testVector;
+ Vector v = this.TestVector;
- for (int i = 0; i < this.input.Length; i += Vector.Count)
+ for (int i = 0; i < this.Input.Length; i += Vector.Count)
{
- Vector a = Unsafe.As>(ref this.input[i]);
- a = a * v;
- Unsafe.As>(ref this.result[i]) = a;
+ Vector a = Unsafe.As>(ref this.Input[i]);
+ a *= v;
+ Unsafe.As>(ref this.Result[i]) = a;
}
}
}
@@ -55,13 +55,13 @@ public abstract class SIMDBenchmarkBase
[Benchmark]
public void Simd()
{
- Vector v = this.testVector;
+ Vector v = this.TestVector;
- for (int i = 0; i < this.input.Length; i += Vector.Count)
+ for (int i = 0; i < this.Input.Length; i += Vector.Count)
{
- Vector a = Unsafe.As>(ref this.input[i]);
- a = a / v;
- Unsafe.As>(ref this.result[i]) = a;
+ Vector a = Unsafe.As>(ref this.Input[i]);
+ a /= v;
+ Unsafe.As>(ref this.Result[i]) = a;
}
}
}
diff --git a/tests/ImageSharp.Benchmarks/General/Vectorization/UInt32ToSingle.cs b/tests/ImageSharp.Benchmarks/General/Vectorization/UInt32ToSingle.cs
index 5f1f5666d..4048bc210 100644
--- a/tests/ImageSharp.Benchmarks/General/Vectorization/UInt32ToSingle.cs
+++ b/tests/ImageSharp.Benchmarks/General/Vectorization/UInt32ToSingle.cs
@@ -27,20 +27,20 @@ public class UInt32ToSingle
nuint n = Count / (uint)Vector.Count;
- var bVec = new Vector(256.0f / 255.0f);
- var magicFloat = new Vector(32768.0f);
- var magicInt = new Vector(1191182336); // reinterpreted value of 32768.0f
- var mask = new Vector(255);
+ Vector bVec = new(256.0f / 255.0f);
+ Vector magicFloat = new(32768.0f);
+ Vector magicInt = new(1191182336); // reinterpreted value of 32768.0f
+ Vector mask = new(255);
for (nuint i = 0; i < n; i++)
{
ref Vector df = ref Unsafe.Add(ref b, i);
- var vi = Vector.AsVectorUInt32(df);
+ Vector vi = Vector.AsVectorUInt32(df);
vi &= mask;
vi |= magicInt;
- var vf = Vector.AsVectorSingle(vi);
+ Vector vf = Vector.AsVectorSingle(vi);
vf = (vf - magicFloat) * bVec;
df = vf;
@@ -55,7 +55,7 @@ public class UInt32ToSingle
ref Vector bf = ref Unsafe.As>(ref this.data[0]);
ref Vector bu = ref Unsafe.As, Vector>(ref bf);
- var scale = new Vector(1f / 255f);
+ Vector scale = new(1f / 255f);
for (nuint i = 0; i < n; i++)
{
@@ -74,7 +74,7 @@ public class UInt32ToSingle
ref Vector bf = ref Unsafe.As>(ref this.data[0]);
ref Vector bu = ref Unsafe.As, Vector>(ref bf);
- var scale = new Vector(1f / 255f);
+ Vector scale = new(1f / 255f);
for (nuint i = 0; i < n; i++)
{
@@ -91,7 +91,7 @@ public class UInt32ToSingle
nuint n = Count / (uint)Vector.Count;
ref Vector bf = ref Unsafe.As>(ref this.data[0]);
- var scale = new Vector(1f / 255f);
+ Vector scale = new(1f / 255f);
for (nuint i = 0; i < n; i++)
{
diff --git a/tests/ImageSharp.Benchmarks/General/Vectorization/VectorFetching.cs b/tests/ImageSharp.Benchmarks/General/Vectorization/VectorFetching.cs
index 5d20f29d1..9c7fd5b6c 100644
--- a/tests/ImageSharp.Benchmarks/General/Vectorization/VectorFetching.cs
+++ b/tests/ImageSharp.Benchmarks/General/Vectorization/VectorFetching.cs
@@ -47,11 +47,11 @@ public class VectorFetching
[Benchmark]
public void FetchWithVectorConstructor()
{
- var v = new Vector(this.testValue);
+ Vector v = new(this.testValue);
for (int i = 0; i < this.data.Length; i += Vector.Count)
{
- var a = new Vector(this.data, i);
+ Vector a = new(this.data, i);
a = a * v;
a.CopyTo(this.data, i);
}
@@ -60,7 +60,7 @@ public class VectorFetching
[Benchmark]
public void FetchWithUnsafeCast()
{
- var v = new Vector(this.testValue);
+ Vector v = new(this.testValue);
ref Vector start = ref Unsafe.As>(ref this.data[0]);
nuint n = (uint)this.InputSize / (uint)Vector.Count;
@@ -79,7 +79,7 @@ public class VectorFetching
[Benchmark]
public void FetchWithUnsafeCastNoTempVector()
{
- var v = new Vector(this.testValue);
+ Vector v = new(this.testValue);
ref Vector start = ref Unsafe.As>(ref this.data[0]);
nuint n = (uint)this.InputSize / (uint)Vector.Count;
@@ -94,9 +94,9 @@ public class VectorFetching
[Benchmark]
public void FetchWithUnsafeCastFromReference()
{
- var v = new Vector(this.testValue);
+ Vector v = new(this.testValue);
- var span = new Span(this.data);
+ Span span = new(this.data);
ref Vector start = ref Unsafe.As>(ref MemoryMarshal.GetReference(span));
diff --git a/tests/ImageSharp.Benchmarks/ImageSharp.Benchmarks.csproj b/tests/ImageSharp.Benchmarks/ImageSharp.Benchmarks.csproj
index a705b24b2..fa5fdd816 100644
--- a/tests/ImageSharp.Benchmarks/ImageSharp.Benchmarks.csproj
+++ b/tests/ImageSharp.Benchmarks/ImageSharp.Benchmarks.csproj
@@ -15,15 +15,31 @@
-
+
+
- CA1822
+
+
+
+ CA1822;CA1416;CA1001;CS0029;CA1861;CA2201
+
+
+
+
+
+
+
+
+
- net8.0;net9.0
+ net8.0;net10.0
@@ -41,8 +57,9 @@
-
-
+
+
+
diff --git a/tests/ImageSharp.Benchmarks/LoadResizeSave/LoadResizeSaveStressBenchmarks.cs b/tests/ImageSharp.Benchmarks/LoadResizeSave/LoadResizeSaveStressBenchmarks.cs
index 04621695c..0731c7c00 100644
--- a/tests/ImageSharp.Benchmarks/LoadResizeSave/LoadResizeSaveStressBenchmarks.cs
+++ b/tests/ImageSharp.Benchmarks/LoadResizeSave/LoadResizeSaveStressBenchmarks.cs
@@ -18,7 +18,7 @@ public class LoadResizeSaveStressBenchmarks
[GlobalSetup]
public void Setup()
{
- this.runner = new LoadResizeSaveStressRunner()
+ this.runner = new LoadResizeSaveStressRunner
{
ImageCount = Environment.ProcessorCount,
Filter = Filter
@@ -34,12 +34,12 @@ public class LoadResizeSaveStressBenchmarks
}
public int[] ParallelismValues { get; } =
- {
+ [
// Environment.ProcessorCount,
// Environment.ProcessorCount / 2,
// Environment.ProcessorCount / 4,
1
- };
+ ];
[Benchmark]
[ArgumentsSource(nameof(ParallelismValues))]
diff --git a/tests/ImageSharp.Benchmarks/LoadResizeSave/LoadResizeSaveStressRunner.cs b/tests/ImageSharp.Benchmarks/LoadResizeSave/LoadResizeSaveStressRunner.cs
index a06784f1b..f8bf19d57 100644
--- a/tests/ImageSharp.Benchmarks/LoadResizeSave/LoadResizeSaveStressRunner.cs
+++ b/tests/ImageSharp.Benchmarks/LoadResizeSave/LoadResizeSaveStressRunner.cs
@@ -19,6 +19,7 @@ using SystemDrawingImage = System.Drawing.Image;
namespace SixLabors.ImageSharp.Benchmarks.LoadResizeSave;
+[Flags]
public enum JpegKind
{
Baseline = 1,
@@ -30,7 +31,7 @@ public class LoadResizeSaveStressRunner
{
private const int Quality = 75;
- // Set the quality for ImagSharp
+ // Set the quality for ImageSharp
private readonly JpegEncoder imageSharpJpegEncoder = new() { Quality = Quality };
private readonly ImageCodecInfo systemDrawingJpegCodec =
ImageCodecInfo.GetImageEncoders().First(codec => codec.FormatID == ImageFormat.Jpeg.Guid);
@@ -39,7 +40,7 @@ public class LoadResizeSaveStressRunner
public double TotalProcessedMegapixels { get; private set; }
- public Size LastProcessedImageSize { get; private set; }
+ public ImageSharpSize LastProcessedImageSize { get; private set; }
private string outputDirectory;
@@ -52,7 +53,7 @@ public class LoadResizeSaveStressRunner
public int ThumbnailSize { get; set; } = 150;
private static readonly string[] ProgressiveFiles =
- {
+ [
"ancyloscelis-apiformis-m-paraguay-face_2014-08-08-095255-zs-pmax_15046500892_o.jpg",
"acanthopus-excellens-f-face-brasil_2014-08-06-132105-zs-pmax_14792513890_o.jpg",
"bee-ceratina-monster-f-ukraine-face_2014-08-09-123342-zs-pmax_15068816101_o.jpg",
@@ -83,8 +84,8 @@ public class LoadResizeSaveStressRunner
"triepeolus-simplex-m-face-md-kent-county_2014-07-22-100937-zs-pmax_14805405233_o.jpg",
"washed-megachile-f-face-chile_2014-08-06-103414-zs-pmax_14977843152_o.jpg",
"xylocopa-balck-violetwing-f-kyrgystan-angle_2014-08-09-182433-zs-pmax_15123416061_o.jpg",
- "xylocopa-india-yellow-m-india-face_2014-08-10-111701-zs-pmax_15166559172_o.jpg",
- };
+ "xylocopa-india-yellow-m-india-face_2014-08-10-111701-zs-pmax_15166559172_o.jpg"
+ ];
public void Init()
{
@@ -126,7 +127,7 @@ public class LoadResizeSaveStressRunner
: Environment.ProcessorCount;
int partitionSize = (int)Math.Ceiling((double)this.Images.Length / maxDegreeOfParallelism);
- List tasks = new();
+ List tasks = [];
for (int i = 0; i < this.Images.Length; i += partitionSize)
{
int end = Math.Min(i + partitionSize, this.Images.Length);
@@ -147,7 +148,7 @@ public class LoadResizeSaveStressRunner
private void LogImageProcessed(int width, int height)
{
- this.LastProcessedImageSize = new Size(width, height);
+ this.LastProcessedImageSize = new ImageSharpSize(width, height);
double pixels = width * (double)height;
this.TotalProcessedMegapixels += pixels / 1_000_000.0;
}
@@ -176,13 +177,13 @@ public class LoadResizeSaveStressRunner
public void SystemDrawingResize(string input)
{
- using var image = SystemDrawingImage.FromFile(input, true);
+ using SystemDrawingImage image = SystemDrawingImage.FromFile(input, true);
this.LogImageProcessed(image.Width, image.Height);
- (int Width, int Height) scaled = this.ScaledSize(image.Width, image.Height, this.ThumbnailSize);
- var resized = new Bitmap(scaled.Width, scaled.Height);
- using var graphics = Graphics.FromImage(resized);
- using var attributes = new ImageAttributes();
+ (int width, int height) = this.ScaledSize(image.Width, image.Height, this.ThumbnailSize);
+ Bitmap resized = new(width, height);
+ using Graphics graphics = Graphics.FromImage(resized);
+ using ImageAttributes attributes = new();
attributes.SetWrapMode(WrapMode.TileFlipXY);
graphics.PixelOffsetMode = PixelOffsetMode.HighQuality;
graphics.CompositingMode = CompositingMode.SourceCopy;
@@ -191,8 +192,8 @@ public class LoadResizeSaveStressRunner
graphics.DrawImage(image, System.Drawing.Rectangle.FromLTRB(0, 0, resized.Width, resized.Height), 0, 0, image.Width, image.Height, GraphicsUnit.Pixel, attributes);
// Save the results
- using var encoderParams = new EncoderParameters(1);
- using var qualityParam = new EncoderParameter(Encoder.Quality, (long)Quality);
+ using EncoderParameters encoderParams = new(1);
+ using EncoderParameter qualityParam = new(Encoder.Quality, (long)Quality);
encoderParams.Param[0] = qualityParam;
resized.Save(this.OutputPath(input), this.systemDrawingJpegCodec, encoderParams);
}
@@ -223,7 +224,7 @@ public class LoadResizeSaveStressRunner
public async Task ImageSharpResizeAsync(string input)
{
- using FileStream output = File.Open(this.OutputPath(input), FileMode.Create);
+ await using FileStream output = File.Open(this.OutputPath(input), FileMode.Create);
// Resize it to fit a 150x150 square.
DecoderOptions options = new()
@@ -246,7 +247,7 @@ public class LoadResizeSaveStressRunner
public void MagickResize(string input)
{
- using var image = new MagickImage(input);
+ using MagickImage image = new(input);
this.LogImageProcessed(image.Width, image.Height);
// Resize it to fit a 150x150 square
@@ -264,7 +265,7 @@ public class LoadResizeSaveStressRunner
public void MagicScalerResize(string input)
{
- var settings = new ProcessImageSettings()
+ ProcessImageSettings settings = new()
{
Width = this.ThumbnailSize,
Height = this.ThumbnailSize,
@@ -273,19 +274,19 @@ public class LoadResizeSaveStressRunner
};
// TODO: Is there a way to capture input dimensions for IncreaseTotalMegapixels?
- using var output = new FileStream(this.OutputPath(input), FileMode.Create);
+ using FileStream output = new(this.OutputPath(input), FileMode.Create);
MagicImageProcessor.ProcessImage(input, output, settings);
}
public void SkiaCanvasResize(string input)
{
- using var original = SKBitmap.Decode(input);
+ using SKBitmap original = SKBitmap.Decode(input);
this.LogImageProcessed(original.Width, original.Height);
- (int Width, int Height) scaled = this.ScaledSize(original.Width, original.Height, this.ThumbnailSize);
- using var surface = SKSurface.Create(new SKImageInfo(scaled.Width, scaled.Height, original.ColorType, original.AlphaType));
- using var paint = new SKPaint() { FilterQuality = SKFilterQuality.High };
+ (int width, int height) = this.ScaledSize(original.Width, original.Height, this.ThumbnailSize);
+ using SKSurface surface = SKSurface.Create(new SKImageInfo(width, height, original.ColorType, original.AlphaType));
+ using SKPaint paint = new() { FilterQuality = SKFilterQuality.High };
SKCanvas canvas = surface.Canvas;
- canvas.Scale((float)scaled.Width / original.Width);
+ canvas.Scale((float)width / original.Width);
canvas.DrawBitmap(original, 0, 0, paint);
canvas.Flush();
@@ -297,16 +298,16 @@ public class LoadResizeSaveStressRunner
public void SkiaBitmapResize(string input)
{
- using var original = SKBitmap.Decode(input);
+ using SKBitmap original = SKBitmap.Decode(input);
this.LogImageProcessed(original.Width, original.Height);
- (int Width, int Height) scaled = this.ScaledSize(original.Width, original.Height, this.ThumbnailSize);
- using var resized = original.Resize(new SKImageInfo(scaled.Width, scaled.Height), SKFilterQuality.High);
+ (int width, int height) = this.ScaledSize(original.Width, original.Height, this.ThumbnailSize);
+ using SKBitmap resized = original.Resize(new SKImageInfo(width, height), SKFilterQuality.High);
if (resized == null)
{
return;
}
- using var image = SKImage.FromBitmap(resized);
+ using SKImage image = SKImage.FromBitmap(resized);
using FileStream output = File.OpenWrite(this.OutputPath(input));
image.Encode(SKEncodedImageFormat.Jpeg, Quality)
.SaveTo(output);
@@ -314,21 +315,21 @@ public class LoadResizeSaveStressRunner
public void SkiaBitmapDecodeToTargetSize(string input)
{
- using var codec = SKCodec.Create(input);
+ using SKCodec codec = SKCodec.Create(input);
SKImageInfo info = codec.Info;
this.LogImageProcessed(info.Width, info.Height);
- (int Width, int Height) scaled = this.ScaledSize(info.Width, info.Height, this.ThumbnailSize);
- SKSizeI supportedScale = codec.GetScaledDimensions((float)scaled.Width / info.Width);
+ (int width, int height) = this.ScaledSize(info.Width, info.Height, this.ThumbnailSize);
+ SKSizeI supportedScale = codec.GetScaledDimensions((float)width / info.Width);
- using var original = SKBitmap.Decode(codec, new SKImageInfo(supportedScale.Width, supportedScale.Height));
- using SKBitmap resized = original.Resize(new SKImageInfo(scaled.Width, scaled.Height), SKFilterQuality.High);
+ using SKBitmap original = SKBitmap.Decode(codec, new SKImageInfo(supportedScale.Width, supportedScale.Height));
+ using SKBitmap resized = original.Resize(new SKImageInfo(width, height), SKFilterQuality.High);
if (resized == null)
{
return;
}
- using var image = SKImage.FromBitmap(resized);
+ using SKImage image = SKImage.FromBitmap(resized);
using FileStream output = File.OpenWrite(this.OutputPath(input, nameof(this.SkiaBitmapDecodeToTargetSize)));
image.Encode(SKEncodedImageFormat.Jpeg, Quality)
@@ -338,7 +339,7 @@ public class LoadResizeSaveStressRunner
public void NetVipsResize(string input)
{
// Thumbnail to fit a 150x150 square
- using var thumb = NetVipsImage.Thumbnail(input, this.ThumbnailSize, this.ThumbnailSize);
+ using NetVipsImage thumb = NetVipsImage.Thumbnail(input, this.ThumbnailSize, this.ThumbnailSize);
// Save the results
thumb.Jpegsave(this.OutputPath(input), q: Quality, keep: NetVips.Enums.ForeignKeep.None);
diff --git a/tests/ImageSharp.Benchmarks/Processing/Crop.cs b/tests/ImageSharp.Benchmarks/Processing/Crop.cs
index 0432b7624..e14366bfd 100644
--- a/tests/ImageSharp.Benchmarks/Processing/Crop.cs
+++ b/tests/ImageSharp.Benchmarks/Processing/Crop.cs
@@ -17,9 +17,9 @@ public class Crop
[Benchmark(Baseline = true, Description = "System.Drawing Crop")]
public SDSize CropSystemDrawing()
{
- using var source = new Bitmap(800, 800);
- using var destination = new Bitmap(100, 100);
- using var graphics = Graphics.FromImage(destination);
+ using Bitmap source = new(800, 800);
+ using Bitmap destination = new(100, 100);
+ using Graphics graphics = Graphics.FromImage(destination);
graphics.InterpolationMode = InterpolationMode.HighQualityBicubic;
graphics.PixelOffsetMode = PixelOffsetMode.HighQuality;
@@ -32,7 +32,7 @@ public class Crop
[Benchmark(Description = "ImageSharp Crop")]
public Size CropImageSharp()
{
- using var image = new Image(800, 800);
+ using Image image = new(800, 800);
image.Mutate(x => x.Crop(100, 100));
return new Size(image.Width, image.Height);
}
diff --git a/tests/ImageSharp.Benchmarks/Processing/HistogramEqualization.cs b/tests/ImageSharp.Benchmarks/Processing/HistogramEqualization.cs
index 135145a31..93ac9fc0e 100644
--- a/tests/ImageSharp.Benchmarks/Processing/HistogramEqualization.cs
+++ b/tests/ImageSharp.Benchmarks/Processing/HistogramEqualization.cs
@@ -33,7 +33,7 @@ public class HistogramEqualization
[Benchmark(Description = "Global Histogram Equalization")]
public void GlobalHistogramEqualization()
=> this.image.Mutate(img => img.HistogramEqualization(
- new HistogramEqualizationOptions()
+ new HistogramEqualizationOptions
{
LuminanceLevels = 256,
Method = HistogramEqualizationMethod.Global
@@ -42,7 +42,7 @@ public class HistogramEqualization
[Benchmark(Description = "AdaptiveHistogramEqualization (Tile interpolation)")]
public void AdaptiveHistogramEqualization()
=> this.image.Mutate(img => img.HistogramEqualization(
- new HistogramEqualizationOptions()
+ new HistogramEqualizationOptions
{
LuminanceLevels = 256,
Method = HistogramEqualizationMethod.AdaptiveTileInterpolation
diff --git a/tests/ImageSharp.Benchmarks/Processing/OilPaint.cs b/tests/ImageSharp.Benchmarks/Processing/OilPaint.cs
index e3e413fe4..707748499 100644
--- a/tests/ImageSharp.Benchmarks/Processing/OilPaint.cs
+++ b/tests/ImageSharp.Benchmarks/Processing/OilPaint.cs
@@ -13,7 +13,7 @@ public class OilPaint
[Benchmark]
public void DoOilPaint()
{
- using Image image = new Image(1920, 1200, new(127, 191, 255));
+ using Image image = new(1920, 1200, new RgbaVector(127, 191, 255));
image.Mutate(ctx => ctx.OilPaint());
}
}
diff --git a/tests/ImageSharp.Benchmarks/Processing/Resize.cs b/tests/ImageSharp.Benchmarks/Processing/Resize.cs
index 05baceb6a..3cc10afb7 100644
--- a/tests/ImageSharp.Benchmarks/Processing/Resize.cs
+++ b/tests/ImageSharp.Benchmarks/Processing/Resize.cs
@@ -12,17 +12,17 @@ using SDImage = System.Drawing.Image;
namespace SixLabors.ImageSharp.Benchmarks;
-[Config(typeof(Config.Standard))]
+[Config(typeof(Config.StandardInProcess))]
public abstract class Resize
where TPixel : unmanaged, IPixel
{
- private byte[] bytes = null;
+ private byte[] bytes;
private Image sourceImage;
private SDImage sourceBitmap;
- protected Configuration Configuration { get; } = new Configuration(new JpegConfigurationModule());
+ protected Configuration Configuration { get; } = new(new JpegConfigurationModule());
protected int DestSize { get; private set; }
@@ -35,7 +35,7 @@ public abstract class Resize
this.sourceImage = Image.Load(this.bytes);
- var ms1 = new MemoryStream(this.bytes);
+ MemoryStream ms1 = new(this.bytes);
this.sourceBitmap = SDImage.FromStream(ms1);
this.DestSize = this.sourceBitmap.Width / 2;
}
@@ -52,21 +52,19 @@ public abstract class Resize
[Benchmark(Baseline = true)]
public int SystemDrawing()
{
- using (var destination = new Bitmap(this.DestSize, this.DestSize))
+ using Bitmap destination = new(this.DestSize, this.DestSize);
+ using (Graphics g = Graphics.FromImage(destination))
{
- using (var g = Graphics.FromImage(destination))
- {
- g.CompositingMode = CompositingMode.SourceCopy;
- g.InterpolationMode = InterpolationMode.HighQualityBicubic;
- g.PixelOffsetMode = PixelOffsetMode.HighQuality;
- g.CompositingQuality = CompositingQuality.HighQuality;
- g.SmoothingMode = SmoothingMode.HighQuality;
-
- g.DrawImage(this.sourceBitmap, 0, 0, this.DestSize, this.DestSize);
- }
-
- return destination.Width;
+ g.CompositingMode = CompositingMode.SourceCopy;
+ g.InterpolationMode = InterpolationMode.HighQualityBicubic;
+ g.PixelOffsetMode = PixelOffsetMode.HighQuality;
+ g.CompositingQuality = CompositingQuality.HighQuality;
+ g.SmoothingMode = SmoothingMode.HighQuality;
+
+ g.DrawImage(this.sourceBitmap, 0, 0, this.DestSize, this.DestSize);
}
+
+ return destination.Width;
}
[Benchmark(Description = "ImageSharp, MaxDegreeOfParallelism = 1")]
@@ -87,10 +85,8 @@ public abstract class Resize
{
this.Configuration.MaxDegreeOfParallelism = maxDegreeOfParallelism;
- using (Image clone = this.sourceImage.Clone(this.ExecuteResizeOperation))
- {
- return clone.Width;
- }
+ using Image clone = this.sourceImage.Clone(this.ExecuteResizeOperation);
+ return clone.Width;
}
protected abstract void ExecuteResizeOperation(IImageProcessingContext ctx);
diff --git a/tests/ImageSharp.Tests.ProfilingSandbox/ImageSharp.Tests.ProfilingSandbox.csproj b/tests/ImageSharp.Tests.ProfilingSandbox/ImageSharp.Tests.ProfilingSandbox.csproj
index 832f3d171..bc52610d2 100644
--- a/tests/ImageSharp.Tests.ProfilingSandbox/ImageSharp.Tests.ProfilingSandbox.csproj
+++ b/tests/ImageSharp.Tests.ProfilingSandbox/ImageSharp.Tests.ProfilingSandbox.csproj
@@ -19,7 +19,7 @@
- net8.0;net9.0
+ net8.0;net10.0
diff --git a/tests/ImageSharp.Tests.ProfilingSandbox/LoadResizeSaveParallelMemoryStress.cs b/tests/ImageSharp.Tests.ProfilingSandbox/LoadResizeSaveParallelMemoryStress.cs
index 248912b14..6850756df 100644
--- a/tests/ImageSharp.Tests.ProfilingSandbox/LoadResizeSaveParallelMemoryStress.cs
+++ b/tests/ImageSharp.Tests.ProfilingSandbox/LoadResizeSaveParallelMemoryStress.cs
@@ -17,7 +17,7 @@ internal class LoadResizeSaveParallelMemoryStress
{
private LoadResizeSaveParallelMemoryStress()
{
- this.Benchmarks = new LoadResizeSaveStressRunner()
+ this.Benchmarks = new LoadResizeSaveStressRunner
{
Filter = JpegKind.Baseline,
};
@@ -38,7 +38,7 @@ internal class LoadResizeSaveParallelMemoryStress
Console.WriteLine($"64 bit: {Environment.Is64BitProcess}");
CommandLineOptions options = args.Length > 0 ? CommandLineOptions.Parse(args) : null;
- var lrs = new LoadResizeSaveParallelMemoryStress();
+ LoadResizeSaveParallelMemoryStress lrs = new();
if (options != null)
{
lrs.Benchmarks.MaxDegreeOfParallelism = options.MaxDegreeOfParallelism;
@@ -108,7 +108,7 @@ internal class LoadResizeSaveParallelMemoryStress
}
}
- var stats = new Stats(timer, lrs.Benchmarks.TotalProcessedMegapixels);
+ Stats stats = new(timer, lrs.Benchmarks.TotalProcessedMegapixels);
Console.WriteLine($"Total Megapixels: {stats.TotalMegapixels}, TotalOomRetries: {UnmanagedMemoryHandle.TotalOomRetries}, TotalOutstandingHandles: {UnmanagedMemoryHandle.TotalOutstandingHandles}, Total Gen2 GC count: {GC.CollectionCount(2)}");
Console.WriteLine(stats.GetMarkdown());
if (options?.FileOutput != null)
@@ -203,7 +203,7 @@ internal class LoadResizeSaveParallelMemoryStress
public string GetMarkdown()
{
- var bld = new StringBuilder();
+ StringBuilder bld = new();
bld.AppendLine($"| {nameof(this.TotalSeconds)} | {nameof(this.MegapixelsPerSec)} | {nameof(this.MegapixelsPerSecPerCpu)} |");
bld.AppendLine(
$"| {L(nameof(this.TotalSeconds))} | {L(nameof(this.MegapixelsPerSec))} | {L(nameof(this.MegapixelsPerSecPerCpu))} |");
diff --git a/tests/ImageSharp.Tests.ProfilingSandbox/Program.cs b/tests/ImageSharp.Tests.ProfilingSandbox/Program.cs
index b5c8b70cd..8ba862560 100644
--- a/tests/ImageSharp.Tests.ProfilingSandbox/Program.cs
+++ b/tests/ImageSharp.Tests.ProfilingSandbox/Program.cs
@@ -52,7 +52,7 @@ public class Program
{
Assembly assembly = typeof(System.Runtime.GCSettings).GetTypeInfo().Assembly;
Console.WriteLine(assembly.Location);
- string[] assemblyPath = assembly.Location.Split(new[] { '/', '\\' }, StringSplitOptions.RemoveEmptyEntries);
+ string[] assemblyPath = assembly.Location.Split(['/', '\\'], StringSplitOptions.RemoveEmptyEntries);
int netCoreAppIndex = Array.IndexOf(assemblyPath, "Microsoft.NETCore.App");
if (netCoreAppIndex > 0 && netCoreAppIndex < assemblyPath.Length - 2)
{
@@ -64,13 +64,13 @@ public class Program
private static void RunResizeProfilingTest()
{
- var test = new ResizeProfilingBenchmarks(new ConsoleOutput());
+ ResizeProfilingBenchmarks test = new(new ConsoleOutput());
test.ResizeBicubic(4000, 4000);
}
private static void RunToVector4ProfilingTest()
{
- var tests = new PixelOperationsTests.Rgba32_OperationsTests(new ConsoleOutput());
+ PixelOperationsTests.Rgba32_OperationsTests tests = new(new ConsoleOutput());
tests.Benchmark_ToVector4();
}
}
diff --git a/tests/ImageSharp.Tests/Color/ColorTests.CastTo.cs b/tests/ImageSharp.Tests/Color/ColorTests.CastTo.cs
index 4247345c7..2e2f0d07d 100644
--- a/tests/ImageSharp.Tests/Color/ColorTests.CastTo.cs
+++ b/tests/ImageSharp.Tests/Color/ColorTests.CastTo.cs
@@ -13,10 +13,10 @@ public partial class ColorTests
[Fact]
public void Rgba64()
{
- var source = new Rgba64(100, 2222, 3333, 4444);
+ Rgba64 source = new(100, 2222, 3333, 4444);
// Act:
- var color = Color.FromPixel(source);
+ Color color = Color.FromPixel(source);
// Assert:
Rgba64 data = color.ToPixel();
@@ -26,10 +26,10 @@ public partial class ColorTests
[Fact]
public void Rgba32()
{
- var source = new Rgba32(1, 22, 33, 231);
+ Rgba32 source = new(1, 22, 33, 231);
// Act:
- var color = Color.FromPixel(source);
+ Color color = Color.FromPixel(source);
// Assert:
Rgba32 data = color.ToPixel();
@@ -39,10 +39,10 @@ public partial class ColorTests
[Fact]
public void Argb32()
{
- var source = new Argb32(1, 22, 33, 231);
+ Argb32 source = new(1, 22, 33, 231);
// Act:
- var color = Color.FromPixel(source);
+ Color color = Color.FromPixel(source);
// Assert:
Argb32 data = color.ToPixel();
@@ -52,10 +52,10 @@ public partial class ColorTests
[Fact]
public void Bgra32()
{
- var source = new Bgra32(1, 22, 33, 231);
+ Bgra32 source = new(1, 22, 33, 231);
// Act:
- var color = Color.FromPixel(source);
+ Color color = Color.FromPixel(source);
// Assert:
Bgra32 data = color.ToPixel();
@@ -65,10 +65,10 @@ public partial class ColorTests
[Fact]
public void Abgr32()
{
- var source = new Abgr32(1, 22, 33, 231);
+ Abgr32 source = new(1, 22, 33, 231);
// Act:
- var color = Color.FromPixel(source);
+ Color color = Color.FromPixel(source);
// Assert:
Abgr32 data = color.ToPixel();
@@ -78,10 +78,10 @@ public partial class ColorTests
[Fact]
public void Rgb24()
{
- var source = new Rgb24(1, 22, 231);
+ Rgb24 source = new(1, 22, 231);
// Act:
- var color = Color.FromPixel(source);
+ Color color = Color.FromPixel(source);
// Assert:
Rgb24 data = color.ToPixel();
@@ -91,10 +91,10 @@ public partial class ColorTests
[Fact]
public void Bgr24()
{
- var source = new Bgr24(1, 22, 231);
+ Bgr24 source = new(1, 22, 231);
// Act:
- var color = Color.FromPixel(source);
+ Color color = Color.FromPixel(source);
// Assert:
Bgr24 data = color.ToPixel();
@@ -129,7 +129,7 @@ public partial class ColorTests
where TPixel : unmanaged, IPixel
{
// Act:
- var color = Color.FromPixel(source);
+ Color color = Color.FromPixel(source);
// Assert:
TPixel actual = color.ToPixel();
@@ -150,7 +150,7 @@ public partial class ColorTests
where TPixel2 : unmanaged, IPixel
{
// Act:
- var color = Color.FromPixel(source);
+ Color color = Color.FromPixel(source);
// Assert:
TPixel2 actual = color.ToPixel();
diff --git a/tests/ImageSharp.Tests/Color/ColorTests.cs b/tests/ImageSharp.Tests/Color/ColorTests.cs
index d430df5b4..c482fc998 100644
--- a/tests/ImageSharp.Tests/Color/ColorTests.cs
+++ b/tests/ImageSharp.Tests/Color/ColorTests.cs
@@ -67,9 +67,9 @@ public partial class ColorTests
[Theory]
[InlineData(false)]
[InlineData(true)]
- public void ToHex(bool highPrecision)
+ public void ToHexRgba(bool highPrecision)
{
- string expected = "ABCD1234";
+ const string expected = "AABBCCDD";
Color color = Color.ParseHex(expected);
if (highPrecision)
@@ -81,10 +81,27 @@ public partial class ColorTests
Assert.Equal(expected, actual);
}
+ [Theory]
+ [InlineData(false)]
+ [InlineData(true)]
+ public void ToHexArgb(bool highPrecision)
+ {
+ const string expected = "AABBCCDD";
+ Color color = Color.ParseHex(expected, ColorHexFormat.Argb);
+
+ if (highPrecision)
+ {
+ color = Color.FromPixel(color.ToPixel());
+ }
+
+ string actual = color.ToHex(ColorHexFormat.Argb);
+ Assert.Equal(expected, actual);
+ }
+
[Fact]
public void WebSafePalette_IsCorrect()
{
- Rgba32[] actualPalette = Color.WebSafePalette.ToArray().Select(c => c.ToPixel()).ToArray();
+ Rgba32[] actualPalette = [.. Color.WebSafePalette.ToArray().Select(c => c.ToPixel())];
for (int i = 0; i < ReferencePalette.WebSafeColors.Length; i++)
{
@@ -95,7 +112,7 @@ public partial class ColorTests
[Fact]
public void WernerPalette_IsCorrect()
{
- Rgba32[] actualPalette = Color.WernerPalette.ToArray().Select(c => c.ToPixel()).ToArray();
+ Rgba32[] actualPalette = [.. Color.WernerPalette.ToArray().Select(c => c.ToPixel())];
for (int i = 0; i < ReferencePalette.WernerColors.Length; i++)
{
@@ -103,7 +120,7 @@ public partial class ColorTests
}
}
- public class FromHex
+ public class FromHexRgba
{
[Fact]
public void ShortHex()
@@ -126,6 +143,23 @@ public partial class ColorTests
Assert.Equal(new Rgba32(0, 0, 0, 255), actual.ToPixel());
}
+ [Fact]
+ public void LongHex()
+ {
+ Assert.Equal(new Rgba32(255, 255, 255, 0), Color.ParseHex("#FFFFFF00").ToPixel());
+ Assert.Equal(new Rgba32(255, 255, 255, 128), Color.ParseHex("#FFFFFF80").ToPixel());
+ }
+
+ [Fact]
+ public void TryLongHex()
+ {
+ Assert.True(Color.TryParseHex("#FFFFFF00", out Color actual));
+ Assert.Equal(new Rgba32(255, 255, 255, 0), actual.ToPixel());
+
+ Assert.True(Color.TryParseHex("#FFFFFF80", out actual));
+ Assert.Equal(new Rgba32(255, 255, 255, 128), actual.ToPixel());
+ }
+
[Fact]
public void LeadingPoundIsOptional()
{
@@ -152,6 +186,72 @@ public partial class ColorTests
public void FalseOnNull() => Assert.False(Color.TryParseHex(null, out Color _));
}
+ public class FromHexArgb
+ {
+ [Fact]
+ public void ShortHex()
+ {
+ Assert.Equal(new Rgb24(255, 255, 255), Color.ParseHex("#fff", ColorHexFormat.Argb).ToPixel());
+ Assert.Equal(new Rgb24(255, 255, 255), Color.ParseHex("fff", ColorHexFormat.Argb).ToPixel());
+ Assert.Equal(new Argb32(0, 0, 255, 0), Color.ParseHex("000f", ColorHexFormat.Argb).ToPixel());
+ }
+
+ [Fact]
+ public void TryShortHex()
+ {
+ Assert.True(Color.TryParseHex("#fff", out Color actual, ColorHexFormat.Argb));
+ Assert.Equal(new Rgb24(255, 255, 255), actual.ToPixel());
+
+ Assert.True(Color.TryParseHex("fff", out actual, ColorHexFormat.Argb));
+ Assert.Equal(new Rgb24(255, 255, 255), actual.ToPixel());
+
+ Assert.True(Color.TryParseHex("000f", out actual, ColorHexFormat.Argb));
+ Assert.Equal(new Argb32(0, 0, 255, 0), actual.ToPixel());
+ }
+
+ [Fact]
+ public void LongHex()
+ {
+ Assert.Equal(new Argb32(255, 255, 255, 0), Color.ParseHex("#00FFFFFF", ColorHexFormat.Argb).ToPixel());
+ Assert.Equal(new Argb32(255, 255, 255, 128), Color.ParseHex("#80FFFFFF", ColorHexFormat.Argb).ToPixel());
+ }
+
+ [Fact]
+ public void TryLongHex()
+ {
+ Assert.True(Color.TryParseHex("#00FFFFFF", out Color actual, ColorHexFormat.Argb));
+ Assert.Equal(new Argb32(255, 255, 255, 0), actual.ToPixel());
+
+ Assert.True(Color.TryParseHex("#80FFFFFF", out actual, ColorHexFormat.Argb));
+ Assert.Equal(new Argb32(255, 255, 255, 128), actual.ToPixel());
+ }
+
+ [Fact]
+ public void LeadingPoundIsOptional()
+ {
+ Assert.Equal(new Rgb24(0, 128, 128), Color.ParseHex("#008080", ColorHexFormat.Argb).ToPixel());
+ Assert.Equal(new Rgb24(0, 128, 128), Color.ParseHex("008080", ColorHexFormat.Argb).ToPixel());
+ }
+
+ [Fact]
+ public void ThrowsOnEmpty() => Assert.Throws(() => Color.ParseHex(string.Empty, ColorHexFormat.Argb));
+
+ [Fact]
+ public void ThrowsOnInvalid() => Assert.Throws(() => Color.ParseHex("!", ColorHexFormat.Argb));
+
+ [Fact]
+ public void ThrowsOnNull() => Assert.Throws(() => Color.ParseHex(null, ColorHexFormat.Argb));
+
+ [Fact]
+ public void FalseOnEmpty() => Assert.False(Color.TryParseHex(string.Empty, out Color _, ColorHexFormat.Argb));
+
+ [Fact]
+ public void FalseOnInvalid() => Assert.False(Color.TryParseHex("!", out Color _, ColorHexFormat.Argb));
+
+ [Fact]
+ public void FalseOnNull() => Assert.False(Color.TryParseHex(null, out Color _, ColorHexFormat.Argb));
+ }
+
public class FromString
{
[Fact]
diff --git a/tests/ImageSharp.Tests/Color/ReferencePalette.cs b/tests/ImageSharp.Tests/Color/ReferencePalette.cs
index 8e2696109..88787afd4 100644
--- a/tests/ImageSharp.Tests/Color/ReferencePalette.cs
+++ b/tests/ImageSharp.Tests/Color/ReferencePalette.cs
@@ -9,7 +9,7 @@ internal static class ReferencePalette
/// Gets a collection of named, web safe, colors as defined in the CSS Color Module Level 4.
///
public static readonly Color[] WebSafeColors =
- {
+ [
Color.AliceBlue,
Color.AntiqueWhite,
Color.Aqua,
@@ -152,14 +152,14 @@ internal static class ReferencePalette
Color.WhiteSmoke,
Color.Yellow,
Color.YellowGreen
- };
+ ];
///
/// Gets a collection of colors as defined in the original second edition of Werner’s Nomenclature of Colours 1821.
/// The hex codes were collected and defined by Nicholas Rougeux
///
public static readonly Color[] WernerColors =
- {
+ [
Color.ParseHex("#f1e9cd"),
Color.ParseHex("#f2e7cf"),
Color.ParseHex("#ece6d0"),
@@ -270,10 +270,10 @@ internal static class ReferencePalette
Color.ParseHex("#9b856b"),
Color.ParseHex("#766051"),
Color.ParseHex("#453b32")
- };
+ ];
public static readonly Dictionary ColorNames =
- new Dictionary(StringComparer.OrdinalIgnoreCase)
+ new(StringComparer.OrdinalIgnoreCase)
{
{ nameof(Color.AliceBlue), Color.AliceBlue },
{ nameof(Color.AntiqueWhite), Color.AntiqueWhite },
diff --git a/tests/ImageSharp.Tests/Color/RgbaDouble.cs b/tests/ImageSharp.Tests/Color/RgbaDouble.cs
index 9a751e879..76fdf365c 100644
--- a/tests/ImageSharp.Tests/Color/RgbaDouble.cs
+++ b/tests/ImageSharp.Tests/Color/RgbaDouble.cs
@@ -115,7 +115,7 @@ public struct RgbaDouble : IPixel
public static RgbaDouble FromVector4(Vector4 source)
{
source = Numerics.Clamp(source, Vector4.Zero, Vector4.One);
- return new(source.X, source.Y, source.Z, source.W);
+ return new RgbaDouble(source.X, source.Y, source.Z, source.W);
}
///
diff --git a/tests/ImageSharp.Tests/ColorProfiles/ApproximateColorProfileComparer.cs b/tests/ImageSharp.Tests/ColorProfiles/ApproximateColorProfileComparer.cs
index 56d495a87..f4078887c 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/ApproximateColorProfileComparer.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/ApproximateColorProfileComparer.cs
@@ -22,7 +22,9 @@ internal readonly struct ApproximateColorProfileComparer :
IEqualityComparer,
IEqualityComparer,
IEqualityComparer,
- IEqualityComparer
+ IEqualityComparer,
+ IEqualityComparer,
+ IEqualityComparer
{
private readonly float epsilon;
@@ -58,6 +60,10 @@ internal readonly struct ApproximateColorProfileComparer :
public bool Equals(HunterLab x, HunterLab y) => this.Equals(x.L, y.L) && this.Equals(x.A, y.A) && this.Equals(x.B, y.B);
+ public bool Equals(Y x, Y y) => this.Equals(x.L, y.L);
+
+ public bool Equals(YccK x, YccK y) => this.Equals(x.Y, y.Y) && this.Equals(x.Cb, y.Cb) && this.Equals(x.Cr, y.Cr) && this.Equals(x.K, y.K);
+
public int GetHashCode([DisallowNull] CieLab obj) => obj.GetHashCode();
public int GetHashCode([DisallowNull] CieXyz obj) => obj.GetHashCode();
@@ -84,6 +90,10 @@ internal readonly struct ApproximateColorProfileComparer :
public int GetHashCode([DisallowNull] HunterLab obj) => obj.GetHashCode();
+ public int GetHashCode([DisallowNull] Y obj) => obj.GetHashCode();
+
+ public int GetHashCode([DisallowNull] YccK obj) => obj.GetHashCode();
+
private bool Equals(float x, float y)
{
float d = x - y;
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLabAndCieLchConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLabAndCieLchConversionTests.cs
index 9a894c776..d6e373895 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLabAndCieLchConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLabAndCieLchConversionTests.cs
@@ -12,6 +12,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
/// Test data generated using:
///
///
+[Trait("Color", "Conversion")]
public class CieLabAndCieLchConversionTests
{
private static readonly ApproximateColorProfileComparer Comparer = new(.0001f);
@@ -30,7 +31,7 @@ public class CieLabAndCieLchConversionTests
// Arrange
CieLch input = new(l, c, h);
CieLab expected = new(l2, a, b);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D50, TargetWhitePoint = KnownIlluminants.D50 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D50, TargetWhitePoint = KnownIlluminants.D50 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLch[5];
@@ -65,7 +66,7 @@ public class CieLabAndCieLchConversionTests
// Arrange
CieLab input = new(l, a, b);
CieLch expected = new(l2, c, h);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D50, TargetWhitePoint = KnownIlluminants.D50 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D50, TargetWhitePoint = KnownIlluminants.D50 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLab[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLabAndCieLchuvConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLabAndCieLchuvConversionTests.cs
index 4b1b5e1a5..73fa7128f 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLabAndCieLchuvConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLabAndCieLchuvConversionTests.cs
@@ -24,7 +24,7 @@ public class CieLabAndCieLchuvConversionTests
// Arrange
CieLchuv input = new(l, c, h);
CieLab expected = new(l2, a, b);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D50 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D50 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLchuv[5];
@@ -53,7 +53,7 @@ public class CieLabAndCieLchuvConversionTests
// Arrange
CieLab input = new(l, a, b);
CieLchuv expected = new(l2, c, h);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D50, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D50, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLab[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLabAndCieLuvConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLabAndCieLuvConversionTests.cs
index 44756c779..0846bdda3 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLabAndCieLuvConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLabAndCieLuvConversionTests.cs
@@ -24,7 +24,7 @@ public class CieLabAndCieLuvConversionTests
// Arrange
CieLuv input = new(l, u, v);
CieLab expected = new(l2, a, b);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D50 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D50 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLuv[5];
@@ -53,7 +53,7 @@ public class CieLabAndCieLuvConversionTests
// Arrange
CieLab input = new(l, a, b);
CieLuv expected = new(l2, u, v);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D50, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D50, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLab[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLabAndYCbCrConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLabAndYCbCrConversionTests.cs
index 9a29b1539..15677c46f 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLabAndYCbCrConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLabAndYCbCrConversionTests.cs
@@ -13,8 +13,9 @@ public class CieLabAndYCbCrConversionTests
private static readonly ApproximateColorProfileComparer Comparer = new(.0002F);
[Theory]
- [InlineData(0, 128, 128, 0, 0, 0)]
- [InlineData(87.4179, 133.9763, 247.5308, 55.06287, 82.54838, 23.1697)]
+ [InlineData(1, .5F, .5F, 100, 0, 0)]
+ [InlineData(0, .5F, .5F, 0, 0, 0)]
+ [InlineData(.5F, .5F, .5F, 53.38897F, 0, 0)]
public void Convert_YCbCr_to_CieLab(float y, float cb, float cr, float l, float a, float b)
{
// Arrange
@@ -41,8 +42,9 @@ public class CieLabAndYCbCrConversionTests
}
[Theory]
- [InlineData(0, 0, 0, 0, 128, 128)]
- [InlineData(55.06287, 82.54838, 23.1697, 87.41701, 133.97232, 247.5314)]
+ [InlineData(100, 0, 0, 1, .5F, .5F)]
+ [InlineData(0, 0, 0, 0, .5F, .5F)]
+ [InlineData(53.38897F, 0, 0, .5F, .5F, .5F)]
public void Convert_CieLab_to_YCbCr(float l, float a, float b, float y, float cb, float cr)
{
// Arrange
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLabTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLabTests.cs
index 3c015259b..69fabc750 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLabTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLabTests.cs
@@ -9,6 +9,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
/// Tests the struct.
///
+[Trait("Color", "Conversion")]
public class CieLabTests
{
[Fact]
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLchAndCieLuvConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLchAndCieLuvConversionTests.cs
index 598d4af33..12313281f 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLchAndCieLuvConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLchAndCieLuvConversionTests.cs
@@ -20,7 +20,7 @@ public class CieLchAndCieLuvConversionTests
// Arrange
CieLch input = new(l, c, h);
CieLuv expected = new(l2, u, v);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D50, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D50, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLch[5];
@@ -48,7 +48,7 @@ public class CieLchAndCieLuvConversionTests
// Arrange
CieLuv input = new(l2, u, v);
CieLch expected = new(l, c, h);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D50 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D50 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLuv[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLchuvAndCieLchConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLchuvAndCieLchConversionTests.cs
index a3e0b45e0..857bdb3da 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLchuvAndCieLchConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLchuvAndCieLchConversionTests.cs
@@ -20,7 +20,7 @@ public class CieLchuvAndCieLchConversionTests
// Arrange
CieLch input = new(l2, c2, h2);
CieLchuv expected = new(l, c, h);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D50, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D50, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLch[5];
@@ -48,7 +48,7 @@ public class CieLchuvAndCieLchConversionTests
// Arrange
CieLchuv input = new(l, c, h);
CieLch expected = new(l2, c2, h2);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D50 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D50 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLchuv[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLchuvAndCieLuvConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLchuvAndCieLuvConversionTests.cs
index 465237490..424cb8cc7 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLchuvAndCieLuvConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLchuvAndCieLuvConversionTests.cs
@@ -12,6 +12,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
/// Test data generated using:
///
///
+[Trait("Color", "Conversion")]
public class CieLchuvAndCieLuvConversionTests
{
private static readonly ApproximateColorProfileComparer Comparer = new(.0001F);
@@ -30,7 +31,7 @@ public class CieLchuvAndCieLuvConversionTests
// Arrange
CieLchuv input = new(l, c, h);
CieLuv expected = new(l2, u, v);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLchuv[5];
@@ -66,7 +67,7 @@ public class CieLchuvAndCieLuvConversionTests
// Arrange
CieLuv input = new(l, u, v);
CieLchuv expected = new(l2, c, h);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLuv[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLchuvAndCmykConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLchuvAndCmykConversionTests.cs
index 60ac3da16..3c8a93ee1 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLchuvAndCmykConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLchuvAndCmykConversionTests.cs
@@ -20,7 +20,7 @@ public class CieLchuvAndCmykConversionTests
// Arrange
Cmyk input = new(c2, m, y, k);
CieLchuv expected = new(l, c, h);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new Cmyk[5];
@@ -49,7 +49,7 @@ public class CieLchuvAndCmykConversionTests
// Arrange
CieLchuv input = new(l, c, h);
Cmyk expected = new(c2, m, y, k);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLchuv[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLchuvTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLchuvTests.cs
index 0b737cdfc..3fe550a5b 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLchuvTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLchuvTests.cs
@@ -9,6 +9,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
/// Tests the struct.
///
+[Trait("Color", "Conversion")]
public class CieLchuvTests
{
[Fact]
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndCieXyyConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndCieXyyConversionTests.cs
index e73edcda7..08e73a1a7 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndCieXyyConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndCieXyyConversionTests.cs
@@ -20,7 +20,7 @@ public class CieLuvAndCieXyyConversionTests
// Arrange
CieLuv input = new(l, u, v);
CieXyy expected = new(x, y, yl);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLuv[5];
@@ -49,7 +49,7 @@ public class CieLuvAndCieXyyConversionTests
// Arrange
CieXyy input = new(x, y, yl);
CieLuv expected = new(l, u, v);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieXyy[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndHslConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndHslConversionTests.cs
index b178b22b2..bfcd236c7 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndHslConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndHslConversionTests.cs
@@ -20,7 +20,7 @@ public class CieLuvAndHslConversionTests
// Arrange
CieLuv input = new(l, u, v);
Hsl expected = new(h, s, l2);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLuv[5];
@@ -49,7 +49,7 @@ public class CieLuvAndHslConversionTests
// Arrange
Hsl input = new(h, s, l2);
CieLuv expected = new(l, u, v);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new Hsl[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndHsvConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndHsvConversionTests.cs
index 286609337..8a25f95b7 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndHsvConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndHsvConversionTests.cs
@@ -20,7 +20,7 @@ public class CieLuvAndHsvConversionTests
// Arrange
CieLuv input = new(l, u, v);
Hsv expected = new(h, s, v2);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLuv[5];
@@ -49,7 +49,7 @@ public class CieLuvAndHsvConversionTests
// Arrange
Hsv input = new(h, s, v2);
CieLuv expected = new(l, u, v);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new Hsv[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndHunterLabConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndHunterLabConversionTests.cs
index 73b605fb6..1c667f679 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndHunterLabConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndHunterLabConversionTests.cs
@@ -20,7 +20,7 @@ public class CieLuvAndHunterLabConversionTests
// Arrange
CieLuv input = new(l, u, v);
HunterLab expected = new(l2, a, b);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D50 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D50 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLuv[5];
@@ -49,7 +49,7 @@ public class CieLuvAndHunterLabConversionTests
// Arrange
HunterLab input = new(l2, a, b);
CieLuv expected = new(l, u, v);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D50, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D50, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new HunterLab[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndLmsConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndLmsConversionTests.cs
index 812ca44dd..812b2b61e 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndLmsConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndLmsConversionTests.cs
@@ -20,7 +20,7 @@ public class CieLuvAndLmsConversionTests
// Arrange
CieLuv input = new(l, u, v);
Lms expected = new(l2, m, s);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLuv[5];
@@ -49,7 +49,7 @@ public class CieLuvAndLmsConversionTests
// Arrange
Lms input = new(l2, m, s);
CieLuv expected = new(l, u, v);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new Lms[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndRgbConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndRgbConversionTests.cs
index f1da6e33f..1af802326 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndRgbConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndRgbConversionTests.cs
@@ -20,7 +20,7 @@ public class CieLuvAndRgbConversionTests
// Arrange
CieLuv input = new(l, u, v);
Rgb expected = new(r, g, b);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLuv[5];
@@ -49,7 +49,7 @@ public class CieLuvAndRgbConversionTests
// Arrange
Rgb input = new(r, g, b);
CieLuv expected = new(l, u, v);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new Rgb[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndYCbCrConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndYCbCrConversionTests.cs
index fa7e2ece3..62b276a1f 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndYCbCrConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLuvAndYCbCrConversionTests.cs
@@ -13,14 +13,15 @@ public class CieLuvAndYCbCrConversionTests
private static readonly ApproximateColorProfileComparer Comparer = new(.0002F);
[Theory]
- [InlineData(0, 0, 0, 0, 128, 128)]
- [InlineData(36.0555, 93.6901, 10.01514, 71.8283, 119.3174, 193.9839)]
+ [InlineData(100, 0, 0, 1, .5F, .5F)]
+ [InlineData(0, 0, 0, 0, .5F, .5F)]
+ [InlineData(53.38897F, 0, 0, .5F, .5F, .5F)]
public void Convert_CieLuv_to_YCbCr(float l, float u, float v, float y, float cb, float cr)
{
// Arrange
CieLuv input = new(l, u, v);
YCbCr expected = new(y, cb, cr);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLuv[5];
@@ -42,14 +43,15 @@ public class CieLuvAndYCbCrConversionTests
}
[Theory]
- [InlineData(0, 128, 128, 0, 0, 0)]
- [InlineData(71.8283, 119.3174, 193.9839, 36.00565, 93.44593, 10.2234)]
+ [InlineData(1, .5F, .5F, 100, 0, 0)]
+ [InlineData(0, .5F, .5F, 0, 0, 0)]
+ [InlineData(.5F, .5F, .5F, 53.38897F, 0, 0)]
public void Convert_YCbCr_to_CieLuv(float y, float cb, float cr, float l, float u, float v)
{
// Arrange
YCbCr input = new(y, cb, cr);
CieLuv expected = new(l, u, v);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new YCbCr[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieLuvTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieLuvTests.cs
index db903a0bf..173491081 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieLuvTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieLuvTests.cs
@@ -9,6 +9,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
/// Tests the struct.
///
+[Trait("Color", "Conversion")]
public class CieLuvTests
{
[Fact]
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieXyChromaticityCoordinatesTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieXyChromaticityCoordinatesTests.cs
index a85a08a21..8bc71f1e1 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieXyChromaticityCoordinatesTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieXyChromaticityCoordinatesTests.cs
@@ -8,6 +8,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
/// Tests the struct.
///
+[Trait("Color", "Conversion")]
public class CieXyChromaticityCoordinatesTests
{
[Fact]
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieXyyAndYCbCrConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieXyyAndYCbCrConversionTests.cs
index 1fe359603..f9d571e03 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieXyyAndYCbCrConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieXyyAndYCbCrConversionTests.cs
@@ -13,8 +13,9 @@ public class CieXyyAndYCbCrConversionTests
private static readonly ApproximateColorProfileComparer Comparer = new(.0002f);
[Theory]
- [InlineData(0, 0, 0, 0, 128, 128)]
- [InlineData(0.360555, 0.936901, 0.1001514, 64.0204849, 91.87107, 82.33627)]
+ [InlineData(.34566915F, .358496159F, .99999994F, 1, .5F, .5F)]
+ [InlineData(0, 0, 0, 0, .5F, .5F)]
+ [InlineData(.34566915F, .358496159F, .214041144F, .5F, .5F, .5F)]
public void Convert_CieXyy_to_YCbCr(float x, float y, float yl, float y2, float cb, float cr)
{
// Arrange
@@ -41,8 +42,9 @@ public class CieXyyAndYCbCrConversionTests
}
[Theory]
- [InlineData(0, 128, 128, 0, 0, 0)]
- [InlineData(64.0204849, 91.87107, 82.33627, 0.32114, 0.59787, 0.10976)]
+ [InlineData(1, .5F, .5F, .34566915F, .358496159F, .99999994F)]
+ [InlineData(0, .5F, .5F, 0, 0, 0)]
+ [InlineData(.5F, .5F, .5F, .34566915F, .358496159F, .214041144F)]
public void Convert_YCbCr_to_CieXyy(float y2, float cb, float cr, float x, float y, float yl)
{
// Arrange
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieXyyTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieXyyTests.cs
index 245512f8a..80904c5df 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieXyyTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieXyyTests.cs
@@ -9,6 +9,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
/// Tests the struct.
///
+[Trait("Color", "Conversion")]
public class CieXyyTests
{
[Fact]
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndCieLabConversionTest.cs b/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndCieLabConversionTest.cs
index cb4d02889..76fceec41 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndCieLabConversionTest.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndCieLabConversionTest.cs
@@ -12,6 +12,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
/// Test data generated using:
///
///
+[Trait("Color", "Conversion")]
public class CieXyzAndCieLabConversionTest
{
private static readonly ApproximateColorProfileComparer Comparer = new(.0001f);
@@ -29,7 +30,7 @@ public class CieXyzAndCieLabConversionTest
{
// Arrange
CieLab input = new(l, a, b);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
CieXyz expected = new(x, y, z);
@@ -62,7 +63,7 @@ public class CieXyzAndCieLabConversionTest
{
// Arrange
CieXyz input = new(x, y, z);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
CieLab expected = new(l, a, b);
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndCieLuvConversionTest.cs b/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndCieLuvConversionTest.cs
index 944b99005..b269818ae 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndCieLuvConversionTest.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndCieLuvConversionTest.cs
@@ -29,7 +29,7 @@ public class CieXyzAndCieLuvConversionTest
CieXyz input = new(x, y, z);
CieLuv expected = new(l, u, v);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieXyz[5];
@@ -64,7 +64,7 @@ public class CieXyzAndCieLuvConversionTest
CieLuv input = new(l, u, v);
CieXyz expected = new(x, y, z);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetWhitePoint = KnownIlluminants.D65 };
ColorProfileConverter converter = new(options);
Span inputSpan = new CieLuv[5];
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndCieXyyConversionTest.cs b/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndCieXyyConversionTest.cs
index 7b1d0ac78..48bb6c1e1 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndCieXyyConversionTest.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndCieXyyConversionTest.cs
@@ -12,6 +12,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
/// Test data generated using:
///
///
+[Trait("Color", "Conversion")]
public class CieXyzAndCieXyyConversionTest
{
private static readonly ApproximateColorProfileComparer Comparer = new(.0001F);
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndLmsConversionTest.cs b/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndLmsConversionTest.cs
index 185fcd256..c7898904d 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndLmsConversionTest.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndLmsConversionTest.cs
@@ -11,6 +11,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
/// Test data generated using original colorful library.
///
+[Trait("Color", "Conversion")]
public class CieXyzAndLmsConversionTest
{
private static readonly ApproximateColorProfileComparer Comparer = new(.0001f);
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndYCbCrConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndYCbCrConversionTests.cs
index 475673da8..90175a058 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndYCbCrConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieXyzAndYCbCrConversionTests.cs
@@ -13,8 +13,8 @@ public class CieXyzAndYCbCrConversionTests
private static readonly ApproximateColorProfileComparer Comparer = new(.0002f);
[Theory]
- [InlineData(0, 0, 0, 0, 128, 128)]
- [InlineData(0.360555, 0.936901, 0.1001514, 149.685, 43.52769, 21.23457)]
+ [InlineData(0, 0, 0, 0, .5F, .5F)]
+ [InlineData(.206382737F, .214041144F, .176628917F, .5F, .5F, .5F)]
public void Convert_CieXyz_to_YCbCr(float x, float y, float z, float y2, float cb, float cr)
{
// Arrange
@@ -41,8 +41,8 @@ public class CieXyzAndYCbCrConversionTests
}
[Theory]
- [InlineData(0, 128, 128, 0, 0, 0)]
- [InlineData(149.685, 43.52769, 21.23457, 0.38506496, 0.716878653, 0.0971045)]
+ [InlineData(0, .5F, .5F, 0, 0, 0)]
+ [InlineData(.5F, .5F, .5F, .206382737F, .214041144F, .176628917F)]
public void Convert_YCbCr_to_CieXyz(float y2, float cb, float cr, float x, float y, float z)
{
// Arrange
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CieXyzTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CieXyzTests.cs
index 88138304a..683b3b661 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CieXyzTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CieXyzTests.cs
@@ -9,6 +9,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
/// Tests the struct.
///
+[Trait("Color", "Conversion")]
public class CieXyzTests
{
[Fact]
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CmykAndYCbCrConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CmykAndYCbCrConversionTests.cs
index 64b47e2b9..3a5fe7c15 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CmykAndYCbCrConversionTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CmykAndYCbCrConversionTests.cs
@@ -13,8 +13,9 @@ public class CmykAndYCbCrConversionTests
private static readonly ApproximateColorProfileComparer Comparer = new(.0002F);
[Theory]
- [InlineData(0, 0, 0, 0, 255, 128, 128)]
- [InlineData(0.360555, 0.1036901, 0.818514, 0.274615, 136.5134, 69.90555, 114.9948)]
+ [InlineData(0, 0, 0, 1, 0, .5F, .5F)]
+ [InlineData(0, 0, 0, 0, 1, .5F, .5F)]
+ [InlineData(0, .8570679F, .49999997F, 0, .439901F, .5339159F, .899500132F)]
public void Convert_Cmyk_To_YCbCr(float c, float m, float y, float k, float y2, float cb, float cr)
{
// Arrange
@@ -41,8 +42,9 @@ public class CmykAndYCbCrConversionTests
}
[Theory]
- [InlineData(255, 128, 128, 0, 0, 0, 5.960464E-08)]
- [InlineData(136.5134, 69.90555, 114.9948, 0.2891567, 0, 0.7951807, 0.3490196)]
+ [InlineData(0, .5F, .5F, 0, 0, 0, 1)]
+ [InlineData(1, .5F, .5F, 0, 0, 0, 0)]
+ [InlineData(.5F, .5F, 1F, 0, .8570679F, .49999997F, 0)]
public void Convert_YCbCr_To_Cmyk(float y2, float cb, float cr, float c, float m, float y, float k)
{
// Arrange
diff --git a/tests/ImageSharp.Tests/ColorProfiles/CmykTests.cs b/tests/ImageSharp.Tests/ColorProfiles/CmykTests.cs
index e2044a75d..22b7a7f70 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/CmykTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/CmykTests.cs
@@ -9,6 +9,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
/// Tests the struct.
///
+[Trait("Color", "Conversion")]
public class CmykTests
{
[Fact]
diff --git a/tests/ImageSharp.Tests/ColorProfiles/ColorProfileConverterChomaticAdaptationTests.cs b/tests/ImageSharp.Tests/ColorProfiles/ColorProfileConverterChomaticAdaptationTests.cs
index a90e5b9e8..525220d8e 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/ColorProfileConverterChomaticAdaptationTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/ColorProfileConverterChomaticAdaptationTests.cs
@@ -26,7 +26,7 @@ public class ColorProfileConverterChomaticAdaptationTests
Rgb expected = new(r2, g2, b2);
ColorConversionOptions options = new()
{
- RgbWorkingSpace = KnownRgbWorkingSpaces.WideGamutRgb,
+ SourceRgbWorkingSpace = KnownRgbWorkingSpaces.WideGamutRgb,
TargetRgbWorkingSpace = KnownRgbWorkingSpaces.SRgb
};
ColorProfileConverter converter = new(options);
@@ -49,7 +49,7 @@ public class ColorProfileConverterChomaticAdaptationTests
Rgb expected = new(r2, g2, b2);
ColorConversionOptions options = new()
{
- RgbWorkingSpace = KnownRgbWorkingSpaces.SRgb,
+ SourceRgbWorkingSpace = KnownRgbWorkingSpaces.SRgb,
TargetRgbWorkingSpace = KnownRgbWorkingSpaces.WideGamutRgb
};
ColorProfileConverter converter = new(options);
@@ -71,7 +71,7 @@ public class ColorProfileConverterChomaticAdaptationTests
CieLab expected = new(l2, a2, b2);
ColorConversionOptions options = new()
{
- WhitePoint = KnownIlluminants.D65,
+ SourceWhitePoint = KnownIlluminants.D65,
TargetWhitePoint = KnownIlluminants.D50
};
ColorProfileConverter converter = new(options);
@@ -93,7 +93,7 @@ public class ColorProfileConverterChomaticAdaptationTests
CieXyz expected = new(x2, y2, z2);
ColorConversionOptions options = new()
{
- WhitePoint = KnownIlluminants.D65,
+ SourceWhitePoint = KnownIlluminants.D65,
TargetWhitePoint = KnownIlluminants.D50,
AdaptationMatrix = KnownChromaticAdaptationMatrices.Bradford
};
@@ -117,7 +117,7 @@ public class ColorProfileConverterChomaticAdaptationTests
CieXyz expected = new(x2, y2, z2);
ColorConversionOptions options = new()
{
- WhitePoint = KnownIlluminants.D65,
+ SourceWhitePoint = KnownIlluminants.D65,
TargetWhitePoint = KnownIlluminants.D50,
AdaptationMatrix = KnownChromaticAdaptationMatrices.XyzScaling
};
@@ -141,7 +141,7 @@ public class ColorProfileConverterChomaticAdaptationTests
HunterLab expected = new(l2, a2, b2);
ColorConversionOptions options = new()
{
- WhitePoint = KnownIlluminants.D65,
+ SourceWhitePoint = KnownIlluminants.D65,
TargetWhitePoint = KnownIlluminants.D50,
};
@@ -164,7 +164,7 @@ public class ColorProfileConverterChomaticAdaptationTests
CieLchuv expected = new(l2, c2, h2);
ColorConversionOptions options = new()
{
- WhitePoint = KnownIlluminants.D65,
+ SourceWhitePoint = KnownIlluminants.D65,
TargetWhitePoint = KnownIlluminants.D50,
AdaptationMatrix = KnownChromaticAdaptationMatrices.XyzScaling
};
@@ -187,7 +187,7 @@ public class ColorProfileConverterChomaticAdaptationTests
CieLch expected = new(l2, c2, h2);
ColorConversionOptions options = new()
{
- WhitePoint = KnownIlluminants.D65,
+ SourceWhitePoint = KnownIlluminants.D65,
TargetWhitePoint = KnownIlluminants.D50,
AdaptationMatrix = KnownChromaticAdaptationMatrices.XyzScaling
};
diff --git a/tests/ImageSharp.Tests/ColorProfiles/HslTests.cs b/tests/ImageSharp.Tests/ColorProfiles/HslTests.cs
index d18e65117..6697cbfde 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/HslTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/HslTests.cs
@@ -9,6 +9,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
/// Tests the struct.
///
+[Trait("Color", "Conversion")]
public class HslTests
{
[Fact]
diff --git a/tests/ImageSharp.Tests/ColorProfiles/HsvTests.cs b/tests/ImageSharp.Tests/ColorProfiles/HsvTests.cs
index 46f58b18e..dd71fcd3f 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/HsvTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/HsvTests.cs
@@ -9,6 +9,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
/// Tests the struct.
///
+[Trait("Color", "Conversion")]
public class HsvTests
{
[Fact]
diff --git a/tests/ImageSharp.Tests/ColorProfiles/HunterLabTests.cs b/tests/ImageSharp.Tests/ColorProfiles/HunterLabTests.cs
index 5fbdd0788..af06b3c91 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/HunterLabTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/HunterLabTests.cs
@@ -9,6 +9,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
/// Tests the struct.
///
+[Trait("Color", "Conversion")]
public class HunterLabTests
{
[Fact]
diff --git a/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/ClutCalculatorTests.cs b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/ClutCalculatorTests.cs
new file mode 100644
index 000000000..249e7f4ed
--- /dev/null
+++ b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/ClutCalculatorTests.cs
@@ -0,0 +1,27 @@
+// Copyright (c) Six Labors.
+// Licensed under the Six Labors Split License.
+
+using System.Numerics;
+using SixLabors.ImageSharp.ColorProfiles.Icc.Calculators;
+using SixLabors.ImageSharp.Metadata.Profiles.Icc;
+using SixLabors.ImageSharp.Tests.TestDataIcc.Conversion;
+
+namespace SixLabors.ImageSharp.Tests.ColorProfiles.Icc.Calculators;
+
+///
+/// Tests ICC
+///
+[Trait("Color", "Conversion")]
+public class ClutCalculatorTests
+{
+ [Theory]
+ [MemberData(nameof(IccConversionDataClut.ClutConversionTestData), MemberType = typeof(IccConversionDataClut))]
+ internal void ClutCalculator_WithClut_ReturnsResult(IccClut lut, Vector4 input, Vector4 expected)
+ {
+ ClutCalculator calculator = new(lut);
+
+ Vector4 result = calculator.Calculate(input);
+
+ VectorAssert.Equal(expected, result, 4);
+ }
+}
diff --git a/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/CurveCalculatorTests.cs b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/CurveCalculatorTests.cs
new file mode 100644
index 000000000..8f48277d6
--- /dev/null
+++ b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/CurveCalculatorTests.cs
@@ -0,0 +1,26 @@
+// Copyright (c) Six Labors.
+// Licensed under the Six Labors Split License.
+
+using SixLabors.ImageSharp.ColorProfiles.Conversion.Icc;
+using SixLabors.ImageSharp.Metadata.Profiles.Icc;
+using SixLabors.ImageSharp.Tests.TestDataIcc.Conversion;
+
+namespace SixLabors.ImageSharp.Tests.ColorProfiles.Icc.Calculators;
+
+///
+/// Tests ICC
+///
+[Trait("Color", "Conversion")]
+public class CurveCalculatorTests
+{
+ [Theory]
+ [MemberData(nameof(IccConversionDataTrc.CurveConversionTestData), MemberType = typeof(IccConversionDataTrc))]
+ internal void CurveCalculator_WithCurveEntry_ReturnsResult(IccCurveTagDataEntry curve, bool inverted, float input, float expected)
+ {
+ CurveCalculator calculator = new(curve, inverted);
+
+ float result = calculator.Calculate(input);
+
+ Assert.Equal(expected, result, 4f);
+ }
+}
diff --git a/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/LutABCalculatorTests.cs b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/LutABCalculatorTests.cs
new file mode 100644
index 000000000..de2b4f5fa
--- /dev/null
+++ b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/LutABCalculatorTests.cs
@@ -0,0 +1,38 @@
+// Copyright (c) Six Labors.
+// Licensed under the Six Labors Split License.
+
+using System.Numerics;
+using SixLabors.ImageSharp.ColorProfiles.Conversion.Icc;
+using SixLabors.ImageSharp.Metadata.Profiles.Icc;
+using SixLabors.ImageSharp.Tests.TestDataIcc.Conversion;
+
+namespace SixLabors.ImageSharp.Tests.ColorProfiles.Icc.Calculators;
+
+///
+/// Tests ICC
+///
+[Trait("Color", "Conversion")]
+public class LutABCalculatorTests
+{
+ [Theory]
+ [MemberData(nameof(IccConversionDataLutAB.LutAToBConversionTestData), MemberType = typeof(IccConversionDataLutAB))]
+ internal void LutABCalculator_WithLutAToB_ReturnsResult(IccLutAToBTagDataEntry lut, Vector4 input, Vector4 expected)
+ {
+ LutABCalculator calculator = new(lut);
+
+ Vector4 result = calculator.Calculate(input);
+
+ VectorAssert.Equal(expected, result, 4);
+ }
+
+ [Theory]
+ [MemberData(nameof(IccConversionDataLutAB.LutBToAConversionTestData), MemberType = typeof(IccConversionDataLutAB))]
+ internal void LutABCalculator_WithLutBToA_ReturnsResult(IccLutBToATagDataEntry lut, Vector4 input, Vector4 expected)
+ {
+ LutABCalculator calculator = new(lut);
+
+ Vector4 result = calculator.Calculate(input);
+
+ VectorAssert.Equal(expected, result, 4);
+ }
+}
diff --git a/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/LutCalculatorTests.cs b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/LutCalculatorTests.cs
new file mode 100644
index 000000000..6cc77247a
--- /dev/null
+++ b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/LutCalculatorTests.cs
@@ -0,0 +1,25 @@
+// Copyright (c) Six Labors.
+// Licensed under the Six Labors Split License.
+
+using SixLabors.ImageSharp.ColorProfiles.Icc.Calculators;
+using SixLabors.ImageSharp.Tests.TestDataIcc.Conversion;
+
+namespace SixLabors.ImageSharp.Tests.ColorProfiles.Icc.Calculators;
+
+///
+/// Tests ICC
+///
+[Trait("Color", "Conversion")]
+public class LutCalculatorTests
+{
+ [Theory]
+ [MemberData(nameof(IccConversionDataLut.LutConversionTestData), MemberType = typeof(IccConversionDataLut))]
+ internal void LutCalculator_WithLut_ReturnsResult(float[] lut, bool inverted, float input, float expected)
+ {
+ LutCalculator calculator = new(lut, inverted);
+
+ float result = calculator.Calculate(input);
+
+ Assert.Equal(expected, result, 4f);
+ }
+}
diff --git a/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/LutEntryCalculatorTests.cs b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/LutEntryCalculatorTests.cs
new file mode 100644
index 000000000..14f1386eb
--- /dev/null
+++ b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/LutEntryCalculatorTests.cs
@@ -0,0 +1,38 @@
+// Copyright (c) Six Labors.
+// Licensed under the Six Labors Split License.
+
+using System.Numerics;
+using SixLabors.ImageSharp.ColorProfiles.Icc.Calculators;
+using SixLabors.ImageSharp.Metadata.Profiles.Icc;
+using SixLabors.ImageSharp.Tests.TestDataIcc.Conversion;
+
+namespace SixLabors.ImageSharp.Tests.ColorProfiles.Icc.Calculators;
+
+///
+/// Tests ICC
+///
+[Trait("Color", "Conversion")]
+public class LutEntryCalculatorTests
+{
+ [Theory]
+ [MemberData(nameof(IccConversionDataLutEntry.Lut8ConversionTestData), MemberType = typeof(IccConversionDataLutEntry))]
+ internal void LutEntryCalculator_WithLut8_ReturnsResult(IccLut8TagDataEntry lut, Vector4 input, Vector4 expected)
+ {
+ LutEntryCalculator calculator = new(lut);
+
+ Vector4 result = calculator.Calculate(input);
+
+ VectorAssert.Equal(expected, result, 4);
+ }
+
+ [Theory]
+ [MemberData(nameof(IccConversionDataLutEntry.Lut16ConversionTestData), MemberType = typeof(IccConversionDataLutEntry))]
+ internal void LutEntryCalculator_WithLut16_ReturnsResult(IccLut16TagDataEntry lut, Vector4 input, Vector4 expected)
+ {
+ LutEntryCalculator calculator = new(lut);
+
+ Vector4 result = calculator.Calculate(input);
+
+ VectorAssert.Equal(expected, result, 4);
+ }
+}
diff --git a/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/MatrixCalculatorTests.cs b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/MatrixCalculatorTests.cs
new file mode 100644
index 000000000..f56bf5873
--- /dev/null
+++ b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/MatrixCalculatorTests.cs
@@ -0,0 +1,26 @@
+// Copyright (c) Six Labors.
+// Licensed under the Six Labors Split License.
+
+using System.Numerics;
+using SixLabors.ImageSharp.ColorProfiles.Icc.Calculators;
+using SixLabors.ImageSharp.Tests.TestDataIcc.Conversion;
+
+namespace SixLabors.ImageSharp.Tests.ColorProfiles.Icc.Calculators;
+
+///
+/// Tests ICC
+///
+[Trait("Color", "Conversion")]
+public class MatrixCalculatorTests
+{
+ [Theory]
+ [MemberData(nameof(IccConversionDataMatrix.MatrixConversionTestData), MemberType = typeof(IccConversionDataMatrix))]
+ internal void MatrixCalculator_WithMatrix_ReturnsResult(Matrix4x4 matrix2D, Vector3 matrix1D, Vector4 input, Vector4 expected)
+ {
+ MatrixCalculator calculator = new(matrix2D, matrix1D);
+
+ Vector4 result = calculator.Calculate(input);
+
+ VectorAssert.Equal(expected, result, 4);
+ }
+}
diff --git a/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/ParametricCurveCalculatorTests.cs b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/ParametricCurveCalculatorTests.cs
new file mode 100644
index 000000000..aac3f42c9
--- /dev/null
+++ b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/ParametricCurveCalculatorTests.cs
@@ -0,0 +1,26 @@
+// Copyright (c) Six Labors.
+// Licensed under the Six Labors Split License.
+
+using SixLabors.ImageSharp.ColorProfiles.Icc.Calculators;
+using SixLabors.ImageSharp.Metadata.Profiles.Icc;
+using SixLabors.ImageSharp.Tests.TestDataIcc.Conversion;
+
+namespace SixLabors.ImageSharp.Tests.ColorProfiles.Icc.Calculators;
+
+///
+/// Tests ICC
+///
+[Trait("Color", "Conversion")]
+public class ParametricCurveCalculatorTests
+{
+ [Theory]
+ [MemberData(nameof(IccConversionDataTrc.ParametricCurveConversionTestData), MemberType = typeof(IccConversionDataTrc))]
+ internal void ParametricCurveCalculator_WithCurveEntry_ReturnsResult(IccParametricCurveTagDataEntry curve, bool inverted, float input, float expected)
+ {
+ ParametricCurveCalculator calculator = new(curve, inverted);
+
+ float result = calculator.Calculate(input);
+
+ Assert.Equal(expected, result, 4f);
+ }
+}
diff --git a/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/TrcCalculatorTests.cs b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/TrcCalculatorTests.cs
new file mode 100644
index 000000000..65f02c3fb
--- /dev/null
+++ b/tests/ImageSharp.Tests/ColorProfiles/Icc/Calculators/TrcCalculatorTests.cs
@@ -0,0 +1,27 @@
+// Copyright (c) Six Labors.
+// Licensed under the Six Labors Split License.
+
+using System.Numerics;
+using SixLabors.ImageSharp.ColorProfiles.Icc.Calculators;
+using SixLabors.ImageSharp.Metadata.Profiles.Icc;
+using SixLabors.ImageSharp.Tests.TestDataIcc.Conversion;
+
+namespace SixLabors.ImageSharp.Tests.ColorProfiles.Icc.Calculators;
+
+///
+/// Tests ICC
+///
+[Trait("Color", "Conversion")]
+public class TrcCalculatorTests
+{
+ [Theory]
+ [MemberData(nameof(IccConversionDataTrc.TrcArrayConversionTestData), MemberType = typeof(IccConversionDataTrc))]
+ internal void TrcCalculator_WithCurvesArray_ReturnsResult(IccTagDataEntry[] entries, bool inverted, Vector4 input, Vector4 expected)
+ {
+ TrcCalculator calculator = new(entries, inverted);
+
+ Vector4 result = calculator.Calculate(input);
+
+ VectorAssert.Equal(expected, result, 4);
+ }
+}
diff --git a/tests/ImageSharp.Tests/ColorProfiles/Icc/ColorProfileConverterTests.Icc.cs b/tests/ImageSharp.Tests/ColorProfiles/Icc/ColorProfileConverterTests.Icc.cs
new file mode 100644
index 000000000..cb349af96
--- /dev/null
+++ b/tests/ImageSharp.Tests/ColorProfiles/Icc/ColorProfileConverterTests.Icc.cs
@@ -0,0 +1,263 @@
+// Copyright (c) Six Labors.
+// Licensed under the Six Labors Split License.
+
+using System.Numerics;
+using SixLabors.ImageSharp.ColorProfiles;
+using SixLabors.ImageSharp.Metadata.Profiles.Icc;
+using Wacton.Unicolour;
+using Wacton.Unicolour.Icc;
+using Xunit.Abstractions;
+using Rgb = SixLabors.ImageSharp.ColorProfiles.Rgb;
+
+namespace SixLabors.ImageSharp.Tests.ColorProfiles.Icc;
+
+public class ColorProfileConverterTests(ITestOutputHelper testOutputHelper)
+{
+ // for 3-channel spaces, 4th item is ignored
+ private static readonly List Inputs =
+ [
+ [0, 0, 0, 0],
+ [1, 0, 0, 0],
+ [0, 1, 0, 0],
+ [0, 0, 1, 0],
+ [0, 0, 0, 1],
+ [1, 1, 1, 1],
+ [0.5f, 0.5f, 0.5f, 0.5f],
+ [0.199678659f, 0.67982769f, 0.805381715f, 0.982666492f], // requires clipping before source is PCS adjusted for Fogra39 -> sRGBv2
+ [0.776568174f, 0.961630166f, 0.31032759f, 0.895294666f], // requires clipping after target is PCS adjusted for Fogra39 -> sRGBv2
+ [GetNormalizedRandomValue(), GetNormalizedRandomValue(), GetNormalizedRandomValue(), GetNormalizedRandomValue()]
+ ];
+
+ [Theory]
+ [InlineData(TestIccProfiles.Fogra39, TestIccProfiles.Fogra39)] // CMYK -> LAB -> CMYK (commonly used v2 profiles)
+ [InlineData(TestIccProfiles.Fogra39, TestIccProfiles.Swop2006)] // CMYK -> LAB -> CMYK (commonly used v2 profiles)
+ [InlineData(TestIccProfiles.Swop2006, TestIccProfiles.Fogra39)] // CMYK -> LAB -> CMYK (commonly used v2 profiles)
+ [InlineData(TestIccProfiles.Swop2006, TestIccProfiles.Swop2006)] // CMYK -> LAB -> CMYK (commonly used v2 profiles)
+ [InlineData(TestIccProfiles.Fogra39, TestIccProfiles.JapanColor2003)] // CMYK -> LAB -> CMYK (different bit depth v2 LUTs, 8-bit vs 16-bit)
+ [InlineData(TestIccProfiles.JapanColor2011, TestIccProfiles.Fogra39)] // CMYK -> LAB -> CMYK (different LUT versions, v2 vs v4)
+ [InlineData(TestIccProfiles.Fogra39, TestIccProfiles.Cgats21)] // CMYK -> LAB -> RGB (different LUT versions, v2 vs v4)
+ [InlineData(TestIccProfiles.Fogra39, TestIccProfiles.StandardRgbV4)] // RGB -> LAB -> CMYK (different LUT versions, v4 vs v2)
+ [InlineData(TestIccProfiles.StandardRgbV4, TestIccProfiles.Fogra39)] // RGB -> LAB -> XYZ -> RGB (different LUT elements, B-Matrix-M-CLUT-A vs B-Matrix-M)
+ [InlineData(TestIccProfiles.StandardRgbV4, TestIccProfiles.RommRgb)] // RGB -> XYZ -> LAB -> RGB (different LUT elements, B-Matrix-M vs B-Matrix-M-CLUT-A)
+ [InlineData(TestIccProfiles.RommRgb, TestIccProfiles.StandardRgbV4)] // CMYK -> LAB -> CMYK (different bit depth v2 LUTs, 16-bit vs 8-bit)
+ [InlineData(TestIccProfiles.Fogra39, TestIccProfiles.StandardRgbV2, 0.0005)] // CMYK -> LAB -> XYZ -> RGB (different LUT tags, A2B vs TRC) --- tolerance slightly higher due to difference in inverse curve implementation
+ [InlineData(TestIccProfiles.StandardRgbV2, TestIccProfiles.Fogra39)] // RGB -> XYZ -> LAB -> CMYK (different LUT tags, TRC vs A2B)
+ public void CanConvertIccProfiles(string sourceProfile, string targetProfile, double tolerance = 0.000005)
+ {
+ List actual = Inputs.ConvertAll(input => GetActualTargetValues(input, sourceProfile, targetProfile));
+ AssertConversion(sourceProfile, targetProfile, actual, tolerance, testOutputHelper);
+ }
+
+ [Theory]
+ [InlineData(TestIccProfiles.Fogra39, TestIccProfiles.Fogra39)] // CMYK -> LAB -> CMYK (commonly used v2 profiles)
+ [InlineData(TestIccProfiles.Fogra39, TestIccProfiles.Swop2006)] // CMYK -> LAB -> CMYK (commonly used v2 profiles)
+ [InlineData(TestIccProfiles.Swop2006, TestIccProfiles.Fogra39)] // CMYK -> LAB -> CMYK (commonly used v2 profiles)
+ [InlineData(TestIccProfiles.Swop2006, TestIccProfiles.Swop2006)] // CMYK -> LAB -> CMYK (commonly used v2 profiles)
+ [InlineData(TestIccProfiles.Fogra39, TestIccProfiles.JapanColor2003)] // CMYK -> LAB -> CMYK (different bit depth v2 LUTs, 8-bit vs 16-bit)
+ [InlineData(TestIccProfiles.JapanColor2011, TestIccProfiles.Fogra39)] // CMYK -> LAB -> CMYK (different LUT versions, v2 vs v4)
+ [InlineData(TestIccProfiles.Fogra39, TestIccProfiles.Cgats21)] // CMYK -> LAB -> RGB (different LUT versions, v2 vs v4)
+ [InlineData(TestIccProfiles.Fogra39, TestIccProfiles.StandardRgbV4)] // RGB -> LAB -> CMYK (different LUT versions, v4 vs v2)
+ [InlineData(TestIccProfiles.StandardRgbV4, TestIccProfiles.Fogra39)] // RGB -> LAB -> XYZ -> RGB (different LUT elements, B-Matrix-M-CLUT-A vs B-Matrix-M)
+ [InlineData(TestIccProfiles.StandardRgbV4, TestIccProfiles.RommRgb)] // RGB -> XYZ -> LAB -> RGB (different LUT elements, B-Matrix-M vs B-Matrix-M-CLUT-A)
+ [InlineData(TestIccProfiles.RommRgb, TestIccProfiles.StandardRgbV4)] // CMYK -> LAB -> CMYK (different bit depth v2 LUTs, 16-bit vs 8-bit)
+ [InlineData(TestIccProfiles.Fogra39, TestIccProfiles.StandardRgbV2, 0.0005)] // CMYK -> LAB -> XYZ -> RGB (different LUT tags, A2B vs TRC) --- tolerance slightly higher due to difference in inverse curve implementation
+ [InlineData(TestIccProfiles.StandardRgbV2, TestIccProfiles.Fogra39)] // RGB -> XYZ -> LAB -> CMYK (different LUT tags, TRC vs A2B)
+ [InlineData(TestIccProfiles.Issue129, TestIccProfiles.StandardRgbV4)] // CMYK -> LAB -> -> XYZ -> RGB
+ public void CanBulkConvertIccProfiles(string sourceProfile, string targetProfile, double tolerance = 0.000005)
+ {
+ List actual = GetBulkActualTargetValues(Inputs, sourceProfile, targetProfile);
+ AssertConversion(sourceProfile, targetProfile, actual, tolerance, testOutputHelper);
+ }
+
+ private static void AssertConversion(string sourceProfile, string targetProfile, List actual, double tolerance, ITestOutputHelper testOutputHelper)
+ {
+ List expected = Inputs.ConvertAll(input => GetExpectedTargetValues(sourceProfile, targetProfile, input, testOutputHelper));
+ Assert.Equal(expected.Count, actual.Count);
+
+ for (int i = 0; i < expected.Count; i++)
+ {
+ Log(testOutputHelper, Inputs[i], expected[i], actual[i]);
+ for (int j = 0; j < expected[i].Length; j++)
+ {
+ Assert.Equal(expected[i][j], actual[i][j], tolerance);
+ }
+ }
+ }
+
+ private static double[] GetExpectedTargetValues(string sourceProfile, string targetProfile, float[] input, ITestOutputHelper testOutputHelper)
+ {
+ Wacton.Unicolour.Configuration sourceConfig = TestIccProfiles.GetUnicolourConfiguration(sourceProfile);
+ Wacton.Unicolour.Configuration targetConfig = TestIccProfiles.GetUnicolourConfiguration(targetProfile);
+
+ if (sourceConfig.Icc.Error != null || targetConfig.Icc.Error != null)
+ {
+ Assert.Fail("Unicolour does not support the ICC profile - test values will need to be calculated manually");
+ }
+
+ /* This is a hack to trick Unicolour to work in the same way as ImageSharp.
+ * ImageSharp bypasses PCS adjustment for v2 perceptual intent if source and target both need it
+ * as they both share the same understanding of what the PCS is (see ColorProfileConverterExtensionsIcc.GetTargetPcsWithPerceptualAdjustment)
+ * Unicolour does not support a direct profile-to-profile conversion so will always perform PCS adjustment for v2 perceptual intent.
+ * However, PCS adjustment clips negative XYZ values, causing those particular values in Unicolour and ImageSharp to diverge.
+ * It's unclear to me if there's a fundamental correct answer here.
+ *
+ * There are two obvious ways to keep Unicolour and ImageSharp values aligned:
+ * 1. Make ImageSharp always perform PCS adjustment, clipping negative XYZ values during the process - but creates a lot more calculations
+ * 2. Make Unicolour stop performing PCS adjustment, allowing negative XYZ values during conversion
+ *
+ * Option 2 is implemented by modifying the profiles so they claim to be v4 profiles
+ * since v4 perceptual profiles do not apply PCS adjustment.
+ */
+ bool isSourcePerceptualV2 = sourceConfig.Icc.Intent == Intent.Perceptual && sourceConfig.Icc.Profile!.Header.ProfileVersion.Major == 2;
+ bool isTargetPerceptualV2 = targetConfig.Icc.Intent == Intent.Perceptual && targetConfig.Icc.Profile!.Header.ProfileVersion.Major == 2;
+ if (isSourcePerceptualV2 && isTargetPerceptualV2)
+ {
+ sourceConfig = GetUnicolourConfigAsV4Header(sourceConfig);
+ targetConfig = GetUnicolourConfigAsV4Header(targetConfig);
+ }
+
+ Channels channels = new([.. input.Select(value => (double)value)]);
+ Unicolour source = new(sourceConfig, channels);
+ Unicolour target = source.ConvertToConfiguration(targetConfig);
+ if (target.Icc.Error != null)
+ {
+ testOutputHelper.WriteLine($"Error during Unicolour ICC conversion of supported profile: {target.Icc.Error}");
+ }
+
+ return target.Icc.Values;
+ }
+
+ private static Wacton.Unicolour.Configuration GetUnicolourConfigAsV4Header(Wacton.Unicolour.Configuration config)
+ {
+ string profilePath = config.Icc.Profile!.FileInfo.FullName;
+ string modifiedFilename = $"{Path.GetFileNameWithoutExtension(profilePath)}_modified.icc";
+ string modifiedProfile = Path.Combine(Path.GetDirectoryName(profilePath)!, modifiedFilename);
+
+ Wacton.Unicolour.Configuration modifiedConfig;
+ if (!TestIccProfiles.HasUnicolourConfiguration(modifiedProfile))
+ {
+ byte[] bytes = File.ReadAllBytes(profilePath);
+ bytes[8] = 4; // byte 8 of profile is major version
+ File.WriteAllBytes(modifiedProfile, bytes);
+ modifiedConfig = TestIccProfiles.GetUnicolourConfiguration(modifiedProfile);
+ File.Delete(modifiedProfile);
+ }
+ else
+ {
+ modifiedConfig = TestIccProfiles.GetUnicolourConfiguration(modifiedProfile);
+ }
+
+ return modifiedConfig;
+ }
+
+ private static Vector4 GetActualTargetValues(float[] input, string sourceProfile, string targetProfile)
+ {
+ ColorProfileConverter converter = new(new ColorConversionOptions
+ {
+ SourceIccProfile = TestIccProfiles.GetProfile(sourceProfile),
+ TargetIccProfile = TestIccProfiles.GetProfile(targetProfile)
+ });
+
+ IccColorSpaceType sourceDataSpace = converter.Options.SourceIccProfile!.Header.DataColorSpace;
+ IccColorSpaceType targetDataSpace = converter.Options.TargetIccProfile!.Header.DataColorSpace;
+ return sourceDataSpace switch
+ {
+ IccColorSpaceType.Cmyk when targetDataSpace == IccColorSpaceType.Cmyk
+ => converter.Convert(new Cmyk(new Vector4(input))).ToScaledVector4(),
+ IccColorSpaceType.Cmyk when targetDataSpace == IccColorSpaceType.Rgb
+ => converter.Convert(new Cmyk(new Vector4(input))).ToScaledVector4(),
+ IccColorSpaceType.Rgb when targetDataSpace == IccColorSpaceType.Cmyk
+ => converter.Convert(new Rgb(new Vector3(input))).ToScaledVector4(),
+ IccColorSpaceType.Rgb when targetDataSpace == IccColorSpaceType.Rgb
+ => converter.Convert(new Rgb(new Vector3(input))).ToScaledVector4(),
+ _ => throw new NotSupportedException($"Unsupported ICC profile data color space conversion: {sourceDataSpace} -> {targetDataSpace}")
+ };
+ }
+
+ private static List GetBulkActualTargetValues(List inputs, string sourceProfile, string targetProfile)
+ {
+ ColorProfileConverter converter = new(new ColorConversionOptions
+ {
+ SourceIccProfile = TestIccProfiles.GetProfile(sourceProfile),
+ TargetIccProfile = TestIccProfiles.GetProfile(targetProfile)
+ });
+
+ IccColorSpaceType sourceDataSpace = converter.Options.SourceIccProfile!.Header.DataColorSpace;
+ IccColorSpaceType targetDataSpace = converter.Options.TargetIccProfile!.Header.DataColorSpace;
+
+ switch (sourceDataSpace)
+ {
+ case IccColorSpaceType.Cmyk:
+ {
+ Span inputSpan = inputs.Select(x => new Cmyk(new Vector4(x))).ToArray();
+
+ switch (targetDataSpace)
+ {
+ case IccColorSpaceType.Cmyk:
+ {
+ Span outputSpan = stackalloc Cmyk[inputs.Count];
+ converter.Convert(inputSpan, outputSpan);
+ return [.. outputSpan.ToArray().Select(x => x.ToScaledVector4())];
+ }
+
+ case IccColorSpaceType.Rgb:
+ {
+ Span outputSpan = stackalloc Rgb[inputs.Count];
+ converter.Convert(inputSpan, outputSpan);
+ return [.. outputSpan.ToArray().Select(x => x.ToScaledVector4())];
+ }
+
+ default:
+ throw new NotSupportedException($"Unsupported ICC profile data color space conversion: {sourceDataSpace} -> {targetDataSpace}");
+ }
+ }
+
+ case IccColorSpaceType.Rgb:
+ {
+ Span inputSpan = inputs.Select(x => new Rgb(new Vector3(x))).ToArray();
+
+ switch (targetDataSpace)
+ {
+ case IccColorSpaceType.Cmyk:
+ {
+ Span outputSpan = stackalloc Cmyk[inputs.Count];
+ converter.Convert(inputSpan, outputSpan);
+ return [.. outputSpan.ToArray().Select(x => x.ToScaledVector4())];
+ }
+
+ case IccColorSpaceType.Rgb:
+ {
+ Span outputSpan = stackalloc Rgb[inputs.Count];
+ converter.Convert(inputSpan, outputSpan);
+ return [.. outputSpan.ToArray().Select(x => x.ToScaledVector4())];
+ }
+
+ default:
+ throw new NotSupportedException($"Unsupported ICC profile data color space conversion: {sourceDataSpace} -> {targetDataSpace}");
+ }
+ }
+
+ default:
+ throw new NotSupportedException($"Unsupported ICC profile data color space conversion: {sourceDataSpace} -> {targetDataSpace}");
+ }
+ }
+
+ private static float GetNormalizedRandomValue()
+ {
+ // Generate a random value between 0 (inclusive) and 1 (exclusive).
+ double value = Random.Shared.NextDouble();
+
+ // If the random value is exactly 0, return 0F to ensure inclusivity at the lower bound.
+ // For non-zero values, add a small increment (0.0000001F) to ensure the range
+ // is inclusive at the upper bound while retaining precision.
+ // Clamp the result between 0 and 1 to ensure it does not exceed the bounds.
+ return value == 0 ? 0F : Math.Clamp((float)value + 0.0000001F, 0, 1);
+ }
+
+ private static void Log(ITestOutputHelper testOutputHelper, float[] input, double[] expected, Vector4 actual)
+ {
+ string inputText = string.Join(", ", input);
+ string expectedText = string.Join(", ", expected.Select(x => $"{x:f8}"));
+ testOutputHelper.WriteLine($"Input {inputText} · Expected output {expectedText} · Actual output {actual}");
+ }
+}
diff --git a/tests/ImageSharp.Tests/ColorProfiles/Icc/TestIccProfiles.cs b/tests/ImageSharp.Tests/ColorProfiles/Icc/TestIccProfiles.cs
new file mode 100644
index 000000000..eec27fcd7
--- /dev/null
+++ b/tests/ImageSharp.Tests/ColorProfiles/Icc/TestIccProfiles.cs
@@ -0,0 +1,74 @@
+// Copyright (c) Six Labors.
+// Licensed under the Six Labors Split License.
+
+using System.Collections.Concurrent;
+using SixLabors.ImageSharp.Metadata.Profiles.Icc;
+using Wacton.Unicolour;
+using Wacton.Unicolour.Icc;
+
+namespace SixLabors.ImageSharp.Tests.ColorProfiles.Icc;
+
+internal static class TestIccProfiles
+{
+ private static readonly ConcurrentDictionary ProfileCache = new();
+ private static readonly ConcurrentDictionary UnicolourConfigurationCache = new();
+
+ ///
+ /// v2 CMYK -> LAB, output, lut16
+ ///
+ public const string Fogra39 = "Coated_Fogra39L_VIGC_300.icc";
+
+ ///
+ /// v2 CMYK -> LAB, output, lut16
+ ///
+ public const string Swop2006 = "SWOP2006_Coated5v2.icc";
+
+ ///
+ /// v2 CMYK -> LAB, output, lut8 (A2B tags)
+ ///
+ public const string JapanColor2011 = "JapanColor2011Coated.icc";
+
+ ///
+ /// v2 CMYK -> LAB, output, lut8 (B2A tags)
+ ///
+ public const string JapanColor2003 = "JapanColor2003WebCoated.icc";
+
+ ///
+ /// v4 CMYK -> LAB, output, lutAToB: B-CLUT-A
+ ///
+ public const string Cgats21 = "CGATS21_CRPC7.icc";
+
+ ///
+ /// v4 RGB -> XYZ, colorspace, lutAToB: B-Matrix-M [only intent 0]
+ ///
+ public const string RommRgb = "ISO22028-2_ROMM-RGB.icc";
+
+ ///
+ /// v4 RGB -> LAB, colorspace, lutAToB: B-Matrix-M-CLUT-A [only intent 0 & 1]
+ ///
+ public const string StandardRgbV4 = "sRGB_v4_ICC_preference.icc";
+
+ ///
+ /// v2 CMYK -> LAB, output
+ ///
+ public const string Issue129 = "issue-129.icc";
+
+ ///
+ /// v2 RGB -> XYZ, display, TRCs
+ ///
+ public const string StandardRgbV2 = "sRGB2014.icc";
+
+ public static IccProfile GetProfile(string file)
+ => ProfileCache.GetOrAdd(file, f => new IccProfile(File.ReadAllBytes(GetFullPath(f))));
+
+ public static Wacton.Unicolour.Configuration GetUnicolourConfiguration(string file)
+ => UnicolourConfigurationCache.GetOrAdd(
+ file,
+ f => new Wacton.Unicolour.Configuration(iccConfig: new IccConfiguration(GetFullPath(f), Intent.Unspecified, f)));
+
+ public static bool HasUnicolourConfiguration(string file)
+ => UnicolourConfigurationCache.ContainsKey(file);
+
+ private static string GetFullPath(string file)
+ => Path.GetFullPath(Path.Combine(".", "TestDataIcc", "Profiles", file));
+}
diff --git a/tests/ImageSharp.Tests/ColorProfiles/LmsTests.cs b/tests/ImageSharp.Tests/ColorProfiles/LmsTests.cs
index 138fd544d..395b547fd 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/LmsTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/LmsTests.cs
@@ -9,6 +9,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
/// Tests the struct.
///
+[Trait("Color", "Conversion")]
public class LmsTests
{
[Fact]
diff --git a/tests/ImageSharp.Tests/ColorProfiles/RbgAndYConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/RbgAndYConversionTests.cs
new file mode 100644
index 000000000..017ba78d0
--- /dev/null
+++ b/tests/ImageSharp.Tests/ColorProfiles/RbgAndYConversionTests.cs
@@ -0,0 +1,84 @@
+// Copyright (c) Six Labors.
+// Licensed under the Six Labors Split License.
+
+using SixLabors.ImageSharp.ColorProfiles;
+
+namespace SixLabors.ImageSharp.Tests.ColorProfiles;
+
+///
+/// Tests - conversions.
+///
+///
+/// Test data generated mathematically
+///
+public class RbgAndYConversionTests
+{
+ private static readonly ApproximateColorProfileComparer Comparer = new(.001F);
+
+ [Theory]
+ [InlineData(0F, 0F, 0F, 0F)]
+ [InlineData(0.5F, 0.5F, 0.5F, 0.5F)]
+ [InlineData(1F, 1F, 1F, 1F)]
+ public void Convert_Rgb_To_Y_BT601(float r, float g, float b, float y)
+ {
+ ColorConversionOptions options = new()
+ {
+ YCbCrTransform = KnownYCbCrMatrices.BT601
+ };
+
+ Convert_Rgb_To_Y_Core(r, g, b, y, options);
+ }
+
+ [Theory]
+ [InlineData(0F, 0F, 0F, 0F)]
+ [InlineData(0.5F, 0.5F, 0.5F, 0.5F)]
+ [InlineData(1F, 1F, 1F, 1F)]
+ public void Convert_Rgb_To_Y_BT709(float r, float g, float b, float y)
+ {
+ ColorConversionOptions options = new()
+ {
+ YCbCrTransform = KnownYCbCrMatrices.BT709
+ };
+
+ Convert_Rgb_To_Y_Core(r, g, b, y, options);
+ }
+
+ [Theory]
+ [InlineData(0F, 0F, 0F, 0F)]
+ [InlineData(0.5F, 0.5F, 0.5F, 0.49999997F)]
+ [InlineData(1F, 1F, 1F, 0.99999994F)]
+ public void Convert_Rgb_To_Y_BT2020(float r, float g, float b, float y)
+ {
+ ColorConversionOptions options = new()
+ {
+ YCbCrTransform = KnownYCbCrMatrices.BT2020
+ };
+
+ Convert_Rgb_To_Y_Core(r, g, b, y, options);
+ }
+
+ private static void Convert_Rgb_To_Y_Core(float r, float g, float b, float y, ColorConversionOptions options)
+ {
+ // Arrange
+ Rgb input = new(r, g, b);
+ Y expected = new(y);
+ ColorProfileConverter converter = new(options);
+
+ Span inputSpan = new Rgb[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new Y[5];
+
+ // Act
+ Y actual = converter.Convert(input);
+ converter.Convert(inputSpan, actualSpan);
+
+ // Assert
+ Assert.Equal(expected, actual, Comparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], Comparer);
+ }
+ }
+}
diff --git a/tests/ImageSharp.Tests/ColorProfiles/RgbAndCieXyzConversionTest.cs b/tests/ImageSharp.Tests/ColorProfiles/RgbAndCieXyzConversionTest.cs
index c10aa2c3c..7b48089c7 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/RgbAndCieXyzConversionTest.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/RgbAndCieXyzConversionTest.cs
@@ -27,7 +27,7 @@ public class RgbAndCieXyzConversionTest
{
// Arrange
CieXyz input = new(x, y, z);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D50, TargetRgbWorkingSpace = KnownRgbWorkingSpaces.SRgb };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D50, TargetRgbWorkingSpace = KnownRgbWorkingSpaces.SRgb };
ColorProfileConverter converter = new(options);
Rgb expected = new(r, g, b);
@@ -60,7 +60,7 @@ public class RgbAndCieXyzConversionTest
{
// Arrange
CieXyz input = new(x, y, z);
- ColorConversionOptions options = new() { WhitePoint = KnownIlluminants.D65, TargetRgbWorkingSpace = KnownRgbWorkingSpaces.SRgb };
+ ColorConversionOptions options = new() { SourceWhitePoint = KnownIlluminants.D65, TargetRgbWorkingSpace = KnownRgbWorkingSpaces.SRgb };
ColorProfileConverter converter = new(options);
Rgb expected = new(r, g, b);
@@ -93,7 +93,7 @@ public class RgbAndCieXyzConversionTest
{
// Arrange
Rgb input = new(r, g, b);
- ColorConversionOptions options = new() { TargetWhitePoint = KnownIlluminants.D50, RgbWorkingSpace = KnownRgbWorkingSpaces.SRgb };
+ ColorConversionOptions options = new() { TargetWhitePoint = KnownIlluminants.D50, SourceRgbWorkingSpace = KnownRgbWorkingSpaces.SRgb };
ColorProfileConverter converter = new(options);
CieXyz expected = new(x, y, z);
@@ -126,7 +126,7 @@ public class RgbAndCieXyzConversionTest
{
// Arrange
Rgb input = new(r, g, b);
- ColorConversionOptions options = new() { TargetWhitePoint = KnownIlluminants.D65, RgbWorkingSpace = KnownRgbWorkingSpaces.SRgb };
+ ColorConversionOptions options = new() { TargetWhitePoint = KnownIlluminants.D65, SourceRgbWorkingSpace = KnownRgbWorkingSpaces.SRgb };
ColorProfileConverter converter = new(options);
CieXyz expected = new(x, y, z);
diff --git a/tests/ImageSharp.Tests/ColorProfiles/RgbAndCmykConversionTest.cs b/tests/ImageSharp.Tests/ColorProfiles/RgbAndCmykConversionTest.cs
index 4f4ecb70b..bd35fb775 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/RgbAndCmykConversionTest.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/RgbAndCmykConversionTest.cs
@@ -13,6 +13,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
///
///
+[Trait("Color", "Conversion")]
public class RgbAndCmykConversionTest
{
private static readonly ApproximateColorProfileComparer Comparer = new(.0001F);
diff --git a/tests/ImageSharp.Tests/ColorProfiles/RgbAndHslConversionTest.cs b/tests/ImageSharp.Tests/ColorProfiles/RgbAndHslConversionTest.cs
index 0dc95628b..e5874c3d1 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/RgbAndHslConversionTest.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/RgbAndHslConversionTest.cs
@@ -13,6 +13,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
///
///
+[Trait("Color", "Conversion")]
public class RgbAndHslConversionTest
{
private static readonly ApproximateColorProfileComparer Comparer = new(.0001f);
diff --git a/tests/ImageSharp.Tests/ColorProfiles/RgbAndHsvConversionTest.cs b/tests/ImageSharp.Tests/ColorProfiles/RgbAndHsvConversionTest.cs
index b89b576b6..4a685abe5 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/RgbAndHsvConversionTest.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/RgbAndHsvConversionTest.cs
@@ -12,6 +12,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
/// Test data generated using:
///
///
+[Trait("Color", "Conversion")]
public class RgbAndHsvConversionTest
{
private static readonly ApproximateColorProfileComparer Comparer = new(.0001f);
diff --git a/tests/ImageSharp.Tests/ColorProfiles/RgbAndYCbCrConversionTest.cs b/tests/ImageSharp.Tests/ColorProfiles/RgbAndYCbCrConversionTest.cs
index 91f7fc08e..ede8226e4 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/RgbAndYCbCrConversionTest.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/RgbAndYCbCrConversionTest.cs
@@ -16,9 +16,9 @@ public class RgbAndYCbCrConversionTest
private static readonly ApproximateColorProfileComparer Comparer = new(.001F);
[Theory]
- [InlineData(255, 128, 128, 1, 1, 1)]
- [InlineData(0, 128, 128, 0, 0, 0)]
- [InlineData(128, 128, 128, 0.502, 0.502, 0.502)]
+ [InlineData(1, .5F, .5F, 1, 1, 1)]
+ [InlineData(0, .5F, .5F, 0, 0, 0)]
+ [InlineData(.5F, .5F, .5F, .5F, .5F, .5F)]
public void Convert_YCbCr_To_Rgb(float y, float cb, float cr, float r, float g, float b)
{
// Arrange
@@ -45,10 +45,9 @@ public class RgbAndYCbCrConversionTest
}
[Theory]
- [InlineData(0, 0, 0, 0, 128, 128)]
- [InlineData(1, 1, 1, 255, 128, 128)]
- [InlineData(0.5, 0.5, 0.5, 127.5, 128, 128)]
- [InlineData(1, 0, 0, 76.245, 84.972, 255)]
+ [InlineData(1, 1, 1, 1, .5F, .5F)]
+ [InlineData(0, 0, 0, 0, .5F, .5F)]
+ [InlineData(.5F, .5F, .5F, .5F, .5F, .5F)]
public void Convert_Rgb_To_YCbCr(float r, float g, float b, float y, float cb, float cr)
{
// Arrange
diff --git a/tests/ImageSharp.Tests/ColorProfiles/RgbAndYccKConversionTests.cs b/tests/ImageSharp.Tests/ColorProfiles/RgbAndYccKConversionTests.cs
new file mode 100644
index 000000000..78f424cc2
--- /dev/null
+++ b/tests/ImageSharp.Tests/ColorProfiles/RgbAndYccKConversionTests.cs
@@ -0,0 +1,80 @@
+// Copyright (c) Six Labors.
+// Licensed under the Six Labors Split License.
+
+using SixLabors.ImageSharp.ColorProfiles;
+
+namespace SixLabors.ImageSharp.Tests.ColorProfiles;
+
+///
+/// Tests - conversions.
+///
+///
+/// Test data generated mathematically
+///
+public class RgbAndYccKConversionTests
+{
+ private static readonly ApproximateColorProfileComparer Comparer = new(.001F);
+
+ [Theory]
+ [InlineData(1, .5F, .5F, 0, 1, 1, 1)]
+ [InlineData(0, .5F, .5F, 1, 0, 0, 0)]
+ [InlineData(.5F, .5F, .5F, 0, .5F, .5F, .5F)]
+ public void Convert_YccK_To_Rgb(float y, float cb, float cr, float k, float r, float g, float b)
+ {
+ // Arrange
+ YccK input = new(y, cb, cr, k);
+ Rgb expected = new(r, g, b);
+ ColorProfileConverter converter = new();
+
+ Span inputSpan = new YccK[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new Rgb[5];
+
+ // Act
+ Rgb actual = converter.Convert(input);
+ converter.Convert(inputSpan, actualSpan);
+
+ // Assert
+ Assert.Equal(expected, actual, Comparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], Comparer);
+ }
+ }
+
+ [Theory]
+ [InlineData(1, 1, 1, 1, .5F, .5F, 0)]
+ [InlineData(0, 0, 0, 0, .5F, .5F, 1)]
+ [InlineData(.5F, .5F, .5F, 1, .5F, .5F, .5F)]
+ public void Convert_Rgb_To_YccK(float r, float g, float b, float y, float cb, float cr, float k)
+ {
+ // Multiple YccK representations can decode to the same RGB value.
+ // For example, (Y=1.0, Cb=0.5, Cr=0.5, K=0.5) and (Y=0.5, Cb=0.5, Cr=0.5, K=0.0) both yield RGB (0.5, 0.5, 0.5).
+ // This is expected because YccK is not a unique encoding — K modulates RGB after YCbCr decoding.
+ // Round-tripping RGB -> YccK -> RGB is stable, but YccK -> RGB -> YccK is not injective.
+
+ // Arrange
+ Rgb input = new(r, g, b);
+ YccK expected = new(y, cb, cr, k);
+ ColorProfileConverter converter = new();
+
+ Span inputSpan = new Rgb[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new YccK[5];
+
+ // Act
+ YccK actual = converter.Convert(input);
+ converter.Convert(inputSpan, actualSpan);
+
+ // Assert
+ Assert.Equal(expected, actual, Comparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], Comparer);
+ }
+ }
+}
diff --git a/tests/ImageSharp.Tests/ColorProfiles/RgbTests.cs b/tests/ImageSharp.Tests/ColorProfiles/RgbTests.cs
index 7e4d4ee0e..707b3e2a7 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/RgbTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/RgbTests.cs
@@ -10,6 +10,7 @@ namespace SixLabors.ImageSharp.Tests.ColorProfiles;
///
/// Tests the struct.
///
+[Trait("Color", "Conversion")]
public class RgbTests
{
[Fact]
diff --git a/tests/ImageSharp.Tests/ColorProfiles/StringRepresentationTests.cs b/tests/ImageSharp.Tests/ColorProfiles/StringRepresentationTests.cs
index 770c987db..f61124d8f 100644
--- a/tests/ImageSharp.Tests/ColorProfiles/StringRepresentationTests.cs
+++ b/tests/ImageSharp.Tests/ColorProfiles/StringRepresentationTests.cs
@@ -6,11 +6,13 @@ using SixLabors.ImageSharp.ColorProfiles;
namespace SixLabors.ImageSharp.Tests.ColorProfiles;
+[Trait("Color", "Conversion")]
public class StringRepresentationTests
{
private static readonly Vector3 One = new(1);
private static readonly Vector3 Zero = new(0);
private static readonly Vector3 Random = new(42.4F, 94.5F, 83.4F);
+ private static readonly Vector4 Random4 = new(42.4F, 94.5F, 83.4F, 1);
public static readonly TheoryData