Skip to content

Commit 4b17a15

Browse files
authored
Merge pull request #373 from Ogeon/alloc_and_any_features_in_tests
Add an "alloc" feature and make tests work with any feature combination
2 parents 919049c + 6d96f73 commit 4b17a15

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

54 files changed

+1526
-1299
lines changed

.github/workflows/ci.yml

+7-3
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ jobs:
2424
- uses: dtolnay/rust-toolchain@1.60.0
2525
with:
2626
components: clippy
27+
- uses: taiki-e/install-action@cargo-hack
2728
- name: Minimal check
2829
run: cargo clippy -v -p palette --no-default-features --features std
2930
- name: find-crate check
@@ -33,9 +34,7 @@ jobs:
3334
- name: Test all features
3435
run: cargo test -v -p palette --all-features
3536
- name: Test each feature
36-
shell: bash
37-
working-directory: palette
38-
run: bash ../scripts/test_features.sh
37+
run: cargo hack test --tests --feature-powerset --ignore-private --skip default,find-crate --optional-deps libm --depth 2
3938
integration_tests:
4039
name: integration tests
4140
strategy:
@@ -63,8 +62,13 @@ jobs:
6362
with:
6463
toolchain: ${{ matrix.toolchain }}
6564
components: clippy
65+
- uses: taiki-e/install-action@cargo-hack
6666
- name: Check all features
6767
run: cargo clippy -v -p palette --all-features
68+
- name: Check each feature with libm
69+
run: cargo hack clippy --each-feature --ignore-private --features libm --skip default,find-crate --ignore-unknown-features
70+
- name: Check each feature with std
71+
run: cargo hack clippy --each-feature --ignore-private --features std --skip default,find-crate --optional-deps libm --ignore-unknown-features
6872
no_std:
6973
name: "Test #[no_std]"
7074
runs-on: ubuntu-latest

benchmarks/Cargo.toml

+1
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ description = "Benchmark crate for palette."
77
repository = "https://github.com/Ogeon/palette"
88
license = "MIT OR Apache-2.0"
99
edition = "2018"
10+
publish = false
1011

1112
[[bench]]
1213
path = "benches/cie.rs"

integration_tests/Cargo.toml

+1
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ description = "Integration test crate for palette."
77
repository = "https://github.com/Ogeon/palette"
88
license = "MIT OR Apache-2.0"
99
edition = "2018"
10+
publish = false
1011

1112
[[example]]
1213
name = "issue_283"

no_std_test/Cargo.toml

+1
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ description = "Test crate for #[no_std]."
77
repository = "https://github.com/Ogeon/palette"
88
license = "MIT OR Apache-2.0"
99
edition = "2018"
10+
publish = false
1011

1112
[[bin]]
1213
name = "no_std_test"

palette/Cargo.toml

+2-2
Original file line numberDiff line numberDiff line change
@@ -33,9 +33,9 @@ named_from_str = ["named", "phf"]
3333
named = []
3434
random = ["rand"]
3535
serializing = ["serde", "std"]
36-
#ignore in feature test
3736
find-crate = ["palette_derive/find-crate"]
38-
std = ["approx?/std"]
37+
std = ["alloc", "approx?/std"]
38+
alloc = []
3939

4040
[lib]
4141
bench = false

palette/README.md

+3-2
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,8 @@ These features are enabled by default:
4141

4242
* `"named"` - Enables color constants, located in the `named` module.
4343
* `"named_from_str"` - Enables `named::from_str`, which maps name strings to colors.
44-
* `"std"` - Enables use of the standard library.
44+
* `"std"` - Enables use of the standard library. Also enables `"alloc"`.
45+
* `"alloc"` - Enables implementations for allocating types, such as `Vec` or `Box`.
4546
* `"approx"` - Enables approximate comparison using [`approx`].
4647

4748
These features are disabled by default:
@@ -55,7 +56,7 @@ These features are disabled by default:
5556

5657
### Using palette in an embedded environment
5758

58-
Palette supports `#![no_std]` environments by disabling the `"std"` feature. It uses [`libm`] to provide the floating-point operations that are typically in `std`. However, serializing with `serde` is not available without the standard library.
59+
Palette supports `#![no_std]` environments by disabling the `"std"` feature. It uses [`libm`], via the `"libm"` feature, to provide the floating-point operations that are typically in `std`, and the `"alloc"` feature to provide features that use allocating types. However, serializing with `serde` is not available without the standard library.
5960

6061
## Examples
6162

palette/src/alpha/alpha.rs

