1use zencodec::{GainMapParams, Metadata, MetadataPolicy};
6
7#[derive(Debug)]
9#[non_exhaustive]
10pub enum Error {
11 GainMap(zencodec::gainmap::GainMapParseError),
13 Removed(&'static str),
15}
16impl core::fmt::Display for Error {
17 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
18 match self {
19 Self::GainMap(e) => write!(f, "invalid gain map: {e}"),
20 Self::Removed(field) => {
21 write!(f, "retention would remove display information: {field}")
22 }
23 }
24 }
25}
26impl core::error::Error for Error {
27 fn source(&self) -> Option<&(dyn core::error::Error + 'static)> {
28 match self {
29 Self::GainMap(e) => Some(e),
30 _ => None,
31 }
32 }
33}
34pub fn filter_for_gain_map(
42 meta: &Metadata,
43 params: &GainMapParams,
44 policy: &MetadataPolicy,
45) -> Result<Metadata, Error> {
46 params.validate().map_err(Error::GainMap)?;
47 let out = crate::metadata::filter(meta, policy);
48 if out.orientation != meta.orientation {
49 return Err(Error::Removed("orientation"));
50 }
51 if out.cicp != meta.cicp {
52 return Err(Error::Removed("CICP"));
53 }
54 if out.content_light_level != meta.content_light_level
55 || out.mastering_display != meta.mastering_display
56 || out.diffuse_white != meta.diffuse_white
57 {
58 return Err(Error::Removed("HDR luminance"));
59 }
60 if meta.icc_profile.is_some()
61 && out.icc_profile.is_none()
62 && !meta
63 .icc_profile
64 .as_ref()
65 .is_some_and(|icc| zenpixels::icc::is_common_srgb(icc))
66 {
67 return Err(Error::Removed("ICC profile"));
68 }
69 Ok(out)
70}