:: png-unfilter-line ( width prev curr filter -- curr' ) prev :> c prev width tail-slice :> b curr :> a curr width tail-slice :> x x length [0,b) filter { { filter-none [ drop ] } { filter-sub [ [| n | n x nth n a nth + 256 wrap n x set-nth ] each ] } { filter-up [ [| n | n x nth n b nth + 256 wrap n x set-nth ] each ] } { filter-average [ [| n | n x nth n a nth n b nth + 2/ + 256 wrap n x set-nth ] each ] } { filter-paeth [ [| n | n x nth n a nth n b nth n c nth paeth + 256 wrap n x set-nth ] each ] } } case curr width tail ; :: reverse-png-filter ( n lines -- byte-array ) lines dup first length 0 prefix [ n 1 - 0 prepend ] map 2 clump [ first2 [ [ n ] 2dip ] [ n 1 - swap nth ] [ [ 0 n 1 - ] dip set-nth ] tri png-unfilter-line ] map B{ } concat-as ; : png-image-bytes ( loading-png -- byte-array ) [ png-bytes-per-pixel ] [ inflate-data ] [ png-group-width ] tri group rever se-png-filter ;