+2-2
Original file line numberDiff line numberDiff line change
@@ -1240,8 +1240,8 @@ mod test {
12401240

12411241
#[test]
12421242
fn check_min_max_components() {
1243-
assert_relative_eq!(Rgba::<Srgb>::min_alpha(), 0.0);
1244-
assert_relative_eq!(Rgba::<Srgb>::max_alpha(), 1.0);
1243+
assert_eq!(Rgba::<Srgb>::min_alpha(), 0.0);
1244+
assert_eq!(Rgba::<Srgb>::max_alpha(), 1.0);
12451245
}
12461246

12471247
#[cfg(feature = "serializing")]

palette/src/blend/test.rs

+2
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
#![cfg(feature = "approx")]
2+
13
use crate::{
24
blend::{Blend, BlendWith, Compose},
35
LinSrgb, LinSrgba,

palette/src/cast/array.rs

+30-24
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
use core::mem::{transmute_copy, ManuallyDrop};
22

3+
#[cfg(feature = "alloc")]
4+
use alloc::{boxed::Box, vec::Vec};
5+
36
pub use palette_derive::ArrayCast;
47

58
use crate::ArrayExt;
@@ -958,7 +961,7 @@ where
958961
/// let color2 = Box::new(Srgb::new(23u8, 198, 76));
959962
/// let array2 = <Box<[_; 3]>>::from(color2);
960963
/// ```
961-
#[cfg(feature = "std")]
964+
#[cfg(feature = "alloc")]
962965
#[inline]
963966
pub fn into_array_box<T>(value: Box<T>) -> Box<T::Array>
964967
where
@@ -1000,7 +1003,7 @@ where
10001003
/// let array2 = Box::new([23, 198, 76]);
10011004
/// let color2 = <Box<Srgb<u8>>>::from(array2);
10021005
/// ```
1003-
#[cfg(feature = "std")]
1006+
#[cfg(feature = "alloc")]
10041007
#[inline]
10051008
pub fn from_array_box<T>(value: Box<T::Array>) -> Box<T>
10061009
where
@@ -1030,7 +1033,7 @@ where
10301033
/// vec![[64, 139, 10], [93, 18, 214]].into_boxed_slice()
10311034
/// )
10321035
/// ```
1033-
#[cfg(feature = "std")]
1036+
#[cfg(feature = "alloc")]
10341037
#[inline]
10351038
pub fn into_array_slice_box<T>(values: Box<[T]>) -> Box<[T::Array]>
10361039
where
@@ -1053,7 +1056,7 @@ where
10531056
/// vec![64, 139, 10, 93, 18, 214].into_boxed_slice()
10541057
/// )
10551058
/// ```
1056-
#[cfg(feature = "std")]
1059+
#[cfg(feature = "alloc")]
10571060
#[inline]
10581061
pub fn into_component_slice_box<T>(values: Box<[T]>) -> Box<[<T::Array as ArrayExt>::Item]>
10591062
where
@@ -1076,7 +1079,7 @@ where
10761079
/// vec![Srgb::new(64u8, 139, 10), Srgb::new(93, 18, 214)].into_boxed_slice()
10771080
/// )
10781081
/// ```
1079-
#[cfg(feature = "std")]
1082+
#[cfg(feature = "alloc")]
10801083
#[inline]
10811084
pub fn from_array_slice_box<T>(values: Box<[T::Array]>) -> Box<[T]>
10821085
where
@@ -1116,7 +1119,7 @@ where
11161119
/// let components = vec![64, 139, 10, 93, 18, 214, 0, 123].into_boxed_slice();
11171120
/// cast::from_component_slice_box::<Srgb<u8>>(components);
11181121
/// ```
1119-
#[cfg(feature = "std")]
1122+
#[cfg(feature = "alloc")]
11201123
#[inline]
11211124
pub fn from_component_slice_box<T>(values: Box<[<T::Array as ArrayExt>::Item]>) -> Box<[T]>
11221125
where
@@ -1162,7 +1165,7 @@ where
11621165
/// unreachable!();
11631166
/// }
11641167
/// ```
1165-
#[cfg(feature = "std")]
1168+
#[cfg(feature = "alloc")]
11661169
#[inline]
11671170
pub fn try_from_component_slice_box<T>(
11681171
values: Box<[<T::Array as ArrayExt>::Item]>,
@@ -1191,7 +1194,7 @@ where
11911194
/// vec![[64, 139, 10], [93, 18, 214]]
11921195
/// )
11931196
/// ```
1194-
#[cfg(feature = "std")]
1197+
#[cfg(feature = "alloc")]
11951198
#[inline]
11961199
pub fn into_array_vec<T>(values: Vec<T>) -> Vec<T::Array>
11971200
where
@@ -1223,7 +1226,7 @@ where
12231226
/// vec![64, 139, 10, 93, 18, 214]
12241227
/// )
12251228
/// ```
1226-
#[cfg(feature = "std")]
1229+
#[cfg(feature = "alloc")]
12271230
#[inline]
12281231
pub fn into_component_vec<T>(values: Vec<T>) -> Vec<<T::Array as ArrayExt>::Item>
12291232
where
@@ -1257,7 +1260,7 @@ where
12571260
/// vec![Srgb::new(64u8, 139, 10), Srgb::new(93, 18, 214)]
12581261
/// )
12591262
/// ```
1260-
#[cfg(feature = "std")]
1263+
#[cfg(feature = "alloc")]
12611264
#[inline]
12621265
pub fn from_array_vec<T>(values: Vec<T::Array>) -> Vec<T>
12631266
where
@@ -1316,7 +1319,7 @@ where
13161319
/// components.reserve_exact(2); // Not a multiple of 3
13171320
/// cast::from_component_vec::<Srgb<u8>>(components);
13181321
/// ```
1319-
#[cfg(feature = "std")]
1322+
#[cfg(feature = "alloc")]
13201323
#[inline]
13211324
pub fn from_component_vec<T>(values: Vec<<T::Array as ArrayExt>::Item>) -> Vec<T>
13221325
where
@@ -1376,7 +1379,7 @@ where
13761379
/// unreachable!();
13771380
/// }
13781381
/// ```
1379-
#[cfg(feature = "std")]
1382+
#[cfg(feature = "alloc")]
13801383
#[inline]
13811384
pub fn try_from_component_vec<T>(
13821385
values: Vec<<T::Array as ArrayExt>::Item>,
@@ -1419,7 +1422,7 @@ where
14191422
/// Map values of color A to values of color B without creating a new `Vec`.
14201423
///
14211424
/// This uses the guarantees of [`ArrayCast`] to reuse the allocation.
1422-
#[cfg(feature = "std")]
1425+
#[cfg(feature = "alloc")]
14231426
#[inline]
14241427
pub fn map_vec_in_place<A, B, F>(values: Vec<A>, mut map: F) -> Vec<B>
14251428
where
@@ -1453,7 +1456,7 @@ where
14531456
/// Map values of color A to values of color B without creating a new `Box<[B]>`.
14541457
///
14551458
/// This uses the guarantees of [`ArrayCast`] to reuse the allocation.
1456-
#[cfg(feature = "std")]
1459+
#[cfg(feature = "alloc")]
14571460
#[inline]
14581461
pub fn map_slice_box_in_place<A, B, F>(values: Box<[A]>, mut map: F) -> Box<[B]>
14591462
where
@@ -1499,20 +1502,20 @@ impl std::error::Error for SliceCastError {}
14991502

15001503
/// The error type returned when casting a boxed slice of components fails.
15011504
#[derive(Clone, PartialEq, Eq)]
1502-
#[cfg(feature = "std")]
1505+
#[cfg(feature = "alloc")]
15031506
pub struct BoxedSliceCastError<T> {
15041507
/// The original values.
15051508
pub values: Box<[T]>,
15061509
}
15071510

1508-
#[cfg(feature = "std")]
1511+
#[cfg(feature = "alloc")]
15091512
impl<T> core::fmt::Debug for BoxedSliceCastError<T> {
15101513
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
15111514
f.debug_struct("BoxedSliceCastError").finish()
15121515
}
15131516
}
15141517

1515-
#[cfg(feature = "std")]
1518+
#[cfg(feature = "alloc")]
15161519
impl<T> core::fmt::Display for BoxedSliceCastError<T> {
15171520
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
15181521
f.write_str("could not convert boxed component slice to colors")
@@ -1524,7 +1527,7 @@ impl<T> std::error::Error for BoxedSliceCastError<T> {}
15241527

15251528
/// The error type returned when casting a `Vec` of components fails.
15261529
#[derive(Clone, PartialEq, Eq)]
1527-
#[cfg(feature = "std")]
1530+
#[cfg(feature = "alloc")]
15281531
pub struct VecCastError<T> {
15291532
/// The type of error that occurred.
15301533
pub kind: VecCastErrorKind,
@@ -1533,7 +1536,7 @@ pub struct VecCastError<T> {
15331536
pub values: Vec<T>,
15341537
}
15351538

1536-
#[cfg(feature = "std")]
1539+
#[cfg(feature = "alloc")]
15371540
impl<T> core::fmt::Debug for VecCastError<T> {
15381541
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
15391542
f.debug_struct("VecCastError")
@@ -1542,7 +1545,7 @@ impl<T> core::fmt::Debug for VecCastError<T> {
15421545
}
15431546
}
15441547

1545-
#[cfg(feature = "std")]
1548+
#[cfg(feature = "alloc")]
15461549
impl<T> core::fmt::Display for VecCastError<T> {
15471550
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
15481551
f.write_str("could not convert component vector to colors")
@@ -1554,7 +1557,7 @@ impl<T> std::error::Error for VecCastError<T> {}
15541557

15551558
/// The type of error that is returned when casting a `Vec` of components.
15561559
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
1557-
#[cfg(feature = "std")]
1560+
#[cfg(feature = "alloc")]
15581561
pub enum VecCastErrorKind {
15591562
/// The type of error returned when the length of a `Vec` didn't match the
15601563
/// requirements.
@@ -1567,9 +1570,10 @@ pub enum VecCastErrorKind {
15671570

15681571
#[cfg(test)]
15691572
mod test {
1573+
#[cfg(feature = "alloc")]
15701574
use crate::{LinSrgb, Srgb};
15711575

1572-
#[cfg(feature = "std")]
1576+
#[cfg(feature = "alloc")]
15731577
#[test]
15741578
fn array_vec_len_cap() {
15751579
let mut original = vec![
@@ -1596,11 +1600,12 @@ mod test {
15961600
assert_eq!(colors.capacity(), 8);
15971601
}
15981602

1603+
#[cfg(feature = "alloc")]
15991604
#[test]
16001605
fn map_vec_in_place() {
16011606
fn do_things(rgb: Srgb) -> LinSrgb {
16021607
let mut linear = rgb.into_linear();
1603-
std::mem::swap(&mut linear.red, &mut linear.blue);
1608+
core::mem::swap(&mut linear.red, &mut linear.blue);
16041609
linear
16051610
}
16061611

@@ -1615,11 +1620,12 @@ mod test {
16151620
)
16161621
}
16171622

1623+
#[cfg(feature = "alloc")]
16181624
#[test]
16191625
fn map_slice_box_in_place() {
16201626
fn do_things(rgb: Srgb) -> LinSrgb {
16211627
let mut linear = rgb.into_linear();
1622-
std::mem::swap(&mut linear.red, &mut linear.blue);
1628+
core::mem::swap(&mut linear.red, &mut linear.blue);
16231629
linear
16241630
}
16251631

palette/src/cast/as_arrays_traits.rs

+4-4
Original file line numberDiff line numberDiff line change
@@ -78,8 +78,8 @@ macro_rules! impl_as_arrays {
7878

7979
impl_as_arrays!([C], [C; M] where (const M: usize));
8080

81-
#[cfg(feature = "std")]
82-
impl_as_arrays!(Box<[C]>, Vec<C>);
81+
#[cfg(feature = "alloc")]
82+
impl_as_arrays!(alloc::boxed::Box<[C]>, alloc::vec::Vec<C>);
8383

8484
/// Trait for casting a reference to collection of arrays into a reference to
8585
/// collection of colors without copying.
@@ -167,8 +167,8 @@ macro_rules! impl_arrays_as {
167167

168168
impl_arrays_as!([[T; N]], [[T; N]; M] where (const M: usize));
169169

170-
#[cfg(feature = "std")]
171-
impl_arrays_as!(Box<[[T; N]]>, Vec<[T; N]>);
170+
#[cfg(feature = "alloc")]
171+
impl_arrays_as!(alloc::boxed::Box<[[T; N]]>, alloc::vec::Vec<[T; N]>);
172172

173173
#[cfg(test)]
174174
mod test {

palette/src/cast/as_components_traits.rs

+4-4
Original file line numberDiff line numberDiff line change
@@ -82,8 +82,8 @@ macro_rules! impl_as_components {
8282

8383
impl_as_components!([C], [C; M] where (const M: usize));
8484

85-
#[cfg(feature = "std")]
86-
impl_as_components!(Box<[C]>, Vec<C>);
85+
#[cfg(feature = "alloc")]
86+
impl_as_components!(alloc::boxed::Box<[C]>, alloc::vec::Vec<C>);
8787

8888
/// Trait for trying to cast a reference to collection of color components into
8989
/// a reference to collection of colors without copying.
@@ -221,8 +221,8 @@ macro_rules! impl_try_components_as {
221221

222222
impl_try_components_as!([T], [T; M] where (const M: usize));
223223

224-
#[cfg(feature = "std")]
225-
impl_try_components_as!(Box<[T]>, Vec<T>);
224+
#[cfg(feature = "alloc")]
225+
impl_try_components_as!(alloc::boxed::Box<[T]>, alloc::vec::Vec<T>);
226226

227227
/// Trait for casting a reference to collection of color components into a
228228
/// reference to collection of colors without copying.

0 commit comments

Comments
 (0)