diff --git a/dgl/Color.hpp b/dgl/Color.hpp index edf77c0d..d47f354f 100644 --- a/dgl/Color.hpp +++ b/dgl/Color.hpp @@ -28,7 +28,7 @@ START_NAMESPACE_DGL // TODO: create color from "#333" and "#112233" like strings /** - A color made from red, green, blue and alpha floating-point values in [0..1] range. + A color made from red, green, blue and alpha floating-point values in [0..1] range. */ struct Color { /** @@ -73,6 +73,11 @@ struct Color { */ static Color fromHSL(float hue, float saturation, float lightness, float alpha = 1.0f); + /** + Create a color from a HTML string like "#333" or "#112233". + */ + static Color fromHTML(const char* rgb, float alpha = 1.0f); + /** Linearly interpolate this color against another. */ diff --git a/dgl/src/Color.cpp b/dgl/src/Color.cpp index 78bbd488..91c03ec0 100644 --- a/dgl/src/Color.cpp +++ b/dgl/src/Color.cpp @@ -108,6 +108,49 @@ Color Color::fromHSL(float hue, float saturation, float lightness, float alpha) return nvgHSLA(hue, saturation, lightness, static_cast(getFixedRange(alpha)*255.0f)); } +Color Color::fromHTML(const char* rgb, float alpha) +{ + Color fallback; + DISTRHO_SAFE_ASSERT_RETURN(rgb != nullptr && rgb[0] != '\0', fallback); + + if (rgb[0] == '#') ++rgb; + DISTRHO_SAFE_ASSERT_RETURN(rgb[0] != '\0', fallback); + + std::size_t rgblen(std::strlen(rgb)); + DISTRHO_SAFE_ASSERT_RETURN(rgblen == 3 || rgblen == 6, fallback); + + char rgbtmp[3] = { '\0', '\0', '\0' }; + int r, g, b; + + if (rgblen == 3) + { + rgbtmp[0] = rgb[0]; + r = std::strtol(rgbtmp, nullptr, 16); + + rgbtmp[0] = rgb[1]; + g = std::strtol(rgbtmp, nullptr, 16); + + rgbtmp[0] = rgb[2]; + b = std::strtol(rgbtmp, nullptr, 16); + } + else + { + rgbtmp[0] = rgb[0]; + rgbtmp[1] = rgb[1]; + r = std::strtol(rgbtmp, nullptr, 16); + + rgbtmp[0] = rgb[2]; + rgbtmp[1] = rgb[3]; + g = std::strtol(rgbtmp, nullptr, 16); + + rgbtmp[0] = rgb[4]; + rgbtmp[1] = rgb[5]; + b = std::strtol(rgbtmp, nullptr, 16); + } + + return Color(r, g, b, static_cast(getFixedRange(alpha)*255.0f)); +} + void Color::interpolate(const Color& other, float u) noexcept { fixRange(u);