Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Consider a way to represent color spaces #1

Closed
slaren opened this issue Jul 28, 2013 · 6 comments
Closed

Consider a way to represent color spaces #1

slaren opened this issue Jul 28, 2013 · 6 comments

Comments

@slaren
Copy link

slaren commented Jul 28, 2013

We need a way to represent color spaces. It may be desirable to have color spaces defined independantly of color formats, ideally allowing us to have color types defined as a combination of channel type, color format and color space, such as:

// color channels
trait Channel { .. }

// color spaces
enum Linear {}
enum sRGB {}

trait ColorSpace { .. }

impl ColorSpace for Linear { .. }
impl ColorSpace for SRGB { .. }

// color formats
struct RGB<T: Channel, S: ColorSpace> { r: T, g: T, b: T }

// color types
trait Color<T: Channel, S: ColorSpace> { .. }

impl<T: Channel, S: ColorSpace> Color<T, S> for RGB<T, S> { .. }

// possible color types: RGB<u8, sRGB>, RGB<f32, Linear>, etc

However, this may not work well in practice since color spaces are often tied to their own color formats.

@flying-sheep
Copy link

there is another color library that has them: retep998/colors-rs

also there’s rudimentary color structs in PistonDevelopers/image

I’d love to see this stuff unified! Maybe use this (colors, channels, alpha-channel) as a basis without much bloat and base both PistonDevelopers/image and a new color-conversion library on top of it.

gtaylor/python-colormath has pretty complete support of all this, we can use it as orientation (note gtaylor/python-colormath#43, though)

Here’s a small bit of python-colormath expressed in rust + japaric/linalg

use linalg::{Mat, RowVec};

pub trait Illuminant {
    fn illuminant(self) -> RowVec<f32>;
}

#[derive(Copy,Show)]
pub enum Illuminants2 { A, B, C, D50, D55, D65, D75, E, F2, F7, F11 }
#[derive(Copy,Show)]
pub enum Illuminants10 { D50, D55, D65, D75 }

impl Illuminant for Illuminants2 {
    fn illuminant(self) -> RowVec<f32> {
        match self {
            Illuminants2::A   => mat![1.09850, 1., 0.35585],
            Illuminants2::B   => mat![0.99072, 1., 0.85223],
            Illuminants2::C   => mat![0.98074, 1., 1.18232],
            Illuminants2::D50 => mat![0.96422, 1., 0.82521],
            Illuminants2::D55 => mat![0.95682, 1., 0.92149],
            Illuminants2::D65 => mat![0.95047, 1., 1.08883],
            Illuminants2::D75 => mat![0.94972, 1., 1.22638],
            Illuminants2::E   => mat![1.00000, 1., 1.00000],
            Illuminants2::F2  => mat![0.99186, 1., 0.67393],
            Illuminants2::F7  => mat![0.95041, 1., 1.08747],
            Illuminants2::F11 => mat![1.00962, 1., 0.64350],
        }
    }
}

impl Illuminant for Illuminants10 {
    fn illuminant(self) -> RowVec<f32> {
        match self {
            Illuminants10::D50 => mat![0.96720, 1., 0.8143],
            Illuminants10::D55 => mat![0.95800, 1., 0.9093],
            Illuminants10::D65 => mat![0.94810, 1., 1.0730],
            Illuminants10::D75 => mat![0.94416, 1., 1.2064],
        }
    }
}

#[derive(Copy,Show)]
pub enum AdaptionMatrices { XYZScaling, Bradford, VonKries }

impl AdaptionMatrices {
    pub fn adaption_matrix(self) -> Mat<f32> {
        match self {
            AdaptionMatrices::XYZScaling => mat![
                1.0, 0.0, 0.0;
                0.0, 1.0, 0.0;
                0.0, 0.0, 1.0;
            ],
            AdaptionMatrices::Bradford => mat![
                 0.8951,  0.2664, -0.1614;
                -0.7502,  1.7135,  0.0367;
                 0.0389, -0.0685,  1.0296;
            ],
            AdaptionMatrices::VonKries => mat![
                 0.40024, 0.70760, -0.08081;
                -0.22630, 1.16532,  0.04570;
                 0.00000, 0.00000,  0.91822;
            ],
        }
    }
}

@flying-sheep
Copy link

good info is to be found here and here

@retep998
Copy link

retep998 commented Jan 5, 2015

I'll support any initiative to have a standard way of working with colors and colorspaces, as long as it is done well.
You're free to rip any code you want from colors-rs.

@flying-sheep
Copy link

do you have any opinions on #24?

@brendanzab
Copy link
Owner

Awesome! I am just finishing up a massive cleanup of noise-rs with the help of others, and I think it is well time for color-rs to get some love. I'll see what is in colors-rs and am happy to work with you to improve it.

@flying-sheep
Copy link

since this is an info dump as well as an discussion: this project makes advanced use of color models (not in rust).

i think if we could elegantly support that use case, we’re set.

@slaren slaren closed this as completed Oct 10, 2023
KSroido referenced this issue in KSroido/color-rs Nov 22, 2024
…ble items in scope

error[E0034]: multiple applicable items in scope
    --> C:\Users\ksxmy\.cargo\git\checkouts\color-rs-aa80dce33bd75e44\c39c52a\src\channel.rs:130:14
     |
130  |         self.clamp(zero(),one())
     |              ^^^^^ multiple `clamp` found
     |
note: candidate #1 is defined in the trait `Channel`
    --> C:\Users\ksxmy\.cargo\git\checkouts\color-rs-aa80dce33bd75e44\c39c52a\src\channel.rs:31:5
     |
31   |     fn clamp(self, lo: Self, hi: Self) -> Self {
     |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
note: candidate brendanzab#2 is defined in the trait `Float`
    --> C:\Users\ksxmy\.cargo\registry\src\index.crates.io-6f17d22bba15001f\num-traits-0.2.19\src\float.rs:1545:5
     |
1545 |     fn clamp(self, min: Self, max: Self) -> Self {
     |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
help: disambiguate the method for candidate #1
     |
130  |         Channel::clamp(self, zero(), one())
     |
help: disambiguate the method for candidate brendanzab#2
     |
130  |         Float::clamp(self, zero(), one())
     |
photex pushed a commit that referenced this issue Nov 22, 2024
Update fn clamp() in channel.rs to fix error[E0034]: multiple applica…
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants