82
82
tiff:: ColorType :: RGBA ( 8 ) => ColorType :: Rgba8 ,
83
83
tiff:: ColorType :: RGBA ( 16 ) => ColorType :: Rgba16 ,
84
84
tiff:: ColorType :: CMYK ( 8 ) => ColorType :: Rgb8 ,
85
+ tiff:: ColorType :: CMYK ( 16 ) => ColorType :: Rgb16 ,
85
86
tiff:: ColorType :: RGB ( 32 ) => ColorType :: Rgb32F ,
86
87
tiff:: ColorType :: RGBA ( 32 ) => ColorType :: Rgba32F ,
87
88
@@ -108,6 +109,7 @@ where
108
109
let original_color_type = match tiff_color_type {
109
110
tiff:: ColorType :: Gray ( 1 ) => ExtendedColorType :: L1 ,
110
111
tiff:: ColorType :: CMYK ( 8 ) => ExtendedColorType :: Cmyk8 ,
112
+ tiff:: ColorType :: CMYK ( 16 ) => ExtendedColorType :: Cmyk16 ,
111
113
_ => color_type. into ( ) ,
112
114
} ;
113
115
@@ -123,10 +125,11 @@ where
123
125
fn total_bytes_buffer ( & self ) -> u64 {
124
126
let dimensions = self . dimensions ( ) ;
125
127
let total_pixels = u64:: from ( dimensions. 0 ) * u64:: from ( dimensions. 1 ) ;
126
- let bytes_per_pixel = if self . original_color_type == ExtendedColorType :: Cmyk8 {
127
- 16
128
- } else {
129
- u64:: from ( self . color_type ( ) . bytes_per_pixel ( ) )
128
+
129
+ let bytes_per_pixel = match self . original_color_type {
130
+ ExtendedColorType :: Cmyk8 => 4 ,
131
+ ExtendedColorType :: Cmyk16 => 8 ,
132
+ _ => u64:: from ( self . color_type ( ) . bytes_per_pixel ( ) ) ,
130
133
} ;
131
134
total_pixels. saturating_mul ( bytes_per_pixel)
132
135
}
@@ -331,6 +334,12 @@ impl<R: BufRead + Seek> ImageDecoder for TiffDecoder<R> {
331
334
out_cur. write_all ( & cmyk_to_rgb ( cmyk) ) ?;
332
335
}
333
336
}
337
+ DecodingResult :: U16 ( v) if self . original_color_type == ExtendedColorType :: Cmyk16 => {
338
+ let mut out_cur = Cursor :: new ( buf) ;
339
+ for cmyk in v. chunks_exact ( 4 ) {
340
+ out_cur. write_all ( bytemuck:: cast_slice ( & cmyk_to_rgb16 ( cmyk) ) ) ?;
341
+ }
342
+ }
334
343
DecodingResult :: U8 ( v) if self . original_color_type == ExtendedColorType :: L1 => {
335
344
let width = self . dimensions . 0 ;
336
345
let row_bytes = width. div_ceil ( 8 ) ;
@@ -399,6 +408,18 @@ fn cmyk_to_rgb(cmyk: &[u8]) -> [u8; 3] {
399
408
]
400
409
}
401
410
411
+ fn cmyk_to_rgb16 ( cmyk : & [ u16 ] ) -> [ u16 ; 3 ] {
412
+ let c = f32:: from ( cmyk[ 0 ] ) ;
413
+ let m = f32:: from ( cmyk[ 1 ] ) ;
414
+ let y = f32:: from ( cmyk[ 2 ] ) ;
415
+ let kf = 1. - f32:: from ( cmyk[ 3 ] ) / 65535. ;
416
+ [
417
+ ( ( 65535. - c) * kf) as u16 ,
418
+ ( ( 65535. - m) * kf) as u16 ,
419
+ ( ( 65535. - y) * kf) as u16
420
+ ]
421
+ }
422
+
402
423
/// Convert a slice of sample bytes to its semantic type, being a `Pod`.
403
424
fn u8_slice_as_pod < P : bytemuck:: Pod > ( buf : & [ u8 ] ) -> ImageResult < std:: borrow:: Cow < ' _ , [ P ] > > {
404
425
bytemuck:: try_cast_slice ( buf)
0 commit comments