hayro_syntax/filter/
mod.rs1mod ascii_85;
4pub(crate) mod ascii_hex;
5mod ccitt;
6mod dct;
7mod jbig2;
8mod jpx;
9mod lzw_flate;
10mod run_length;
11
12use crate::object::Dict;
13use crate::object::Name;
14use crate::object::dict::keys::*;
15use crate::object::stream::{DecodeFailure, FilterResult, ImageDecodeParams};
16use log::warn;
17use std::ops::Deref;
18
19#[derive(Debug, Copy, Clone, PartialEq, Eq)]
21pub enum Filter {
22 AsciiHexDecode,
24 Ascii85Decode,
26 LzwDecode,
28 FlateDecode,
30 RunLengthDecode,
32 CcittFaxDecode,
34 Jbig2Decode,
36 DctDecode,
38 JpxDecode,
40 Crypt,
42}
43
44impl Filter {
45 fn debug_name(&self) -> &'static str {
46 match self {
47 Self::AsciiHexDecode => "ascii_hex",
48 Self::Ascii85Decode => "ascii_85",
49 Self::LzwDecode => "lzw",
50 Self::FlateDecode => "flate",
51 Self::RunLengthDecode => "run-length",
52 Self::CcittFaxDecode => "ccit_fax",
53 Self::Jbig2Decode => "jbig2",
54 Self::DctDecode => "dct",
55 Self::JpxDecode => "jpx",
56 Self::Crypt => "crypt",
57 }
58 }
59
60 pub(crate) fn from_name(name: Name<'_>) -> Option<Self> {
61 match name.deref() {
62 ASCII_HEX_DECODE | ASCII_HEX_DECODE_ABBREVIATION => Some(Self::AsciiHexDecode),
63 ASCII85_DECODE | ASCII85_DECODE_ABBREVIATION => Some(Self::Ascii85Decode),
64 LZW_DECODE | LZW_DECODE_ABBREVIATION => Some(Self::LzwDecode),
65 FLATE_DECODE | FLATE_DECODE_ABBREVIATION => Some(Self::FlateDecode),
66 RUN_LENGTH_DECODE | RUN_LENGTH_DECODE_ABBREVIATION => Some(Self::RunLengthDecode),
67 CCITTFAX_DECODE | CCITTFAX_DECODE_ABBREVIATION => Some(Self::CcittFaxDecode),
68 JBIG2_DECODE => Some(Self::Jbig2Decode),
69 DCT_DECODE | DCT_DECODE_ABBREVIATION => Some(Self::DctDecode),
70 JPX_DECODE => Some(Self::JpxDecode),
71 CRYPT => Some(Self::Crypt),
72 _ => {
73 warn!("unknown filter: {}", name.as_str());
74
75 None
76 }
77 }
78 }
79
80 pub(crate) fn apply(
81 &self,
82 data: &[u8],
83 params: Dict<'_>,
84 image_params: &ImageDecodeParams,
85 ) -> Result<FilterResult, DecodeFailure> {
86 let res = match self {
87 Self::AsciiHexDecode => ascii_hex::decode(data)
88 .map(FilterResult::from_data)
89 .ok_or(DecodeFailure::StreamDecode),
90 Self::Ascii85Decode => ascii_85::decode(data)
91 .map(FilterResult::from_data)
92 .ok_or(DecodeFailure::StreamDecode),
93 Self::RunLengthDecode => run_length::decode(data)
94 .map(FilterResult::from_data)
95 .ok_or(DecodeFailure::StreamDecode),
96 Self::LzwDecode => lzw_flate::lzw::decode(data, params)
97 .map(FilterResult::from_data)
98 .ok_or(DecodeFailure::StreamDecode),
99 Self::DctDecode => {
100 dct::decode(data, params, image_params).ok_or(DecodeFailure::ImageDecode)
101 }
102 Self::FlateDecode => lzw_flate::flate::decode(data, params)
103 .map(FilterResult::from_data)
104 .ok_or(DecodeFailure::StreamDecode),
105 Self::CcittFaxDecode => {
106 ccitt::decode(data, params, image_params).ok_or(DecodeFailure::ImageDecode)
107 }
108 Self::Jbig2Decode => Ok(FilterResult::from_data(
109 jbig2::decode(data, params).ok_or(DecodeFailure::ImageDecode)?,
110 )),
111 Self::JpxDecode => jpx::decode(data, image_params).ok_or(DecodeFailure::ImageDecode),
112 _ => Err(DecodeFailure::StreamDecode),
113 };
114
115 if res.is_err() {
116 warn!("failed to apply filter {}", self.debug_name());
117 }
118
119 res
120 }
121}