Skip to content

Commit 87ef7b2

Browse files
burbokopkornelski
authored andcommitted
GrayAlpha44 type added
1 parent 4a67b55 commit 87ef7b2

File tree

3 files changed

+89
-1
lines changed

3 files changed

+89
-1
lines changed

src/bytemuck_impl.rs

Lines changed: 45 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
use crate::{Abgr, Argb, Bgr, Bgra, GrayA, Gray_v09, Grb, Rgb, Rgba, Rgbw};
1+
use crate::{Abgr, Argb, Bgr, Bgra, GrayA, GrayAlpha44, Gray_v09, Grb, Rgb, Rgba, Rgbw};
22

33
macro_rules! bytemuck {
44
($name:ident) => {
@@ -7,6 +7,13 @@ macro_rules! bytemuck {
77
};
88
}
99

10+
macro_rules! bytemuck_no_generic {
11+
($name:ident) => {
12+
unsafe impl ::bytemuck::Zeroable for $name {}
13+
unsafe impl ::bytemuck::Pod for $name {}
14+
};
15+
}
16+
1017
bytemuck!(Rgb);
1118
bytemuck!(Bgr);
1219
bytemuck!(Grb);
@@ -17,6 +24,7 @@ bytemuck!(Argb);
1724
bytemuck!(Bgra);
1825
bytemuck!(Abgr);
1926
bytemuck!(GrayA);
27+
bytemuck_no_generic!(GrayAlpha44);
2028

2129
use crate::formats::gray_alpha::GrayAlpha_v08;
2230
bytemuck!(GrayAlpha_v08);
@@ -39,6 +47,21 @@ impl<T: ::bytemuck::Pod> crate::ComponentBytes<T> for [Gray_v08<T>] {
3947
}
4048
}
4149

50+
#[cfg(feature = "as-bytes")]
51+
impl<T: ::bytemuck::Pod> crate::ComponentBytes<T> for [Gray_v09<T>] {
52+
#[inline]
53+
fn as_bytes(&self) -> &[u8] {
54+
assert_ne!(0, core::mem::size_of::<T>());
55+
::bytemuck::cast_slice(self)
56+
}
57+
58+
#[inline]
59+
fn as_bytes_mut(&mut self) -> &mut [u8] {
60+
assert_ne!(0, core::mem::size_of::<T>());
61+
::bytemuck::cast_slice_mut(self)
62+
}
63+
}
64+
4265
#[cfg(feature = "as-bytes")]
4366
impl<T: ::bytemuck::Pod> crate::ComponentBytes<T> for [GrayAlpha_v08<T>] {
4467
#[inline]
@@ -53,3 +76,24 @@ impl<T: ::bytemuck::Pod> crate::ComponentBytes<T> for [GrayAlpha_v08<T>] {
5376
::bytemuck::cast_slice_mut(self)
5477
}
5578
}
79+
80+
#[cfg(feature = "as-bytes")]
81+
impl crate::ComponentBytes<u8> for [GrayAlpha44] {
82+
#[inline]
83+
fn as_bytes(&self) -> &[u8] {
84+
::bytemuck::cast_slice(self)
85+
}
86+
87+
#[inline]
88+
fn as_bytes_mut(&mut self) -> &mut [u8] {
89+
::bytemuck::cast_slice_mut(self)
90+
}
91+
}
92+
93+
#[test]
94+
fn test_component_bytes_capable() {
95+
assert_eq!(
96+
core::mem::size_of::<GrayAlpha44>(),
97+
core::mem::size_of::<u8>()
98+
);
99+
}

src/formats/gray_alpha44.rs

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
#[repr(C)]
2+
#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
3+
#[cfg_attr(feature = "defmt-03", derive(defmt::Format))]
4+
#[derive(Copy, Clone, Debug, Default, Eq, PartialEq, Ord, PartialOrd, Hash)]
5+
/// A pixel for grayscale value (4 bit) + alpha components (4 bit). in total 8 bit
6+
pub struct GrayAlpha44(pub(crate) u8);
7+
8+
impl GrayAlpha44 {
9+
/// Convert 16 bit gray+alpha into 8 bit gray+alpha with precision loss
10+
/// Example:
11+
/// ```
12+
/// use rgb::GrayAlpha44;
13+
/// let g = GrayAlpha44::new(120, 20);
14+
/// assert_eq!(112, g.v()); // due to loss of precision you got 112 instead of initial 120
15+
/// assert_eq!(16, g.a()); // due to loss of precision you got 16 instead of initial 20
16+
/// ```
17+
#[inline]
18+
pub fn new(v: u8, a: u8) -> Self {
19+
Self((v & 0xf0) | (a >> 4))
20+
}
21+
22+
#[inline]
23+
pub fn v(self) -> u8 {
24+
self.0 & 0xf0
25+
}
26+
27+
#[inline]
28+
pub fn a(self) -> u8 {
29+
self.0 << 4
30+
}
31+
}
32+
33+
#[test]
34+
fn zero() {
35+
let g = GrayAlpha44::new(0, 0);
36+
assert_eq!(0, g.v());
37+
assert_eq!(0, g.a());
38+
assert_eq!(0, g.0);
39+
}

src/lib.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
#![cfg_attr(docsrs, feature(doc_auto_cfg))]
55
#![no_std]
66

7+
#[cfg(test)]
78
#[macro_use]
89
extern crate std;
910

@@ -15,6 +16,7 @@ mod formats {
1516
pub mod gray;
1617
pub mod gray_a;
1718
pub mod gray_alpha;
19+
pub mod gray_alpha44;
1820
pub mod grb;
1921
pub mod rgb;
2022
pub mod rgba;
@@ -68,6 +70,7 @@ pub use formats::gray::Gray_v08 as Gray;
6870
pub use formats::gray::Gray_v09;
6971
pub use formats::gray_a::GrayA;
7072
pub use formats::gray_alpha::GrayAlpha_v08 as GrayAlpha;
73+
pub use formats::gray_alpha44::GrayAlpha44;
7174
pub use formats::grb::Grb;
7275
pub use formats::rgb::Rgb;
7376
pub use formats::rgba::Rgba;
@@ -111,6 +114,8 @@ pub type BGR8 = formats::bgr::Bgr<u8>;
111114
pub type BGRA8 = formats::bgra::Bgra<u8>;
112115
/// [`Gray<u8>`]
113116
pub type GRAY8 = formats::gray::Gray_v09<u8>;
117+
/// 4 bit for gray and 4 bit for alpha
118+
pub type GRAYA4 = formats::gray_alpha44::GrayAlpha44;
114119
/// [`GrayA<u8>`]
115120
pub type GRAYA8 = formats::gray_a::GrayA<u8>;
116121
/// [`Grb<u8>`]

0 commit comments

Comments
 (0)