diff --git a/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndCieLuvConversionTests.cs b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndCieLuvConversionTests.cs
new file mode 100644
index 000000000..e465757ef
--- /dev/null
+++ b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndCieLuvConversionTests.cs
@@ -0,0 +1,78 @@
+// Copyright (c) Six Labors and contributors.
+// Licensed under the Apache License, Version 2.0.
+
+using System;
+using SixLabors.ImageSharp.ColorSpaces;
+using SixLabors.ImageSharp.ColorSpaces.Conversion;
+using Xunit;
+
+namespace SixLabors.ImageSharp.Tests.Colorspaces.Conversion
+{
+ ///
+ /// Tests - conversions.
+ ///
+ public class CieLchAndCieLuvConversionTests
+ {
+ private static readonly ApproximateColorSpaceComparer ColorSpaceComparer = new ApproximateColorSpaceComparer(.0002F);
+ private static readonly ColorSpaceConverter Converter = new ColorSpaceConverter();
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 0, 0)]
+ [InlineData(36.0555, 103.6901, 10.01514, 34.89777, 187.6642, -7.181467)]
+ public void Convert_CieLch_to_CieLuv(float l, float c, float h, float l2, float u, float v)
+ {
+ // Arrange
+ var input = new CieLch(l, c, h);
+ var expected = new CieLuv(l2, u, v);
+
+ Span inputSpan = new CieLch[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieLuv[5];
+
+ // Act
+ var actual = Converter.ToCieLuv(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(34.89777, 187.6642, -7.181467, 36.05552, 103.6901, 10.01514)]
+ public void Convert_CieLuv_to_CieLch(float l2, float u, float v, float l, float c, float h)
+ {
+ // Arrange
+ var input = new CieLuv(l2, u, v);
+ var expected = new CieLch(l, c, h);
+
+ Span inputSpan = new CieLuv[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieLch[5];
+
+ // Act
+ var actual = Converter.ToCieLch(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndHslConversionTests.cs b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndHslConversionTests.cs
new file mode 100644
index 000000000..d00a164c0
--- /dev/null
+++ b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndHslConversionTests.cs
@@ -0,0 +1,78 @@
+// Copyright (c) Six Labors and contributors.
+// Licensed under the Apache License, Version 2.0.
+
+using System;
+using SixLabors.ImageSharp.ColorSpaces;
+using SixLabors.ImageSharp.ColorSpaces.Conversion;
+using Xunit;
+
+namespace SixLabors.ImageSharp.Tests.Colorspaces.Conversion
+{
+ ///
+ /// Tests - conversions.
+ ///
+ public class CieLchAndHslConversionTests
+ {
+ private static readonly ApproximateColorSpaceComparer ColorSpaceComparer = new ApproximateColorSpaceComparer(.0002F);
+ private static readonly ColorSpaceConverter Converter = new ColorSpaceConverter();
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 0, 0)]
+ [InlineData(36.0555, 103.6901, 10.01514, 341.959, 1, 0.4207301)]
+ public void Convert_CieLch_to_Hsl(float l, float c, float h, float h2, float s, float l2)
+ {
+ // Arrange
+ var input = new CieLch(l, c, h);
+ var expected = new Hsl(h2, s, l2);
+
+ Span inputSpan = new CieLch[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new Hsl[5];
+
+ // Act
+ var actual = Converter.ToHsl(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(341.959, 1, 0.4207301, 46.13444, 78.0637, 22.90503)]
+ public void Convert_Hsl_to_CieLch(float h2, float s, float l2, float l, float c, float h)
+ {
+ // Arrange
+ var input = new Hsl(h2, s, l2);
+ var expected = new CieLch(l, c, h);
+
+ Span inputSpan = new Hsl[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieLch[5];
+
+ // Act
+ var actual = Converter.ToCieLch(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndHsvConversionTests.cs b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndHsvConversionTests.cs
new file mode 100644
index 000000000..d3ff04a75
--- /dev/null
+++ b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndHsvConversionTests.cs
@@ -0,0 +1,78 @@
+// Copyright (c) Six Labors and contributors.
+// Licensed under the Apache License, Version 2.0.
+
+using System;
+using SixLabors.ImageSharp.ColorSpaces;
+using SixLabors.ImageSharp.ColorSpaces.Conversion;
+using Xunit;
+
+namespace SixLabors.ImageSharp.Tests.Colorspaces.Conversion
+{
+ ///
+ /// Tests - conversions.
+ ///
+ public class CieLchAndHsvConversionTests
+ {
+ private static readonly ApproximateColorSpaceComparer ColorSpaceComparer = new ApproximateColorSpaceComparer(.0002F);
+ private static readonly ColorSpaceConverter Converter = new ColorSpaceConverter();
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 0, 0)]
+ [InlineData(36.0555, 103.6901, 10.01514, 341.959, 1, 0.8414602)]
+ public void Convert_CieLch_to_Hsv(float l, float c, float h, float h2, float s, float v)
+ {
+ // Arrange
+ var input = new CieLch(l, c, h);
+ var expected = new Hsv(h2, s, v);
+
+ Span inputSpan = new CieLch[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new Hsv[5];
+
+ // Act
+ var actual = Converter.ToHsv(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(341.959, 1, 0.8414602, 46.13444, 78.0637, 22.90501)]
+ public void Convert_Hsv_to_CieLch(float h2, float s, float v, float l, float c, float h)
+ {
+ // Arrange
+ var input = new Hsv(h2, s, v);
+ var expected = new CieLch(l, c, h);
+
+ Span inputSpan = new Hsv[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieLch[5];
+
+ // Act
+ var actual = Converter.ToCieLch(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndHunterLabConversionTests.cs b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndHunterLabConversionTests.cs
new file mode 100644
index 000000000..852e56110
--- /dev/null
+++ b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndHunterLabConversionTests.cs
@@ -0,0 +1,78 @@
+// Copyright (c) Six Labors and contributors.
+// Licensed under the Apache License, Version 2.0.
+
+using System;
+using SixLabors.ImageSharp.ColorSpaces;
+using SixLabors.ImageSharp.ColorSpaces.Conversion;
+using Xunit;
+
+namespace SixLabors.ImageSharp.Tests.Colorspaces.Conversion
+{
+ ///
+ /// Tests - conversions.
+ ///
+ public class CieLchAndHunterLabConversionTests
+ {
+ private static readonly ApproximateColorSpaceComparer ColorSpaceComparer = new ApproximateColorSpaceComparer(.0002F);
+ private static readonly ColorSpaceConverter Converter = new ColorSpaceConverter();
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 0, 0)]
+ [InlineData(36.0555, 103.6901, 10.01514, 29.41358, 106.6302, 9.102425)]
+ public void Convert_CieLch_to_HunterLab(float l, float c, float h, float l2, float a, float b)
+ {
+ // Arrange
+ var input = new CieLch(l, c, h);
+ var expected = new HunterLab(l2, a, b);
+
+ Span inputSpan = new CieLch[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new HunterLab[5];
+
+ // Act
+ var actual = Converter.ToHunterLab(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(29.41358, 106.6302, 9.102425, 36.05551, 103.6901, 10.01515)]
+ public void Convert_HunterLab_to_CieLch(float l2, float a, float b, float l, float c, float h)
+ {
+ // Arrange
+ var input = new HunterLab(l2, a, b);
+ var expected = new CieLch(l, c, h);
+
+ Span inputSpan = new HunterLab[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieLch[5];
+
+ // Act
+ var actual = Converter.ToCieLch(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndLinearRgbConversionTests.cs b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndLinearRgbConversionTests.cs
new file mode 100644
index 000000000..80b72cb2c
--- /dev/null
+++ b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndLinearRgbConversionTests.cs
@@ -0,0 +1,78 @@
+// Copyright (c) Six Labors and contributors.
+// Licensed under the Apache License, Version 2.0.
+
+using System;
+using SixLabors.ImageSharp.ColorSpaces;
+using SixLabors.ImageSharp.ColorSpaces.Conversion;
+using Xunit;
+
+namespace SixLabors.ImageSharp.Tests.Colorspaces.Conversion
+{
+ ///
+ /// Tests - conversions.
+ ///
+ public class CieLchAndLinearRgbConversionTests
+ {
+ private static readonly ApproximateColorSpaceComparer ColorSpaceComparer = new ApproximateColorSpaceComparer(.0002F);
+ private static readonly ColorSpaceConverter Converter = new ColorSpaceConverter();
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 0, 0)]
+ [InlineData(36.0555, 103.6901, 10.01514, 0.6765013, 0, 0.05209038)]
+ public void Convert_CieLch_to_LinearRgb(float l, float c, float h, float r, float g, float b)
+ {
+ // Arrange
+ var input = new CieLch(l, c, h);
+ var expected = new LinearRgb(r, g, b);
+
+ Span inputSpan = new CieLch[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new LinearRgb[5];
+
+ // Act
+ var actual = Converter.ToLinearRgb(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0.6765013, 0, 0.05209038, 46.13445, 78.06367, 22.90504)]
+ public void Convert_LinearRgb_to_CieLch(float r, float g, float b, float l, float c, float h)
+ {
+ // Arrange
+ var input = new LinearRgb(r, g, b);
+ var expected = new CieLch(l, c, h);
+
+ Span inputSpan = new LinearRgb[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieLch[5];
+
+ // Act
+ var actual = Converter.ToCieLch(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndLmsConversionTests.cs b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndLmsConversionTests.cs
new file mode 100644
index 000000000..314734ff2
--- /dev/null
+++ b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndLmsConversionTests.cs
@@ -0,0 +1,78 @@
+// Copyright (c) Six Labors and contributors.
+// Licensed under the Apache License, Version 2.0.
+
+using System;
+using SixLabors.ImageSharp.ColorSpaces;
+using SixLabors.ImageSharp.ColorSpaces.Conversion;
+using Xunit;
+
+namespace SixLabors.ImageSharp.Tests.Colorspaces.Conversion
+{
+ ///
+ /// Tests - conversions.
+ ///
+ public class CieLchAndLmsConversionTests
+ {
+ private static readonly ApproximateColorSpaceComparer ColorSpaceComparer = new ApproximateColorSpaceComparer(.0002F);
+ private static readonly ColorSpaceConverter Converter = new ColorSpaceConverter();
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 0, 0)]
+ [InlineData(36.0555, 103.6901, 10.01514, 0.2440057, -0.04603009, 0.05780027)]
+ public void Convert_CieLch_to_Lms(float l, float c, float h, float l2, float m, float s)
+ {
+ // Arrange
+ var input = new CieLch(l, c, h);
+ var expected = new Lms(l2, m, s);
+
+ Span inputSpan = new CieLch[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new Lms[5];
+
+ // Act
+ var actual = Converter.ToLms(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0.2440057, -0.04603009, 0.05780027, 36.05552, 103.6901, 10.01515)]
+ public void Convert_Lms_to_CieLch(float l2, float m, float s, float l, float c, float h)
+ {
+ // Arrange
+ var input = new Lms(l2, m, s);
+ var expected = new CieLch(l, c, h);
+
+ Span inputSpan = new Lms[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieLch[5];
+
+ // Act
+ var actual = Converter.ToCieLch(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndRgbConversionTests.cs b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndRgbConversionTests.cs
new file mode 100644
index 000000000..389528dcd
--- /dev/null
+++ b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndRgbConversionTests.cs
@@ -0,0 +1,78 @@
+// Copyright (c) Six Labors and contributors.
+// Licensed under the Apache License, Version 2.0.
+
+using System;
+using SixLabors.ImageSharp.ColorSpaces;
+using SixLabors.ImageSharp.ColorSpaces.Conversion;
+using Xunit;
+
+namespace SixLabors.ImageSharp.Tests.Colorspaces.Conversion
+{
+ ///
+ /// Tests - conversions.
+ ///
+ public class CieLchAndRgbConversionTests
+ {
+ private static readonly ApproximateColorSpaceComparer ColorSpaceComparer = new ApproximateColorSpaceComparer(.0002F);
+ private static readonly ColorSpaceConverter Converter = new ColorSpaceConverter();
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 0, 0)]
+ [InlineData(36.0555, 103.6901, 10.01514, 0.8414602, 0, 0.2530123)]
+ public void Convert_CieLch_to_Rgb(float l, float c, float h, float r, float g, float b)
+ {
+ // Arrange
+ var input = new CieLch(l, c, h);
+ var expected = new Rgb(r, g, b);
+
+ Span inputSpan = new CieLch[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new Rgb[5];
+
+ // Act
+ var actual = Converter.ToRgb(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0.8414602, 0, 0.2530123, 46.13444, 78.0637, 22.90503)]
+ public void Convert_Rgb_to_CieLch(float r, float g, float b, float l, float c, float h)
+ {
+ // Arrange
+ var input = new Rgb(r, g, b);
+ var expected = new CieLch(l, c, h);
+
+ Span inputSpan = new Rgb[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieLch[5];
+
+ // Act
+ var actual = Converter.ToCieLch(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndYCbCrConversionTests.cs b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndYCbCrConversionTests.cs
new file mode 100644
index 000000000..a2bd7eadc
--- /dev/null
+++ b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieLchAndYCbCrConversionTests.cs
@@ -0,0 +1,78 @@
+// Copyright (c) Six Labors and contributors.
+// Licensed under the Apache License, Version 2.0.
+
+using System;
+using SixLabors.ImageSharp.ColorSpaces;
+using SixLabors.ImageSharp.ColorSpaces.Conversion;
+using Xunit;
+
+namespace SixLabors.ImageSharp.Tests.Colorspaces.Conversion
+{
+ ///
+ /// Tests - conversions.
+ ///
+ public class CieLchAndYCbCrConversionTests
+ {
+ private static readonly ApproximateColorSpaceComparer ColorSpaceComparer = new ApproximateColorSpaceComparer(.0002F);
+ private static readonly ColorSpaceConverter Converter = new ColorSpaceConverter();
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 128, 128)]
+ [InlineData(36.0555, 103.6901, 10.01514, 71.5122, 124.053, 230.0401)]
+ public void Convert_CieLch_to_YCbCr(float l, float c, float h, float y, float cb, float cr)
+ {
+ // Arrange
+ var input = new CieLch(l, c, h);
+ var expected = new YCbCr(y, cb, cr);
+
+ Span inputSpan = new CieLch[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new YCbCr[5];
+
+ // Act
+ var actual = Converter.ToYCbCr(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(71.5122, 124.053, 230.0401, 46.23178, 78.1114, 22.7662)]
+ public void Convert_YCbCr_to_CieLch(float y, float cb, float cr, float l, float c, float h)
+ {
+ // Arrange
+ var input = new YCbCr(y, cb, cr);
+ var expected = new CieLch(l, c, h);
+
+ Span inputSpan = new YCbCr[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieLch[5];
+
+ // Act
+ var actual = Converter.ToCieLch(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndCieLchConversionTests.cs b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndCieLchConversionTests.cs
new file mode 100644
index 000000000..89d78ece1
--- /dev/null
+++ b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndCieLchConversionTests.cs
@@ -0,0 +1,79 @@
+// Copyright (c) Six Labors and contributors.
+// Licensed under the Apache License, Version 2.0.
+
+using System;
+using SixLabors.ImageSharp.ColorSpaces;
+using SixLabors.ImageSharp.ColorSpaces.Conversion;
+using Xunit;
+
+namespace SixLabors.ImageSharp.Tests.Colorspaces.Conversion
+{
+ ///
+ /// Tests - conversions.
+ ///
+ public class CieXyzAndCieLchConversionTests
+ {
+ private static readonly ApproximateColorSpaceComparer ColorSpaceComparer = new ApproximateColorSpaceComparer(.0002F);
+ private static readonly ColorSpaceConverter Converter = new ColorSpaceConverter();
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0.360555, 0.936901, 0.1001514, 97.50815, 155.8035, 139.323)]
+ public void Convert_CieXyz_to_CieLch(float x, float y, float yl, float l, float c, float h)
+ {
+ // Arrange
+ var input = new CieXyz(x, y, yl);
+ var expected = new CieLch(l, c, h);
+
+ Span inputSpan = new CieXyz[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieLch[5];
+
+ // Act
+ var actual = Converter.ToCieLch(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 0, 0)]
+ [InlineData(97.50815, 155.8035, 139.323, 0.3605551, 0.936901, 0.1001514)]
+ public void Convert_CieLch_to_CieXyz(float l, float c, float h, float x, float y, float yl)
+ {
+ // Arrange
+ var input = new CieLch(l, c, h);
+ var expected = new CieXyz(x, y, yl);
+
+ Span inputSpan = new CieLch[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieXyz[5];
+
+ // Act
+ var actual = Converter.ToCieXyz(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndCieLchuvConversionTests.cs b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndCieLchuvConversionTests.cs
new file mode 100644
index 000000000..fbd602d9a
--- /dev/null
+++ b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndCieLchuvConversionTests.cs
@@ -0,0 +1,79 @@
+// Copyright (c) Six Labors and contributors.
+// Licensed under the Apache License, Version 2.0.
+
+using System;
+using SixLabors.ImageSharp.ColorSpaces;
+using SixLabors.ImageSharp.ColorSpaces.Conversion;
+using Xunit;
+
+namespace SixLabors.ImageSharp.Tests.Colorspaces.Conversion
+{
+ ///
+ /// Tests - conversions.
+ ///
+ public class CieXyzAndCieLchuvConversionTests
+ {
+ private static readonly ApproximateColorSpaceComparer ColorSpaceComparer = new ApproximateColorSpaceComparer(.0002F);
+ private static readonly ColorSpaceConverter Converter = new ColorSpaceConverter();
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0.360555, 0.936901, 0.1001514, 97.50697, 183.3831, 133.6321)]
+ public void Convert_CieXyz_to_CieLchuv(float x, float y, float yl, float l, float c, float h)
+ {
+ // Arrange
+ var input = new CieXyz(x, y, yl);
+ var expected = new CieLchuv(l, c, h);
+
+ Span inputSpan = new CieXyz[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieLchuv[5];
+
+ // Act
+ var actual = Converter.ToCieLchuv(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 0, 0)]
+ [InlineData(97.50697, 183.3831, 133.6321, 0.360555, 0.936901, 0.1001515)]
+ public void Convert_CieLchuv_to_CieXyz(float l, float c, float h, float x, float y, float yl)
+ {
+ // Arrange
+ var input = new CieLchuv(l, c, h);
+ var expected = new CieXyz(x, y, yl);
+
+ Span inputSpan = new CieLchuv[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieXyz[5];
+
+ // Act
+ var actual = Converter.ToCieXyz(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndHslConversionTests.cs b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndHslConversionTests.cs
new file mode 100644
index 000000000..844372264
--- /dev/null
+++ b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndHslConversionTests.cs
@@ -0,0 +1,80 @@
+// Copyright (c) Six Labors and contributors.
+// Licensed under the Apache License, Version 2.0.
+
+using System;
+using SixLabors.ImageSharp.ColorSpaces;
+using SixLabors.ImageSharp.ColorSpaces.Conversion;
+using Xunit;
+
+namespace SixLabors.ImageSharp.Tests.Colorspaces.Conversion
+{
+ ///
+ /// Tests - conversions.
+ ///
+ public class CieXyzAndHslConversionTests
+ {
+ private static readonly ApproximateColorSpaceComparer ColorSpaceComparer = new ApproximateColorSpaceComparer(.0002F);
+ private static readonly ColorSpaceConverter Converter = new ColorSpaceConverter();
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 0, 0)]
+ [InlineData(0.360555, 0.936901, 0.1001514, 120, 1, 0.5)]
+ public void Convert_CieXyz_to_Hsl(float x, float y, float yl, float h, float s, float l)
+ {
+ // Arrange
+ var input = new CieXyz(x, y, yl);
+ var expected = new Hsl(h, s, l);
+
+ Span inputSpan = new CieXyz[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new Hsl[5];
+
+ // Act
+ var actual = Converter.ToHsl(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 0, 0)]
+ [InlineData(120, 1, 0.5, 0.3575761, 0.7151522, 0.119192)]
+ public void Convert_Hsl_to_CieXyz(float h, float s, float l, float x, float y, float yl)
+ {
+ // Arrange
+ var input = new Hsl(h, s, l);
+ var expected = new CieXyz(x, y, yl);
+
+ Span inputSpan = new Hsl[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieXyz[5];
+
+ // Act
+ var actual = Converter.ToCieXyz(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndHsvConversionTests.cs b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndHsvConversionTests.cs
new file mode 100644
index 000000000..327d660c6
--- /dev/null
+++ b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndHsvConversionTests.cs
@@ -0,0 +1,80 @@
+// Copyright (c) Six Labors and contributors.
+// Licensed under the Apache License, Version 2.0.
+
+using System;
+using SixLabors.ImageSharp.ColorSpaces;
+using SixLabors.ImageSharp.ColorSpaces.Conversion;
+using Xunit;
+
+namespace SixLabors.ImageSharp.Tests.Colorspaces.Conversion
+{
+ ///
+ /// Tests - conversions.
+ ///
+ public class CieXyzAndHsvConversionTests
+ {
+ private static readonly ApproximateColorSpaceComparer ColorSpaceComparer = new ApproximateColorSpaceComparer(.0002F);
+ private static readonly ColorSpaceConverter Converter = new ColorSpaceConverter();
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 0, 0)]
+ [InlineData(0.360555, 0.936901, 0.1001514, 120, 1, 0.9999999)]
+ public void Convert_CieXyz_to_Hsv(float x, float y, float yl, float h, float s, float v)
+ {
+ // Arrange
+ var input = new CieXyz(x, y, yl);
+ var expected = new Hsv(h, s, v);
+
+ Span inputSpan = new CieXyz[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new Hsv[5];
+
+ // Act
+ var actual = Converter.ToHsv(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 0, 0)]
+ [InlineData(120, 1, 0.9999999, 0.3575761, 0.7151522, 0.119192)]
+ public void Convert_Hsv_to_CieXyz(float h, float s, float v, float x, float y, float yl)
+ {
+ // Arrange
+ var input = new Hsv(h, s, v);
+ var expected = new CieXyz(x, y, yl);
+
+ Span inputSpan = new Hsv[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieXyz[5];
+
+ // Act
+ var actual = Converter.ToCieXyz(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndYCbCrConversionTests.cs b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndYCbCrConversionTests.cs
new file mode 100644
index 000000000..eacdc7ffb
--- /dev/null
+++ b/tests/ImageSharp.Tests/Colorspaces/Conversion/CieXyzAndYCbCrConversionTests.cs
@@ -0,0 +1,80 @@
+// Copyright (c) Six Labors and contributors.
+// Licensed under the Apache License, Version 2.0.
+
+using System;
+using SixLabors.ImageSharp.ColorSpaces;
+using SixLabors.ImageSharp.ColorSpaces.Conversion;
+using Xunit;
+
+namespace SixLabors.ImageSharp.Tests.Colorspaces.Conversion
+{
+ ///
+ /// Tests - conversions.
+ ///
+ public class CieXyzAndYCbCrConversionTests
+ {
+ private static readonly ApproximateColorSpaceComparer ColorSpaceComparer = new ApproximateColorSpaceComparer(.0002F);
+ private static readonly ColorSpaceConverter Converter = new ColorSpaceConverter();
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 128, 128)]
+ [InlineData(0.360555, 0.936901, 0.1001514, 149.685, 43.52769, 21.23457)]
+ public void Convert_CieXyz_to_YCbCr(float x, float y, float z, float y2, float cb, float cr)
+ {
+ // Arrange
+ var input = new CieXyz(x, y, z);
+ var expected = new YCbCr(y2, cb, cr);
+
+ Span inputSpan = new CieXyz[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new YCbCr[5];
+
+ // Act
+ var actual = Converter.ToYCbCr(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 128, 128, 0, 0, 0)]
+ [InlineData(149.685, 43.52769, 21.23457, 0.3575761, 0.7151522, 0.119192)]
+ public void Convert_YCbCr_to_CieXyz(float y2, float cb, float cr, float x, float y, float z)
+ {
+ // Arrange
+ var input = new YCbCr(y2, cb, cr);
+ var expected = new CieXyz(x, y, z);
+
+ Span inputSpan = new YCbCr[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new CieXyz[5];
+
+ // Act
+ var actual = Converter.ToCieXyz(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/tests/ImageSharp.Tests/Colorspaces/Conversion/CmykAndYCbCrConversionTests.cs b/tests/ImageSharp.Tests/Colorspaces/Conversion/CmykAndYCbCrConversionTests.cs
new file mode 100644
index 000000000..8c45127e3
--- /dev/null
+++ b/tests/ImageSharp.Tests/Colorspaces/Conversion/CmykAndYCbCrConversionTests.cs
@@ -0,0 +1,79 @@
+// Copyright (c) Six Labors and contributors.
+// Licensed under the Apache License, Version 2.0.
+
+using System;
+using SixLabors.ImageSharp.ColorSpaces;
+using SixLabors.ImageSharp.ColorSpaces.Conversion;
+using Xunit;
+
+namespace SixLabors.ImageSharp.Tests.Colorspaces.Conversion
+{
+ ///
+ /// Tests - conversions.
+ ///
+ public class CmykAndYCbCrConversionTests
+ {
+ private static readonly ApproximateColorSpaceComparer ColorSpaceComparer = new ApproximateColorSpaceComparer(.0002F);
+ private static readonly ColorSpaceConverter Converter = new ColorSpaceConverter();
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [Theory]
+ [InlineData(0, 0, 0, 0, 255, 128, 128)]
+ [InlineData(0.360555, 0.1036901, 0.818514, 0.274615, 136.5134, 69.90555, 114.9948)]
+ public void Convert_Cmyk_to_YCbCr(float c, float m, float y, float k, float y2, float cb, float cr)
+ {
+ // Arrange
+ var input = new Cmyk(c, m, y, k);
+ var expected = new YCbCr(y2, cb, cr);
+
+ Span inputSpan = new Cmyk[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new YCbCr[5];
+
+ // Act
+ var actual = Converter.ToYCbCr(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+
+ ///
+ /// Tests conversion from to .
+ ///
+ [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)]
+ public void Convert_YCbCr_to_Cmyk(float y2, float cb, float cr, float c, float m, float y, float k)
+ {
+ // Arrange
+ var input = new YCbCr(y2, cb, cr);
+ var expected = new Cmyk(c, m, y, k);
+
+ Span inputSpan = new YCbCr[5];
+ inputSpan.Fill(input);
+
+ Span actualSpan = new Cmyk[5];
+
+ // Act
+ var actual = Converter.ToCmyk(input);
+ Converter.Convert(inputSpan, actualSpan, actualSpan.Length);
+
+ // Assert
+ Assert.Equal(expected, actual, ColorSpaceComparer);
+
+ for (int i = 0; i < actualSpan.Length; i++)
+ {
+ Assert.Equal(expected, actualSpan[i], ColorSpaceComparer);
+ }
+ }
+ }
+}
\ No newline at end of file