@@ -364,6 +364,37 @@ impl<T: $($bound+)*> Pixel for $ident<T> {
364364 }
365365 }
366366
367+ fn map2_with_alpha<F , G >( & self , other: & Self , f: F , g: G ) -> $ident<T > where F : FnMut ( T , T ) -> T , G : FnMut ( T , T ) -> T {
368+ let mut this = ( * self ) . clone( ) ;
369+ this. apply2_with_alpha( other, f, g) ;
370+ this
371+ }
372+
373+ fn apply2_with_alpha<F , G >( & mut self , other: & $ident<T >, mut f: F , mut g: G ) where F : FnMut ( T , T ) -> T , G : FnMut ( T , T ) -> T {
374+ const ALPHA : usize = $channels - $alphas;
375+ for ( a, & b) in self . 0 [ ..ALPHA ] . iter_mut( ) . zip( other. 0 [ ..ALPHA ] . iter( ) ) {
376+ * a = f( * a, b)
377+ }
378+ // The branch of this match is `const`. This way ensures that no subexpression fails the
379+ // `const_err` lint (the expression `self.0[ALPHA]` would).
380+ if let ( Some ( a) , Some ( b) ) = ( self . 0 . get_mut( ALPHA ) , other. 0 . get( ALPHA ) ) {
381+ * a = g( * a, * b)
382+ }
383+ }
384+
385+ fn map2_without_alpha<F >( & self , other: & Self , f: F ) -> $ident<T > where F : FnMut ( T , T ) -> T {
386+ let mut this = ( * self ) . clone( ) ;
387+ this. apply2_without_alpha( other, f) ;
388+ this
389+ }
390+
391+ fn apply2_without_alpha<F >( & mut self , other: & $ident<T >, mut f: F ) where F : FnMut ( T , T ) -> T {
392+ const ALPHA : usize = $channels - $alphas;
393+ for ( a, & b) in self . 0 [ ..ALPHA ] . iter_mut( ) . zip( other. 0 [ ..ALPHA ] . iter( ) ) {
394+ * a = f( * a, b)
395+ }
396+ }
397+
367398 fn invert( & mut self ) {
368399 Invert :: invert( self )
369400 }
@@ -924,6 +955,63 @@ mod tests {
924955 assert_eq ! ( rgb, Rgb ( [ 0 , 0 , 0 ] ) ) ;
925956 }
926957
958+ #[ test]
959+ fn test_apply2_with_alpha_rgba ( ) {
960+ let mut rgba = Rgba ( [ 1 , 2 , 3 , 64 ] ) ;
961+ rgba. apply2_with_alpha ( & Rgba ( [ 4 , 5 , 6 , 128 ] ) , |s, o| s + o, |s, o| ( s + o) / 2 ) ;
962+ assert_eq ! ( rgba, Rgba ( [ 5 , 7 , 9 , 96 ] ) ) ;
963+ }
964+
965+ #[ test]
966+ fn test_apply2_with_alpha_rgb ( ) {
967+ let mut rgb = Rgb ( [ 1 , 2 , 3 ] ) ;
968+ rgb. apply2_with_alpha ( & Rgb ( [ 4 , 5 , 6 ] ) , |s, o| s + o, |_s, _o| panic ! ( "bug" ) ) ;
969+ assert_eq ! ( rgb, Rgb ( [ 5 , 7 , 9 ] ) ) ;
970+ }
971+
972+ #[ test]
973+ fn test_map2_with_alpha_rgba ( ) {
974+ let rgba = Rgba ( [ 1 , 2 , 3 , 64 ] ) . map2_with_alpha (
975+ & Rgba ( [ 4 , 5 , 6 , 128 ] ) ,
976+ |s, o| s + o,
977+ |s, o| ( s + o) / 2 ,
978+ ) ;
979+ assert_eq ! ( rgba, Rgba ( [ 5 , 7 , 9 , 96 ] ) ) ;
980+ }
981+
982+ #[ test]
983+ fn test_map2_with_alpha_rgb ( ) {
984+ let rgb =
985+ Rgb ( [ 1 , 2 , 3 ] ) . map2_with_alpha ( & Rgb ( [ 4 , 5 , 6 ] ) , |s, o| s + o, |_s, _o| panic ! ( "bug" ) ) ;
986+ assert_eq ! ( rgb, Rgb ( [ 5 , 7 , 9 ] ) ) ;
987+ }
988+
989+ #[ test]
990+ fn test_apply2_without_alpha_rgba ( ) {
991+ let mut rgba = Rgba ( [ 1 , 2 , 3 , 64 ] ) ;
992+ rgba. apply2_without_alpha ( & Rgba ( [ 4 , 5 , 6 , 128 ] ) , |s, o| s + o) ;
993+ assert_eq ! ( rgba, Rgba ( [ 5 , 7 , 9 , 64 ] ) ) ;
994+ }
995+
996+ #[ test]
997+ fn test_apply2_without_alpha_rgb ( ) {
998+ let mut rgb = Rgb ( [ 1 , 2 , 3 ] ) ;
999+ rgb. apply2_without_alpha ( & Rgb ( [ 4 , 5 , 6 ] ) , |s, o| s + o) ;
1000+ assert_eq ! ( rgb, Rgb ( [ 5 , 7 , 9 ] ) ) ;
1001+ }
1002+
1003+ #[ test]
1004+ fn test_map2_without_alpha_rgba ( ) {
1005+ let rgba = Rgba ( [ 1 , 2 , 3 , 64 ] ) . map2_without_alpha ( & Rgba ( [ 4 , 5 , 6 , 128 ] ) , |s, o| s + o) ;
1006+ assert_eq ! ( rgba, Rgba ( [ 5 , 7 , 9 , 64 ] ) ) ;
1007+ }
1008+
1009+ #[ test]
1010+ fn test_map2_without_alpha_rgb ( ) {
1011+ let rgb = Rgb ( [ 1 , 2 , 3 ] ) . map2_without_alpha ( & Rgb ( [ 4 , 5 , 6 ] ) , |s, o| s + o) ;
1012+ assert_eq ! ( rgb, Rgb ( [ 5 , 7 , 9 ] ) ) ;
1013+ }
1014+
9271015 #[ test]
9281016 fn test_blend_luma_alpha ( ) {
9291017 let a = & mut LumaA ( [ 255_u8 , 255 ] ) ;
0 commit comments