Skip to content

Commit

Permalink
LUV bugfixes, improve LCh
Browse files Browse the repository at this point in the history
  • Loading branch information
awxkee committed Jun 4, 2024
1 parent 6a53466 commit 41d2886
Show file tree
Hide file tree
Showing 4 changed files with 42 additions and 14 deletions.
2 changes: 1 addition & 1 deletion Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 2 additions & 2 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,9 @@ workspace = { members = ["src/app"] }

[package]
name = "colorutils-rs"
version = "0.2.9"
version = "0.2.10"
edition = "2021"
description = "Hig performance utilities for color format handling and conversion."
description = "High performance utilities for color format handling and conversion."
readme = "README.md"
keywords = ["lab", "hsv", "xyz", "luv", "hsl"]
license = "Apache-2.0 OR BSD-3-Clause"
Expand Down
38 changes: 28 additions & 10 deletions src/luv.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,15 +9,15 @@ pub struct Luv {
/// Together with v\* value, it defines chromaticity of the colour. The u\*
/// coordinate represents colour’s position on red-green axis with negative
/// values indicating more red and positive more green colour. Typical
/// values are in -100–100 range (but exact range for ‘valid’ colours
/// values are in -134–220 range (but exact range for ‘valid’ colours
/// depends on luminance and v\* value).
pub u: f32,
/// The u\* value of the colour.
///
/// Together with u\* value, it defines chromaticity of the colour. The v\*
/// coordinate represents colour’s position on blue-yellow axis with
/// negative values indicating more blue and positive more yellow colour.
/// Typical values are in -100–100 range (but exact range for ‘valid’
/// Typical values are in -140–122 range (but exact range for ‘valid’
/// colours depends on luminance and u\* value).
pub v: f32,
}
Expand Down Expand Up @@ -62,6 +62,7 @@ impl Luv {
pub fn from_rgb(rgb: &Rgb<u8>) -> Self {
let xyz = Xyz::from_srgb(rgb);
let [x, y, z] = [xyz.x, xyz.y, xyz.z];
let den = x + 15.0 * y + 3.0 * z;

let l = (if y < CUTOFF_FORWARD_Y {
MULTIPLIER_FORWARD_Y * y
Expand All @@ -70,10 +71,16 @@ impl Luv {
})
.min(100f32)
.max(0f32);
let u_prime = 4.0 * x / (x + 15.0 * y + 3.0 * z);
let v_prime = 9.0 * y / (x + 15.0 * y + 3.0 * z);
let u = 13f32 * l * (u_prime - WHITE_U_PRIME);
let v = 13f32 * l * (v_prime - WHITE_V_PRIME);
let (u, v);
if den != 0f32 {
let u_prime = 4.0 * x / den;
let v_prime = 9.0 * y / den;
u = 13f32 * l * (u_prime - WHITE_U_PRIME);
v = 13f32 * l * (v_prime - WHITE_V_PRIME);
} else {
u = 0f32;
v = 0f32;
}

Luv { l, u, v }
}
Expand All @@ -91,13 +98,19 @@ impl Luv {
let u = self.u * l13 + WHITE_U_PRIME;
let v = self.v * l13 + WHITE_V_PRIME;
let y = if self.l > 8f32 {
((self.l + 16f32) / 116f32).powf(3f32)
((self.l + 16f32) / 116f32).powi(3)
} else {
self.l * MULTIPLIER_INVERSE_Y
};
let den = 1f32 / (4f32 * v);
let x = y * 9f32 * u * den;
let z = y * (12.0 - 3.0 * u - 20.0 * v) * den;
let (x, z);
if v != 0f32 {
let den = 1f32 / (4f32 * v);
x = y * 9f32 * u * den;
z = y * (12.0f32 - 3.0f32 * u - 20f32 * v) * den;
} else {
x = 0f32;
z = 0f32;
}

Xyz::new(x, y, z).to_srgb()
}
Expand All @@ -118,6 +131,11 @@ impl LCh {
LCh::from_luv(Luv::from_rgba(rgba))
}

#[allow(dead_code)]
pub fn new(l: f32, c: f32, h: f32) -> Self {
LCh { l, c, h }
}

pub fn from_luv(luv: Luv) -> Self {
LCh {
l: luv.l,
Expand Down
12 changes: 11 additions & 1 deletion src/rgb.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
use crate::hsv::Hsv;
use crate::lab::Lab;
use crate::luv::Luv;
use crate::Hsl;
use crate::{Hsl, LCh};

pub struct Rgb<T> {
pub r: T,
Expand All @@ -11,23 +11,33 @@ pub struct Rgb<T> {

impl Rgb<u8> {
#[allow(dead_code)]
#[inline]
pub fn to_hsl(&self) -> Hsl {
Hsl::from_rgb(self)
}

#[allow(dead_code)]
#[inline]
pub fn to_hsv(&self) -> Hsv {
Hsv::from(self)
}

#[inline]
pub fn to_lab(&self) -> Lab {
Lab::from_rgb(self)
}

#[inline]
pub fn to_luv(&self) -> Luv {
Luv::from_rgb(self)
}

#[inline]
pub fn to_lch(&self) -> LCh {
LCh::from_rgb(self)
}

#[inline]
pub fn to_rgb_f32(&self) -> Rgb<f32> {
const SCALE: f32 = 1f32 / 255f32;
Rgb::<f32>::new(
Expand Down

0 comments on commit 41d2886

Please sign in to comment.