修正Cam16Jch到sRGB的转换算法。

This commit is contained in:
徐涛 2025-02-08 13:34:55 +08:00
parent 5d3fc2903b
commit e2806a0cc5

View File

@ -2,23 +2,29 @@ use palette::{
cam16::{Cam16Jch, Parameters}, cam16::{Cam16Jch, Parameters},
convert::FromColorUnclamped, convert::FromColorUnclamped,
luma::Luma, luma::Luma,
Hsl, IntoColor, IsWithinBounds, Oklab, Oklch, Srgb, Hsl, IntoColor, IsWithinBounds, Lchuv, Oklab, Oklch, Srgb,
}; };
pub fn map_cam16jch_to_srgb(origin: &Cam16Jch<f32>) -> Srgb { pub fn map_cam16jch_to_srgb(origin: &Cam16Jch<f32>) -> Srgb {
let mut new_original = Cam16Jch::new(origin.lightness, origin.chroma, origin.hue); let original_xyz = origin.into_xyz(Parameters::default_static_wp(40.0));
const FACTOR: f32 = 0.99; let mut new_srgb = Srgb::from_color_unclamped(original_xyz);
if new_srgb.is_within_bounds() {
return new_srgb;
}
let lchuv: Lchuv = Lchuv::from_color_unclamped(original_xyz);
let mut c: f32 = lchuv.chroma;
let original_c = c;
let h = lchuv.hue;
let l = lchuv.l;
loop { loop {
let new_srgb = let new_lchuv = Lchuv::new(l, c, h);
Srgb::from_color_unclamped(new_original.into_xyz(Parameters::default_static_wp(40.0))); new_srgb = new_lchuv.into_color();
if new_srgb.is_within_bounds() { c -= original_c / 1000.0;
if c > 0.0 && (new_srgb.is_within_bounds()) {
break new_srgb; break new_srgb;
} }
new_original = Cam16Jch::new(
new_original.lightness,
new_original.chroma * FACTOR,
new_original.hue,
);
} }
} }