1
0
Fork 0
mirror of https://github.com/Ellpeck/MLEM.git synced 2024-12-24 17:29:23 +01:00

Added ColorExtensions.ToHsv and ColorHelper.FromHsv

This commit is contained in:
Ell 2024-07-29 20:46:40 +02:00
parent 9c4a66ef6d
commit 74254e6cdb
3 changed files with 86 additions and 14 deletions

View file

@ -18,7 +18,7 @@ Jump to version:
### MLEM
Additions
- Added ColorExtensions.ToHsl and ColorHelper.FromHsl
- Added ColorExtensions.ToHsl and ColorHelper.FromHsl as well as ColorExtensions.ToHsv and ColorHelper.FromHsv
## 7.0.0

View file

@ -91,6 +91,38 @@ namespace MLEM.Graphics {
return (h, s, l);
}
/// <summary>
/// Converts the given <paramref name="color"/> into HSV representation and returns the result as a value tuple with values between 0 and 1.
/// </summary>
/// <remarks>This code is adapted from https://gist.github.com/mjackson/5311256.</remarks>
/// <param name="color">The color to convert.</param>
/// <returns>The resulting HSV color as a value tuple containing H, S and V, each between 0 and 1.</returns>
public static (float H, float S, float V) ToHsv(this Color color) {
var r = color.R / 255F;
var g = color.G / 255F;
var b = color.B / 255F;
var max = Math.Max(Math.Max(r, g), b);
var min = Math.Min(Math.Min(r, g), b);
var d = max - min;
float h, s = max == 0 ? 0 : d / max, v = max;
if (max == min) {
h = 0; // achromatic
} else {
if (r == max) {
h = (g - b) / d + (g < b ? 6 : 0);
} else if (g == max) {
h = (b - r) / d + 2;
} else {
h = (r - g) / d + 4;
}
h /= 6;
}
return (h, s, v);
}
}
/// <summary>
@ -184,6 +216,46 @@ namespace MLEM.Graphics {
return new Color(r, g, b);
}
/// <summary>
///Converts the given HSV color to an RGB <see cref="Color"/> and returns the result.
/// </summary>
/// <remarks>This code is adapted from https://gist.github.com/mjackson/5311256.</remarks>
/// <param name="color">The HSV color to convert, as a value tuple that contains H, S and V values, each between 0 and 1.</param>
/// <returns>The resulting RGB color.</returns>
public static Color FromHsv((float H, float S, float V) color) {
return ColorHelper.FromHsv(color.H, color.S, color.V);
}
/// <summary>
///Converts the given HSV values to an RGB <see cref="Color"/> and returns the result.
/// </summary>
/// <remarks>This code is adapted from https://gist.github.com/mjackson/5311256.</remarks>
/// <param name="h">The H component of the HSV color, between 0 and 1.</param>
/// <param name="s">The S component of the HSV color, between 0 and 1.</param>
/// <param name="v">The V component of the HSV color, between 0 and 1.</param>
/// <returns>The resulting RGB color.</returns>
public static Color FromHsv(float h, float s, float v) {
var i = (int) (h * 6);
var f = h * 6 - i;
var p = v * (1 - s);
var q = v * (1 - f * s);
var t = v * (1 - (1 - f) * s);
switch (i % 6) {
case 0:
return new Color(v, t, p);
case 1:
return new Color(q, v, p);
case 2:
return new Color(p, v, t);
case 3:
return new Color(p, q, v);
case 4:
return new Color(t, p, v);
default: // 5
return new Color(v, p, q);
}
}
private static float HueToRgb(float p, float q, float t) {
if (t < 0)
t += 1;

View file

@ -398,27 +398,27 @@ public class GameImpl : MlemGame {
Console.WriteLine("Buttons: " + string.Join(", ", GenericInput.AllButtons));
Console.WriteLine("Inputs: " + string.Join(", ", GenericInput.AllInputs));*/
var hsl = new Panel(Anchor.Center, new Vector2(100), true);
var color = Color.Pink.ToHsl();
hsl.AddChild(new Paragraph(Anchor.AutoLeft, 1, "H"));
hsl.AddChild(new Slider(Anchor.AutoLeft, new Vector2(1, 10), 5, 1) {
var hsv = new Panel(Anchor.Center, new Vector2(100), true);
var color = Color.Pink.ToHsv();
hsv.AddChild(new Paragraph(Anchor.AutoLeft, 1, "H"));
hsv.AddChild(new Slider(Anchor.AutoLeft, new Vector2(1, 10), 5, 1) {
CurrentValue = color.H,
OnValueChanged = (_, v) => color.H = v
});
hsl.AddChild(new Paragraph(Anchor.AutoLeft, 1, "S"));
hsl.AddChild(new Slider(Anchor.AutoLeft, new Vector2(1, 10), 5, 1) {
hsv.AddChild(new Paragraph(Anchor.AutoLeft, 1, "S"));
hsv.AddChild(new Slider(Anchor.AutoLeft, new Vector2(1, 10), 5, 1) {
CurrentValue = color.S,
OnValueChanged = (_, v) => color.S = v
});
hsl.AddChild(new Paragraph(Anchor.AutoLeft, 1, "L"));
hsl.AddChild(new Slider(Anchor.AutoLeft, new Vector2(1, 10), 5, 1) {
CurrentValue = color.L,
OnValueChanged = (_, v) => color.L = v
hsv.AddChild(new Paragraph(Anchor.AutoLeft, 1, "V"));
hsv.AddChild(new Slider(Anchor.AutoLeft, new Vector2(1, 10), 5, 1) {
CurrentValue = color.V,
OnValueChanged = (_, v) => color.V = v
});
hsl.AddChild(new Group(Anchor.AutoLeft, new Vector2(1, 40), false) {
OnDrawn = (e, _, batch, _, _) => batch.Draw(batch.GetBlankTexture(), e.DisplayArea, ColorHelper.FromHsl(color))
hsv.AddChild(new Group(Anchor.AutoLeft, new Vector2(1, 40), false) {
OnDrawn = (e, _, batch, _, _) => batch.Draw(batch.GetBlankTexture(), e.DisplayArea, ColorHelper.FromHsv(color))
});
this.UiSystem.Add("HSL", hsl);
this.UiSystem.Add("HSV", hsv);
}
protected override void DoUpdate(GameTime gameTime) {