diff --git a/src/Avalonia.Base/Media/Color.cs b/src/Avalonia.Base/Media/Color.cs index 5463df0bbb..624513f065 100644 --- a/src/Avalonia.Base/Media/Color.cs +++ b/src/Avalonia.Base/Media/Color.cs @@ -21,10 +21,7 @@ namespace Avalonia.Media #if !BUILDTASK public #endif - readonly struct Color : IEquatable -#if !BUILDTASK - , IFormattable -#endif + readonly struct Color : IEquatable, IFormattable { private const double byteToDouble = 1.0 / 255; @@ -464,7 +461,6 @@ namespace Avalonia.Media } } -#if !BUILDTASK /// /// Returns a formatted string representation of the color. /// @@ -501,10 +497,10 @@ namespace Avalonia.Media "x" => $"#{R:X2}{G:X2}{B:X2}", "H" => $"#{R:X2}{G:X2}{B:X2}{A:X2}", - "R" => string.Format(CultureInfo.InvariantCulture, "rgba({0}, {1}, {2}, {3:F2})", R, G, B, A * byteToDouble), - "r" => string.Format(CultureInfo.InvariantCulture, "rgb({0}, {1}, {2})", R, G, B), - "R%" => FormatRgbaPercent(), - "r%" => FormatRgbPercent(), + "R" => FormatRgbCss(), + "r" => FormatRgbCss(includeAlpha: false), + "R%" => FormatRgbPercentCss(), + "r%" => FormatRgbPercentCss(includeAlpha: false), "L" or "l" or "L%" or "l%" => ToHsl().ToString(format, formatProvider), "V" or "v" or "V%" or "v%" => ToHsv().ToString(format, formatProvider), @@ -513,23 +509,48 @@ namespace Avalonia.Media }; } - private string FormatRgbaPercent() + /// + /// Formats the color as a CSS rgb() or rgba() string using absolute RGB components and fractional alpha. + /// + private string FormatRgbCss(bool includeAlpha = true) { - int rPct = (int)Math.Round(R * byteToDouble * 100.0); - int gPct = (int)Math.Round(G * byteToDouble * 100.0); - int bPct = (int)Math.Round(B * byteToDouble * 100.0); - int aPct = (int)Math.Round(A * byteToDouble * 100.0); - return string.Format(CultureInfo.InvariantCulture, "rgba({0}%, {1}%, {2}%, {3}%)", rPct, gPct, bPct, aPct); + if (includeAlpha) + { + return string.Format( + CultureInfo.InvariantCulture, + "rgba({0}, {1}, {2}, {3:F2})", + R, + G, + B, + A * byteToDouble); + } + + return string.Format(CultureInfo.InvariantCulture, "rgb({0}, {1}, {2})", R, G, B); } - private string FormatRgbPercent() + /// + /// Formats the color as a CSS rgb() or rgba() string with all components as percentages. + /// + private string FormatRgbPercentCss(bool includeAlpha = true) { int rPct = (int)Math.Round(R * byteToDouble * 100.0); int gPct = (int)Math.Round(G * byteToDouble * 100.0); int bPct = (int)Math.Round(B * byteToDouble * 100.0); + + if (includeAlpha) + { + int aPct = (int)Math.Round(A * byteToDouble * 100.0); + return string.Format( + CultureInfo.InvariantCulture, + "rgba({0}%, {1}%, {2}%, {3}%)", + rPct, + gPct, + bPct, + aPct); + } + return string.Format(CultureInfo.InvariantCulture, "rgb({0}%, {1}%, {2}%)", rPct, gPct, bPct); } -#endif /// /// Returns the integer representation of the color. diff --git a/src/Avalonia.Base/Media/HslColor.cs b/src/Avalonia.Base/Media/HslColor.cs index 0bae48417b..2a09575d69 100644 --- a/src/Avalonia.Base/Media/HslColor.cs +++ b/src/Avalonia.Base/Media/HslColor.cs @@ -17,10 +17,7 @@ namespace Avalonia.Media #if !BUILDTASK public #endif - readonly struct HslColor : IEquatable -#if !BUILDTASK - , IFormattable -#endif + readonly struct HslColor : IEquatable, IFormattable { /// /// Initializes a new instance of the struct. @@ -180,7 +177,6 @@ namespace Avalonia.Media return HslColor.ToHsv(H, S, L, A); } -#if !BUILDTASK /// /// Returns a formatted string representation of the HSL color. /// @@ -215,10 +211,10 @@ namespace Avalonia.Media { "X" or "x" or "H" or "R" or "r" or "R%" or "r%" => ToRgb().ToString(format, formatProvider), - "L" => FormatHsla(), - "l" => FormatHsl(), - "L%" => FormatHslaPercent(), - "l%" => FormatHslPercent(), + "L" => FormatHslCss(), + "l" => FormatHslCss(includeAlpha: false), + "L%" => FormatHslPercentCss(), + "l%" => FormatHslPercentCss(includeAlpha: false), "V" or "v" or "V%" or "v%" => ToHsv().ToString(format, formatProvider), @@ -226,39 +222,53 @@ namespace Avalonia.Media }; } - private string FormatHsla() + /// + /// Formats the color as a CSS hsl() or hsla() string using degrees, percent saturation/lightness, + /// and fractional alpha. + /// + private string FormatHslCss(bool includeAlpha = true) { int hDeg = (int)Math.Round(H); int sPct = (int)Math.Round(S * 100.0); int lPct = (int)Math.Round(L * 100.0); - return string.Format(CultureInfo.InvariantCulture, "hsla({0}, {1}%, {2}%, {3:F2})", hDeg, sPct, lPct, A); - } - private string FormatHsl() - { - int hDeg = (int)Math.Round(H); - int sPct = (int)Math.Round(S * 100.0); - int lPct = (int)Math.Round(L * 100.0); + if (includeAlpha) + { + return string.Format( + CultureInfo.InvariantCulture, + "hsla({0}, {1}%, {2}%, {3:F2})", + hDeg, + sPct, + lPct, + A); + } + return string.Format(CultureInfo.InvariantCulture, "hsl({0}, {1}%, {2}%)", hDeg, sPct, lPct); } - private string FormatHslaPercent() + /// + /// Formats the color as a CSS hsl() or hsla() string with all components as percentages. + /// + private string FormatHslPercentCss(bool includeAlpha = true) { int hPct = (int)Math.Round(H / 360.0 * 100.0); int sPct = (int)Math.Round(S * 100.0); int lPct = (int)Math.Round(L * 100.0); - int aPct = (int)Math.Round(A * 100.0); - return string.Format(CultureInfo.InvariantCulture, "hsla({0}%, {1}%, {2}%, {3}%)", hPct, sPct, lPct, aPct); - } - private string FormatHslPercent() - { - int hPct = (int)Math.Round(H / 360.0 * 100.0); - int sPct = (int)Math.Round(S * 100.0); - int lPct = (int)Math.Round(L * 100.0); + if (includeAlpha) + { + int aPct = (int)Math.Round(A * 100.0); + return string.Format( + CultureInfo.InvariantCulture, + "hsla({0}%, {1}%, {2}%, {3}%)", + hPct, + sPct, + lPct, + aPct); + } + return string.Format(CultureInfo.InvariantCulture, "hsl({0}%, {1}%, {2}%)", hPct, sPct, lPct); } -#endif /// public override string ToString() diff --git a/src/Avalonia.Base/Media/HsvColor.cs b/src/Avalonia.Base/Media/HsvColor.cs index 5f36dff9ef..7ff180c8c5 100644 --- a/src/Avalonia.Base/Media/HsvColor.cs +++ b/src/Avalonia.Base/Media/HsvColor.cs @@ -17,10 +17,7 @@ namespace Avalonia.Media #if !BUILDTASK public #endif - readonly struct HsvColor : IEquatable -#if !BUILDTASK - , IFormattable -#endif + readonly struct HsvColor : IEquatable, IFormattable { /// /// Initializes a new instance of the struct. @@ -210,7 +207,6 @@ namespace Avalonia.Media return HsvColor.ToHsl(H, S, V, A); } -#if !BUILDTASK /// /// Returns a formatted string representation of the HSV color. /// @@ -247,48 +243,62 @@ namespace Avalonia.Media "L" or "l" or "L%" or "l%" => ToHsl().ToString(format, formatProvider), - "V" => FormatHsva(), - "v" => FormatHsv(), - "V%" => FormatHsvaPercent(), - "v%" => FormatHsvPercent(), + "V" => FormatHsvCss(), + "v" => FormatHsvCss(includeAlpha: false), + "V%" => FormatHsvPercentCss(), + "v%" => FormatHsvPercentCss(includeAlpha: false), _ => throw new FormatException($"Format string '{format}' is not supported.") }; } - private string FormatHsva() + /// + /// Formats the color as a CSS hsv() or hsva() string using degrees, percent saturation/value, + /// and fractional alpha. + /// + private string FormatHsvCss(bool includeAlpha = true) { int hDeg = (int)Math.Round(H); int sPct = (int)Math.Round(S * 100.0); int vPct = (int)Math.Round(V * 100.0); - return string.Format(CultureInfo.InvariantCulture, "hsva({0}, {1}%, {2}%, {3:F2})", hDeg, sPct, vPct, A); - } - private string FormatHsv() - { - int hDeg = (int)Math.Round(H); - int sPct = (int)Math.Round(S * 100.0); - int vPct = (int)Math.Round(V * 100.0); + if (includeAlpha) + { + return string.Format( + CultureInfo.InvariantCulture, + "hsva({0}, {1}%, {2}%, {3:F2})", + hDeg, + sPct, + vPct, + A); + } + return string.Format(CultureInfo.InvariantCulture, "hsv({0}, {1}%, {2}%)", hDeg, sPct, vPct); } - private string FormatHsvaPercent() + /// + /// Formats the color as a CSS hsv() or hsva() string with all components as percentages. + /// + private string FormatHsvPercentCss(bool includeAlpha = true) { int hPct = (int)Math.Round(H / 360.0 * 100.0); int sPct = (int)Math.Round(S * 100.0); int vPct = (int)Math.Round(V * 100.0); - int aPct = (int)Math.Round(A * 100.0); - return string.Format(CultureInfo.InvariantCulture, "hsva({0}%, {1}%, {2}%, {3}%)", hPct, sPct, vPct, aPct); - } - private string FormatHsvPercent() - { - int hPct = (int)Math.Round(H / 360.0 * 100.0); - int sPct = (int)Math.Round(S * 100.0); - int vPct = (int)Math.Round(V * 100.0); + if (includeAlpha) + { + int aPct = (int)Math.Round(A * 100.0); + return string.Format( + CultureInfo.InvariantCulture, + "hsva({0}%, {1}%, {2}%, {3}%)", + hPct, + sPct, + vPct, + aPct); + } + return string.Format(CultureInfo.InvariantCulture, "hsv({0}%, {1}%, {2}%)", hPct, sPct, vPct); } -#endif /// public override string ToString()