C#: Synchronize Color with Core
- Add `Luminance` readonly property. - Add `LinearToSrgb` and `SrgbToLinear` static methods. - Add `FromOkHsl` static method. - Add `FromRgbe9995` static method. - Add `FromString` static method. - Expose `FromHtml` static method. - Expose `HtmlIsValid` static method. - Add and update some Color documentation.
This commit is contained in:
parent
bc5d67c613
commit
d843a7ab97
4 changed files with 183 additions and 24 deletions
|
@ -205,11 +205,18 @@
|
|||
<description>
|
||||
Returns the [Color] associated with the provided [param hex] integer in 32-bit ARGB format (8 bits per channel, alpha channel first).
|
||||
In GDScript and C#, the [int] is best visualized with hexadecimal notation ([code]"0x"[/code] prefix).
|
||||
[codeblock]
|
||||
[codeblocks]
|
||||
[gdscript]
|
||||
var red = Color.hex(0xffff0000)
|
||||
var dark_cyan = Color.hex(0xff008b8b)
|
||||
var my_color = Color.hex(0xa4bbefd2)
|
||||
[/codeblock]
|
||||
[/gdscript]
|
||||
[csharp]
|
||||
var red = new Color(0xffff0000);
|
||||
var dark_cyan = new Color(0xff008b8b);
|
||||
var my_color = new Color(0xa4bbefd2);
|
||||
[/csharp]
|
||||
[/codeblocks]
|
||||
</description>
|
||||
</method>
|
||||
<method name="hex64" qualifiers="static">
|
||||
|
@ -234,9 +241,9 @@
|
|||
var col = Color.html("663399cc") # col is Color(0.4, 0.2, 0.6, 0.8)
|
||||
[/gdscript]
|
||||
[csharp]
|
||||
var blue = new Color("#0000ff"); // blue is Color(0.0, 0.0, 1.0, 1.0)
|
||||
var green = new Color("#0F0"); // green is Color(0.0, 1.0, 0.0, 1.0)
|
||||
var col = new Color("663399cc"); // col is Color(0.4, 0.2, 0.6, 0.8)
|
||||
var blue = Color.FromHtml("#0000ff"); // blue is Color(0.0, 0.0, 1.0, 1.0)
|
||||
var green = Color.FromHtml("#0F0"); // green is Color(0.0, 1.0, 0.0, 1.0)
|
||||
var col = Color.FromHtml("663399cc"); // col is Color(0.4, 0.2, 0.6, 0.8)
|
||||
[/csharp]
|
||||
[/codeblocks]
|
||||
</description>
|
||||
|
@ -257,14 +264,13 @@
|
|||
Color.html_is_valid("#55aaFF5") # Returns false
|
||||
[/gdscript]
|
||||
[csharp]
|
||||
// This method is not available in C#. Use `StringExtensions.IsValidHtmlColor()`, instead.
|
||||
"#55AAFF".IsValidHtmlColor(); // Returns true
|
||||
"#55AAFF20".IsValidHtmlColor(); // Returns true
|
||||
"55AAFF".IsValidHtmlColor(); // Returns true
|
||||
"#F2C".IsValidHtmlColor(); // Returns true
|
||||
Color.IsHtmlValid("#55AAFF"); // Returns true
|
||||
Color.IsHtmlValid("#55AAFF20"); // Returns true
|
||||
Color.IsHtmlValid("55AAFF"); // Returns true
|
||||
Color.IsHtmlValid("#F2C"); // Returns true
|
||||
|
||||
"#AABBC".IsValidHtmlColor(); // Returns false
|
||||
"#55aaFF5".IsValidHtmlColor(); // Returns false
|
||||
Color.IsHtmlValid("#AABBC"); // Returns false
|
||||
Color.IsHtmlValid("#55aaFF5"); // Returns false
|
||||
[/csharp]
|
||||
[/codeblocks]
|
||||
</description>
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
using System;
|
||||
using System.Runtime.InteropServices;
|
||||
using Godot.NativeInterop;
|
||||
|
||||
namespace Godot
|
||||
{
|
||||
|
@ -186,6 +187,19 @@ namespace Godot
|
|||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Returns the light intensity of the color, as a value between 0.0 and 1.0 (inclusive).
|
||||
/// This is useful when determining light or dark color. Colors with a luminance smaller
|
||||
/// than 0.5 can be generally considered dark.
|
||||
/// Note: <see cref="Luminance"/> relies on the color being in the linear color space to
|
||||
/// return an accurate relative luminance value. If the color is in the sRGB color space
|
||||
/// use <see cref="SrgbToLinear"/> to convert it to the linear color space first.
|
||||
/// </summary>
|
||||
public readonly float Luminance
|
||||
{
|
||||
get { return 0.2126f * r + 0.7152f * g + 0.0722f * b; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Access color components using their index.
|
||||
/// </summary>
|
||||
|
@ -362,6 +376,35 @@ namespace Godot
|
|||
);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Returns the color converted to the sRGB color space.
|
||||
/// This method assumes the original color is in the linear color space.
|
||||
/// See also <see cref="SrgbToLinear"/> which performs the opposite operation.
|
||||
/// </summary>
|
||||
/// <returns>The sRGB color.</returns>
|
||||
public readonly Color LinearToSrgb()
|
||||
{
|
||||
return new Color(
|
||||
r < 0.0031308f ? 12.92f * r : (1.0f + 0.055f) * (float)Mathf.Pow(r, 1.0f / 2.4f) - 0.055f,
|
||||
g < 0.0031308f ? 12.92f * g : (1.0f + 0.055f) * (float)Mathf.Pow(g, 1.0f / 2.4f) - 0.055f,
|
||||
b < 0.0031308f ? 12.92f * b : (1.0f + 0.055f) * (float)Mathf.Pow(b, 1.0f / 2.4f) - 0.055f, a);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Returns the color converted to linear color space.
|
||||
/// This method assumes the original color already is in sRGB color space.
|
||||
/// See also <see cref="LinearToSrgb"/> which performs the opposite operation.
|
||||
/// </summary>
|
||||
/// <returns>The color in linear color space.</returns>
|
||||
public readonly Color SrgbToLinear()
|
||||
{
|
||||
return new Color(
|
||||
r < 0.04045f ? r * (1.0f / 12.92f) : (float)Mathf.Pow((r + 0.055f) * (float)(1.0 / (1.0 + 0.055)), 2.4f),
|
||||
g < 0.04045f ? g * (1.0f / 12.92f) : (float)Mathf.Pow((g + 0.055f) * (float)(1.0 / (1.0 + 0.055)), 2.4f),
|
||||
b < 0.04045f ? b * (1.0f / 12.92f) : (float)Mathf.Pow((b + 0.055f) * (float)(1.0 / (1.0 + 0.055)), 2.4f),
|
||||
a);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Returns the color converted to an unsigned 32-bit integer in ABGR
|
||||
/// format (each byte represents a color channel).
|
||||
|
@ -565,6 +608,10 @@ namespace Godot
|
|||
/// <see cref="Colors"/> constants.
|
||||
/// </summary>
|
||||
/// <param name="code">The HTML color code or color name to construct from.</param>
|
||||
/// <exception cref="ArgumentOutOfRangeException">
|
||||
/// A color cannot be inferred from the given <paramref name="code"/>.
|
||||
/// It was invalid HTML and a color with that name was not found.
|
||||
/// </exception>
|
||||
public Color(string code)
|
||||
{
|
||||
if (HtmlIsValid(code))
|
||||
|
@ -597,7 +644,7 @@ namespace Godot
|
|||
/// <exception name="ArgumentOutOfRangeException">
|
||||
/// <paramref name="rgba"/> color code is invalid.
|
||||
/// </exception>
|
||||
private static Color FromHTML(ReadOnlySpan<char> rgba)
|
||||
public static Color FromHTML(ReadOnlySpan<char> rgba)
|
||||
{
|
||||
Color c;
|
||||
if (rgba.Length == 0)
|
||||
|
@ -705,28 +752,59 @@ namespace Godot
|
|||
/// the constants defined in <see cref="Colors"/>.
|
||||
/// </summary>
|
||||
/// <param name="name">The name of the color.</param>
|
||||
/// <exception cref="ArgumentOutOfRangeException">
|
||||
/// A color with the given name is not found.
|
||||
/// </exception>
|
||||
/// <returns>The constructed color.</returns>
|
||||
private static Color Named(string name)
|
||||
{
|
||||
if (!FindNamedColor(name, out Color color))
|
||||
{
|
||||
throw new ArgumentOutOfRangeException($"Invalid Color Name: {name}");
|
||||
}
|
||||
|
||||
return color;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Returns a color according to the standardized name, with the
|
||||
/// specified alpha value. Supported color names are the same as
|
||||
/// the constants defined in <see cref="Colors"/>.
|
||||
/// If a color with the given name is not found, it returns
|
||||
/// <paramref name="default"/>.
|
||||
/// </summary>
|
||||
/// <param name="name">The name of the color.</param>
|
||||
/// <param name="default">
|
||||
/// The default color to return when a color with the given name
|
||||
/// is not found.
|
||||
/// </param>
|
||||
/// <returns>The constructed color.</returns>
|
||||
private static Color Named(string name, Color @default)
|
||||
{
|
||||
if (!FindNamedColor(name, out Color color))
|
||||
{
|
||||
return @default;
|
||||
}
|
||||
|
||||
return color;
|
||||
}
|
||||
|
||||
private static bool FindNamedColor(string name, out Color color)
|
||||
{
|
||||
name = name.Replace(" ", string.Empty);
|
||||
name = name.Replace("-", string.Empty);
|
||||
name = name.Replace("_", string.Empty);
|
||||
name = name.Replace("'", string.Empty);
|
||||
name = name.Replace(".", string.Empty);
|
||||
name = name.ToUpper();
|
||||
name = name.ToUpperInvariant();
|
||||
|
||||
if (!Colors.namedColors.ContainsKey(name))
|
||||
{
|
||||
throw new ArgumentOutOfRangeException($"Invalid Color Name: {name}");
|
||||
}
|
||||
|
||||
return Colors.namedColors[name];
|
||||
return Colors.namedColors.TryGetValue(name, out color);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Constructs a color from an HSV profile, with values on the
|
||||
/// range of 0 to 1. This is equivalent to using each of
|
||||
/// the <c>h</c>/<c>s</c>/<c>v</c> properties, but much more efficient.
|
||||
/// Constructs a color from an HSV profile. The <paramref name="hue"/>,
|
||||
/// <paramref name="saturation"/>, and <paramref name="value"/> are typically
|
||||
/// between 0.0 and 1.0.
|
||||
/// </summary>
|
||||
/// <param name="hue">The HSV hue, typically on the range of 0 to 1.</param>
|
||||
/// <param name="saturation">The HSV saturation, typically on the range of 0 to 1.</param>
|
||||
|
@ -841,13 +919,78 @@ namespace Godot
|
|||
return ParseCol4(str, index) * 16 + ParseCol4(str, index + 1);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Constructs a color from an OK HSL profile. The <paramref name="hue"/>,
|
||||
/// <paramref name="saturation"/>, and <paramref name="lightness"/> are typically
|
||||
/// between 0.0 and 1.0.
|
||||
/// </summary>
|
||||
/// <param name="hue">The OK HSL hue, typically on the range of 0 to 1.</param>
|
||||
/// <param name="saturation">The OK HSL saturation, typically on the range of 0 to 1.</param>
|
||||
/// <param name="lightness">The OK HSL lightness, typically on the range of 0 to 1.</param>
|
||||
/// <param name="alpha">The alpha (transparency) value, typically on the range of 0 to 1.</param>
|
||||
/// <returns>The constructed color.</returns>
|
||||
public static Color FromOkHsl(float hue, float saturation, float lightness, float alpha = 1.0f)
|
||||
{
|
||||
return NativeFuncs.godotsharp_color_from_ok_hsl(hue, saturation, lightness, alpha);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Encodes a <see cref="Color"/> from a RGBE9995 format integer.
|
||||
/// See <see cref="Image.Format.Rgbe9995"/>.
|
||||
/// </summary>
|
||||
/// <param name="rgbe">The RGBE9995 encoded color.</param>
|
||||
/// <returns>The constructed color.</returns>
|
||||
public static Color FromRgbe9995(uint rgbe)
|
||||
{
|
||||
float r = rgbe & 0x1ff;
|
||||
float g = (rgbe >> 9) & 0x1ff;
|
||||
float b = (rgbe >> 18) & 0x1ff;
|
||||
float e = rgbe >> 27;
|
||||
float m = (float)Mathf.Pow(2.0f, e - 15.0f - 9.0f);
|
||||
|
||||
float rd = r * m;
|
||||
float gd = g * m;
|
||||
float bd = b * m;
|
||||
|
||||
return new Color(rd, gd, bd, 1.0f);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Constructs a color from the given string, which can be either an HTML color
|
||||
/// code or a named color. Returns <paramref name="default"/> if the color cannot
|
||||
/// be inferred from the string. Supported color names are the same as the
|
||||
/// <see cref="Colors"/> constants.
|
||||
/// </summary>
|
||||
/// <param name="str">The HTML color code or color name.</param>
|
||||
/// <param name="default">The fallback color to return if the color cannot be inferred.</param>
|
||||
/// <returns>The constructed color.</returns>
|
||||
public static Color FromString(string str, Color @default)
|
||||
{
|
||||
if (HtmlIsValid(str))
|
||||
{
|
||||
return FromHTML(str);
|
||||
}
|
||||
else
|
||||
{
|
||||
return Named(str, @default);
|
||||
}
|
||||
}
|
||||
|
||||
private static string ToHex32(float val)
|
||||
{
|
||||
byte b = (byte)Mathf.RoundToInt(Mathf.Clamp(val * 255, 0, 255));
|
||||
return b.HexEncode();
|
||||
}
|
||||
|
||||
internal static bool HtmlIsValid(ReadOnlySpan<char> color)
|
||||
/// <summary>
|
||||
/// Returns <see langword="true"/> if <paramref name="color"/> is a valid HTML hexadecimal
|
||||
/// color string. The string must be a hexadecimal value (case-insensitive) of either 3,
|
||||
/// 4, 6 or 8 digits, and may be prefixed by a hash sign (<c>#</c>). This method is
|
||||
/// identical to <see cref="StringExtensions.IsValidHtmlColor(string)"/>.
|
||||
/// </summary>
|
||||
/// <param name="color">The HTML hexadecimal color string.</param>
|
||||
/// <returns>Whether or not the string was a valid HTML hexadecimal color string.</returns>
|
||||
public static bool HtmlIsValid(ReadOnlySpan<char> color)
|
||||
{
|
||||
if (color.IsEmpty)
|
||||
{
|
||||
|
|
|
@ -153,6 +153,8 @@ namespace Godot.NativeInterop
|
|||
internal static partial void godotsharp_callable_call_deferred(in godot_callable p_callable,
|
||||
godot_variant** p_args, int p_arg_count);
|
||||
|
||||
internal static partial Color godotsharp_color_from_ok_hsl(float p_h, float p_s, float p_l, float p_alpha);
|
||||
|
||||
// GDNative functions
|
||||
|
||||
// gdnative.h
|
||||
|
|
|
@ -514,6 +514,13 @@ void godotsharp_callable_call_deferred(Callable *p_callable, const Variant **p_a
|
|||
p_callable->call_deferredp(p_args, p_arg_count);
|
||||
}
|
||||
|
||||
godot_color godotsharp_color_from_ok_hsl(float p_h, float p_s, float p_l, float p_alpha) {
|
||||
godot_color ret;
|
||||
Color *dest = (Color *)&ret;
|
||||
memnew_placement(dest, Color(Color::from_ok_hsl(p_h, p_s, p_l, p_alpha)));
|
||||
return ret;
|
||||
}
|
||||
|
||||
// GDNative functions
|
||||
|
||||
// gdnative.h
|
||||
|
@ -1345,6 +1352,7 @@ static const void *unmanaged_callbacks[]{
|
|||
(void *)godotsharp_callable_get_data_for_marshalling,
|
||||
(void *)godotsharp_callable_call,
|
||||
(void *)godotsharp_callable_call_deferred,
|
||||
(void *)godotsharp_color_from_ok_hsl,
|
||||
(void *)godotsharp_method_bind_ptrcall,
|
||||
(void *)godotsharp_method_bind_call,
|
||||
(void *)godotsharp_variant_new_string_name,
|
||||
|
|
Loading…
Reference in a new issue