Skip to content

Commit

Permalink
Add hwb color space
Browse files Browse the repository at this point in the history
  • Loading branch information
sidred committed Feb 15, 2016
1 parent 209402e commit 50a418a
Show file tree
Hide file tree
Showing 9 changed files with 519 additions and 167 deletions.
31 changes: 22 additions & 9 deletions src/convert.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
use num::Float;

use {Alpha, Rgb, Luma, Xyz, Yxy, Lab, Lch, Hsv, Hsl, Color};
use {Alpha, Rgb, Luma, Xyz, Yxy, Lab, Lch, Hsv, Hwb, Hsl, Color};

///FromColor provides conversion between the colors.
///
Expand Down Expand Up @@ -46,6 +46,11 @@ pub trait FromColor<T>: Sized
Self::from_rgb(inp.into_rgb())
}

///Convert from HWB color space
fn from_hwb(inp: Hwb<T>) -> Self {
Self::from_hsv(inp.into_hsv())
}

///Convert from Luma
fn from_luma(inp: Luma<T>) -> Self {
Self::from_xyz(inp.into_xyz())
Expand Down Expand Up @@ -95,6 +100,11 @@ pub trait IntoColor<T>: Sized
Hsv::from_rgb(self.into_rgb())
}

///Convert into HWB color space
fn into_hwb(self) -> Hwb<T> {
Hwb::from_hsv(self.into_hsv())
}

///Convert into Luma
fn into_luma(self) -> Luma<T> {
Luma::from_xyz(self.into_xyz())
Expand Down Expand Up @@ -163,6 +173,7 @@ macro_rules! impl_from_trait {
Color::Lch(c) => c.$into_fn(),
Color::Hsv(c) => c.$into_fn(),
Color::Hsl(c) => c.$into_fn(),
Color::Hwb(c) => c.$into_fn(),
}
}
}
Expand Down Expand Up @@ -218,14 +229,16 @@ impl_into_color!(Lch,from_lch);
impl_into_color!(Rgb,from_rgb);
impl_into_color!(Hsl,from_hsl);
impl_into_color!(Hsv,from_hsv);
impl_into_color!(Hwb,from_hwb);
impl_into_color!(Luma,from_luma);


impl_from_trait!((Xyz,into_xyz) => {Yxy, Lab, Lch, Rgb, Hsl, Hsv, Luma});
impl_from_trait!((Yxy,into_yxy) => {Xyz, Lab, Lch, Rgb, Hsl, Hsv, Luma});
impl_from_trait!((Lab,into_lab) => {Xyz, Yxy, Lch, Rgb, Hsl, Hsv, Luma});
impl_from_trait!((Lch,into_lch) => {Xyz, Yxy, Lab, Rgb, Hsl, Hsv, Luma});
impl_from_trait!((Rgb,into_rgb) => {Xyz, Yxy, Lab, Lch, Hsl, Hsv, Luma});
impl_from_trait!((Hsl,into_hsl) => {Xyz, Yxy, Lab, Lch, Rgb, Hsv, Luma});
impl_from_trait!((Hsv,into_hsv) => {Xyz, Yxy, Lab, Lch, Rgb, Hsl, Luma});
impl_from_trait!((Luma,into_luma) => {Xyz, Yxy, Lab, Lch, Rgb, Hsl, Hsv});
impl_from_trait!((Xyz,into_xyz) => {Yxy, Lab, Lch, Rgb, Hsl, Hsv, Hwb, Luma});
impl_from_trait!((Yxy,into_yxy) => {Xyz, Lab, Lch, Rgb, Hsl, Hsv, Hwb, Luma});
impl_from_trait!((Lab,into_lab) => {Xyz, Yxy, Lch, Rgb, Hsl, Hsv, Hwb, Luma});
impl_from_trait!((Lch,into_lch) => {Xyz, Yxy, Lab, Rgb, Hsl, Hsv, Hwb, Luma});
impl_from_trait!((Rgb,into_rgb) => {Xyz, Yxy, Lab, Lch, Hsl, Hsv, Hwb, Luma});
impl_from_trait!((Hsl,into_hsl) => {Xyz, Yxy, Lab, Lch, Rgb, Hsv, Hwb, Luma});
impl_from_trait!((Hsv,into_hsv) => {Xyz, Yxy, Lab, Lch, Rgb, Hsl, Hwb, Luma});
impl_from_trait!((Hwb,into_hwb) => {Xyz, Yxy, Lab, Lch, Rgb, Hsl, Hsv, Luma});
impl_from_trait!((Luma,into_luma) => {Xyz, Yxy, Lab, Lch, Rgb, Hsl, Hsv, Hwb});
3 changes: 2 additions & 1 deletion src/equality.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
use num::Float;
use approx::ApproxEq;

use {Xyz, Yxy, Lab, Lch, Rgb, Hsl, Hsv , Luma, LabHue, RgbHue, flt};
use {Xyz, Yxy, Lab, Lch, Rgb, Hsl, Hsv, Hwb, Luma, LabHue, RgbHue, flt};

macro_rules! impl_eq {
( $self_ty: ident , [$($element: ident),+]) => {
Expand Down Expand Up @@ -44,6 +44,7 @@ impl_eq!( Luma, [luma] );
impl_eq!( Lch, [l, chroma] );
impl_eq!( Hsl, [hue, saturation, lightness] );
impl_eq!( Hsv, [hue, saturation, value] );
impl_eq!( Hwb, [hue, whiteness, blackness] );

// For hues diffence is calculated and compared to zero. However due to the way floating point's
// work this is not so simple
Expand Down
17 changes: 16 additions & 1 deletion src/hsv.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ use num::Float;

use std::ops::{Add, Sub};

use {Alpha, Rgb, Xyz, Hsl, Limited, Mix, Shade, GetHue, Hue, Saturate, RgbHue, FromColor, clamp, flt};
use {Alpha, Rgb, Xyz, Hsl, Hwb, Limited, Mix, Shade, GetHue, Hue, Saturate, RgbHue, FromColor, clamp, flt};

///Linear HSV with an alpha component. See the [`Hsva` implementation in `Alpha`](struct.Alpha.html#Hsva).
pub type Hsva<T = f32> = Alpha<Hsv<T>, T>;
Expand Down Expand Up @@ -125,6 +125,21 @@ impl<T: Float> FromColor<T> for Hsv<T> {
hsv
}

fn from_hwb(hwb: Hwb<T>) -> Self {
let inv = T::one() - hwb.blackness;
// avoid divide by zero
let s = if inv.is_normal() {
T::one() - ( hwb.whiteness / inv )
} else {
T::zero()
};
Hsv {
hue: hwb.hue,
saturation: s,
value: inv,
}
}

}

impl<T: Float> Limited for Hsv<T> {
Expand Down
Loading

0 comments on commit 50a418a

Please sign in to comment.