Introduce web-colors feature flag to enable sRGB linear blending
This is how browsers perform color management. They treat gamma-corrected sRGB colors as if they were linear RGB. Correctness aside, this mode is introduced for legacy reasons. Most UI/UX tooling uses this color management as well, and many have created an intuition about how color should behave from interacting with a browser. This feature flag should facilitate application development with `iced` in those cases. More details: https://webcolorisstillbroken.com/
This commit is contained in:
parent
b5f102c558
commit
faa7627ea4
16 changed files with 99 additions and 30 deletions
|
|
@ -14,6 +14,7 @@ categories = ["gui"]
|
|||
geometry = ["lyon_path"]
|
||||
opengl = []
|
||||
image = ["dep:image", "kamadak-exif"]
|
||||
web-colors = []
|
||||
|
||||
[dependencies]
|
||||
glam = "0.24"
|
||||
|
|
|
|||
46
graphics/src/color.rs
Normal file
46
graphics/src/color.rs
Normal file
|
|
@ -0,0 +1,46 @@
|
|||
//! Manage colors for shaders.
|
||||
use crate::core::Color;
|
||||
|
||||
use bytemuck::{Pod, Zeroable};
|
||||
|
||||
/// A color packed as 4 floats representing RGBA channels.
|
||||
#[derive(Debug, Clone, Copy, PartialEq, Zeroable, Pod)]
|
||||
#[repr(C)]
|
||||
pub struct Packed([f32; 4]);
|
||||
|
||||
impl Packed {
|
||||
/// Returns the internal components of the [`Packed`] color.
|
||||
pub fn components(self) -> [f32; 4] {
|
||||
self.0
|
||||
}
|
||||
}
|
||||
|
||||
/// A flag that indicates whether the renderer should perform gamma correction.
|
||||
pub const GAMMA_CORRECTION: bool = internal::GAMMA_CORRECTION;
|
||||
|
||||
/// Packs a [`Color`].
|
||||
pub fn pack(color: impl Into<Color>) -> Packed {
|
||||
Packed(internal::pack(color.into()))
|
||||
}
|
||||
|
||||
#[cfg(not(feature = "web-colors"))]
|
||||
mod internal {
|
||||
use crate::core::Color;
|
||||
|
||||
pub const GAMMA_CORRECTION: bool = true;
|
||||
|
||||
pub fn pack(color: Color) -> [f32; 4] {
|
||||
color.into_linear()
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(feature = "web-colors")]
|
||||
mod internal {
|
||||
use crate::core::Color;
|
||||
|
||||
pub const GAMMA_CORRECTION: bool = false;
|
||||
|
||||
pub fn pack(color: Color) -> [f32; 4] {
|
||||
[color.r, color.g, color.b, color.a]
|
||||
}
|
||||
}
|
||||
|
|
@ -3,8 +3,10 @@
|
|||
//! For a gradient that you can use as a background variant for a widget, see [`Gradient`].
|
||||
//!
|
||||
//! [`Gradient`]: crate::core::Gradient;
|
||||
use crate::color;
|
||||
use crate::core::gradient::ColorStop;
|
||||
use crate::core::{self, Color, Point, Rectangle};
|
||||
|
||||
use std::cmp::Ordering;
|
||||
|
||||
#[derive(Debug, Clone, PartialEq)]
|
||||
|
|
@ -101,7 +103,8 @@ impl Linear {
|
|||
|
||||
for (index, stop) in self.stops.iter().enumerate() {
|
||||
let [r, g, b, a] =
|
||||
stop.map_or(Color::default(), |s| s.color).into_linear();
|
||||
color::pack(stop.map_or(Color::default(), |s| s.color))
|
||||
.components();
|
||||
|
||||
data[index * 4] = r;
|
||||
data[(index * 4) + 1] = g;
|
||||
|
|
@ -133,7 +136,8 @@ pub fn pack(gradient: &core::Gradient, bounds: Rectangle) -> Packed {
|
|||
|
||||
for (index, stop) in linear.stops.iter().enumerate() {
|
||||
let [r, g, b, a] =
|
||||
stop.map_or(Color::default(), |s| s.color).into_linear();
|
||||
color::pack(stop.map_or(Color::default(), |s| s.color))
|
||||
.components();
|
||||
|
||||
data[index * 4] = r;
|
||||
data[(index * 4) + 1] = g;
|
||||
|
|
|
|||
|
|
@ -27,6 +27,7 @@ mod transformation;
|
|||
mod viewport;
|
||||
|
||||
pub mod backend;
|
||||
pub mod color;
|
||||
pub mod compositor;
|
||||
pub mod damage;
|
||||
pub mod gradient;
|
||||
|
|
|
|||
|
|
@ -1,4 +1,5 @@
|
|||
//! Draw using different graphical primitives.
|
||||
use crate::color;
|
||||
use crate::core::alignment;
|
||||
use crate::core::image;
|
||||
use crate::core::svg;
|
||||
|
|
@ -248,7 +249,7 @@ pub struct ColoredVertex2D {
|
|||
pub position: [f32; 2],
|
||||
|
||||
/// The color of the vertex in __linear__ RGBA.
|
||||
pub color: [f32; 4],
|
||||
pub color: color::Packed,
|
||||
}
|
||||
|
||||
/// A vertex which contains 2D position & packed gradient data.
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue