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

Implement bytemuck::Zeroable and bytemuck::Pod for every color type #229

Merged
merged 4 commits into from May 29, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
4 changes: 4 additions & 0 deletions palette/Cargo.toml
Expand Up @@ -48,6 +48,10 @@ version = "1"
features = ["serde_derive"]
optional = true

[dependencies.bytemuck]
version = "1"
optional = true

[dev-dependencies]
csv = "1"
lazy_static = "1"
Expand Down
21 changes: 21 additions & 0 deletions palette/src/alpha/alpha.rs
Expand Up @@ -583,6 +583,27 @@ where
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<C, T> bytemuck::Zeroable for Alpha<C, T>
where
C: bytemuck::Zeroable,
T: bytemuck::Zeroable,
{
}

// Safety:
// It is a requirement of `Pixel<T>` that the in-memory representation of
// `C` is made of `T`s.
// Because `T` is `Pod`, `Alpha<C, T>` is `Pod` as well because no internal
// padding can be introduced during monomorphization.
#[cfg(feature = "bytemuck")]
unsafe impl<C, T> bytemuck::Pod for Alpha<C, T>
where
T: bytemuck::Pod,
C: bytemuck::Pod + Pixel<T>,
{
}

#[cfg(test)]
mod test {
use crate::encoding::Srgb;
Expand Down
18 changes: 18 additions & 0 deletions palette/src/blend/pre_alpha.rs
Expand Up @@ -389,6 +389,24 @@ impl<C, T: Float> DerefMut for PreAlpha<C, T> {
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<C, T> bytemuck::Zeroable for PreAlpha<C, T>
where
C: bytemuck::Zeroable,
T: Float + bytemuck::Zeroable,
{
}

// Safety:
// See `Alpha<C, T>`'s implementation of `Pod`.
#[cfg(feature = "bytemuck")]
unsafe impl<C, T> bytemuck::Pod for PreAlpha<C, T>
where
C: bytemuck::Pod + Pixel<T>,
T: Float + bytemuck::Pod,
{
}

#[cfg(test)]
#[cfg(feature = "serializing")]
mod test {
Expand Down
16 changes: 16 additions & 0 deletions palette/src/hsl.rs
Expand Up @@ -811,6 +811,22 @@ where
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<S, T> bytemuck::Zeroable for Hsl<S, T>
where
S: RgbStandard,
T: FloatComponent + bytemuck::Zeroable,
{
}

#[cfg(feature = "bytemuck")]
unsafe impl<S, T> bytemuck::Pod for Hsl<S, T>
where
S: RgbStandard,
T: FloatComponent + bytemuck::Pod,
{
}

#[cfg(test)]
mod test {
use super::Hsl;
Expand Down
16 changes: 16 additions & 0 deletions palette/src/hsluv.rs
Expand Up @@ -553,6 +553,22 @@ where
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<Wp, T> bytemuck::Zeroable for Hsluv<Wp, T>
where
Wp: WhitePoint,
T: FloatComponent + bytemuck::Zeroable,
{
}

#[cfg(feature = "bytemuck")]
unsafe impl<Wp, T> bytemuck::Pod for Hsluv<Wp, T>
where
Wp: WhitePoint,
T: FloatComponent + bytemuck::Pod,
{
}

#[cfg(test)]
mod test {
use super::Hsluv;
Expand Down
16 changes: 16 additions & 0 deletions palette/src/hsv.rs
Expand Up @@ -825,6 +825,22 @@ where
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<S, T> bytemuck::Zeroable for Hsv<S, T>
where
S: RgbStandard,
T: FloatComponent + bytemuck::Zeroable,
{
}

#[cfg(feature = "bytemuck")]
unsafe impl<S, T> bytemuck::Pod for Hsv<S, T>
where
S: RgbStandard,
T: FloatComponent + bytemuck::Pod,
{
}

#[cfg(test)]
mod test {
use super::Hsv;
Expand Down
5 changes: 5 additions & 0 deletions palette/src/hues.rs
Expand Up @@ -259,6 +259,11 @@ macro_rules! make_hues {
$name(rng.gen() * from_f64(360.0))
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<T: Float + bytemuck::Zeroable> bytemuck::Zeroable for $name<T> {}
#[cfg(feature = "bytemuck")]
unsafe impl<T: Float + bytemuck::Pod> bytemuck::Pod for $name<T> {}
)+)
}

Expand Down
16 changes: 16 additions & 0 deletions palette/src/hwb.rs
Expand Up @@ -764,6 +764,22 @@ where
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<S, T> bytemuck::Zeroable for Hwb<S, T>
where
S: RgbStandard,
T: FloatComponent + bytemuck::Zeroable,
{
}

#[cfg(feature = "bytemuck")]
unsafe impl<S, T> bytemuck::Pod for Hwb<S, T>
where
S: RgbStandard,
T: FloatComponent + bytemuck::Pod,
{
}

#[cfg(test)]
mod test {
use super::Hwb;
Expand Down
16 changes: 16 additions & 0 deletions palette/src/lab.rs
Expand Up @@ -814,6 +814,22 @@ where
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<Wp, T> bytemuck::Zeroable for Lab<Wp, T>
where
Wp: WhitePoint,
T: FloatComponent + bytemuck::Zeroable,
{
}

#[cfg(feature = "bytemuck")]
unsafe impl<Wp, T> bytemuck::Pod for Lab<Wp, T>
where
Wp: WhitePoint,
T: FloatComponent + bytemuck::Pod,
{
}

#[cfg(test)]
mod test {
use super::Lab;
Expand Down
16 changes: 16 additions & 0 deletions palette/src/lch.rs
Expand Up @@ -722,6 +722,22 @@ where
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<Wp, T> bytemuck::Zeroable for Lch<Wp, T>
where
Wp: WhitePoint,
T: FloatComponent + bytemuck::Zeroable,
{
}

#[cfg(feature = "bytemuck")]
unsafe impl<Wp, T> bytemuck::Pod for Lch<Wp, T>
where
Wp: WhitePoint,
T: FloatComponent + bytemuck::Pod,
{
}

#[cfg(test)]
mod test {
use crate::white_point::D65;
Expand Down
16 changes: 16 additions & 0 deletions palette/src/lchuv.rs
Expand Up @@ -563,6 +563,22 @@ where
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<Wp, T> bytemuck::Zeroable for Lchuv<Wp, T>
where
Wp: WhitePoint,
T: FloatComponent + bytemuck::Zeroable,
{
}

#[cfg(feature = "bytemuck")]
unsafe impl<Wp, T> bytemuck::Pod for Lchuv<Wp, T>
where
Wp: WhitePoint,
T: FloatComponent + bytemuck::Pod,
{
}

#[cfg(test)]
mod test {
use crate::white_point::D65;
Expand Down
16 changes: 16 additions & 0 deletions palette/src/luma/luma.rs
Expand Up @@ -876,6 +876,22 @@ where
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<S, T> bytemuck::Zeroable for Luma<S, T>
where
S: LumaStandard,
T: Component + bytemuck::Zeroable,
{
}

#[cfg(feature = "bytemuck")]
unsafe impl<S, T> bytemuck::Pod for Luma<S, T>
where
S: LumaStandard,
T: Component + bytemuck::Pod,
{
}

#[cfg(test)]
mod test {
use crate::encoding::Srgb;
Expand Down
16 changes: 16 additions & 0 deletions palette/src/luv.rs
Expand Up @@ -674,6 +674,22 @@ where
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<Wp, T> bytemuck::Zeroable for Luv<Wp, T>
where
Wp: WhitePoint,
T: FloatComponent + bytemuck::Zeroable,
{
}

#[cfg(feature = "bytemuck")]
unsafe impl<Wp, T> bytemuck::Pod for Luv<Wp, T>
where
Wp: WhitePoint,
T: FloatComponent + bytemuck::Pod,
{
}

#[cfg(test)]
mod test {
use super::Luv;
Expand Down
15 changes: 14 additions & 1 deletion palette/src/rgb/packed.rs
Expand Up @@ -58,7 +58,7 @@ use crate::Pixel;
/// assert_eq!(colors[0].color, 0x7F0080);
/// assert_eq!(colors[1].color, 0x60BBCC);
/// ```
#[derive(Copy, Clone, Debug, PartialEq, Eq, Pixel)]
#[derive(Debug, PartialEq, Eq, Pixel)]
#[palette(palette_internal)]
#[repr(C)]
pub struct Packed<C = channels::Argb> {
Expand All @@ -72,6 +72,14 @@ pub struct Packed<C = channels::Argb> {
pub channel_order: PhantomData<C>,
}

impl<C> Copy for Packed<C> {}

impl<C> Clone for Packed<C> {
fn clone(&self) -> Self {
*self
}
}

/// Splits and combines RGB(A) types with some channel ordering. Channels may be
/// ordered as `Abgr`, `Argb`, `Bgra`, or `Rgba`.
pub trait RgbChannels {
Expand Down Expand Up @@ -159,6 +167,11 @@ where
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<C> bytemuck::Zeroable for Packed<C> {}
#[cfg(feature = "bytemuck")]
unsafe impl<C: 'static> bytemuck::Pod for Packed<C> {}

#[cfg(test)]
mod test {
use crate::rgb::packed::channels::{Abgr, Argb, Bgra, Rgba};
Expand Down
16 changes: 16 additions & 0 deletions palette/src/rgb/rgb.rs
Expand Up @@ -1236,6 +1236,22 @@ where
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<S, T> bytemuck::Zeroable for Rgb<S, T>
where
S: RgbStandard,
T: Component + bytemuck::Zeroable,
{
}

#[cfg(feature = "bytemuck")]
unsafe impl<S, T> bytemuck::Pod for Rgb<S, T>
where
S: RgbStandard,
T: Component + bytemuck::Pod,
{
}

#[cfg(test)]
mod test {
use core::str::FromStr;
Expand Down
16 changes: 16 additions & 0 deletions palette/src/xyz.rs
Expand Up @@ -824,6 +824,22 @@ where
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<Wp, T> bytemuck::Zeroable for Xyz<Wp, T>
where
Wp: WhitePoint,
T: FloatComponent + bytemuck::Zeroable,
{
}

#[cfg(feature = "bytemuck")]
unsafe impl<Wp, T> bytemuck::Pod for Xyz<Wp, T>
where
Wp: WhitePoint,
T: FloatComponent + bytemuck::Pod,
{
}

#[cfg(test)]
mod test {
use super::Xyz;
Expand Down
16 changes: 16 additions & 0 deletions palette/src/yxy.rs
Expand Up @@ -752,6 +752,22 @@ where
}
}

#[cfg(feature = "bytemuck")]
unsafe impl<Wp, T> bytemuck::Zeroable for Yxy<Wp, T>
where
Wp: WhitePoint,
T: FloatComponent + bytemuck::Zeroable,
{
}

#[cfg(feature = "bytemuck")]
unsafe impl<Wp, T> bytemuck::Pod for Yxy<Wp, T>
where
Wp: WhitePoint,
T: FloatComponent + bytemuck::Pod,
{
}

#[cfg(test)]
mod test {
use super::Yxy;
Expand Down