chunk_decoder.go (1877B)
1 package pngstructure 2 3 import ( 4 "bytes" 5 "fmt" 6 7 "encoding/binary" 8 9 "github.com/dsoprea/go-logging" 10 ) 11 12 type ChunkDecoder struct { 13 } 14 15 func NewChunkDecoder() *ChunkDecoder { 16 return new(ChunkDecoder) 17 } 18 19 func (cd *ChunkDecoder) Decode(c *Chunk) (decoded interface{}, err error) { 20 defer func() { 21 if state := recover(); state != nil { 22 err := log.Wrap(state.(error)) 23 log.Panic(err) 24 } 25 }() 26 27 switch c.Type { 28 case "IHDR": 29 ihdr, err := cd.decodeIHDR(c) 30 log.PanicIf(err) 31 32 return ihdr, nil 33 } 34 35 // We don't decode this particular type. 36 return nil, nil 37 } 38 39 type ChunkIHDR struct { 40 Width uint32 41 Height uint32 42 BitDepth uint8 43 ColorType uint8 44 CompressionMethod uint8 45 FilterMethod uint8 46 InterlaceMethod uint8 47 } 48 49 func (ihdr *ChunkIHDR) String() string { 50 return fmt.Sprintf("IHDR<WIDTH=(%d) HEIGHT=(%d) DEPTH=(%d) COLOR-TYPE=(%d) COMP-METHOD=(%d) FILTER-METHOD=(%d) INTRLC-METHOD=(%d)>", ihdr.Width, ihdr.Height, ihdr.BitDepth, ihdr.ColorType, ihdr.CompressionMethod, ihdr.FilterMethod, ihdr.InterlaceMethod) 51 } 52 53 func (cd *ChunkDecoder) decodeIHDR(c *Chunk) (ihdr *ChunkIHDR, err error) { 54 defer func() { 55 if state := recover(); state != nil { 56 err := log.Wrap(state.(error)) 57 log.Panic(err) 58 } 59 }() 60 61 b := bytes.NewBuffer(c.Data) 62 63 ihdr = new(ChunkIHDR) 64 65 err = binary.Read(b, binary.BigEndian, &ihdr.Width) 66 log.PanicIf(err) 67 68 err = binary.Read(b, binary.BigEndian, &ihdr.Height) 69 log.PanicIf(err) 70 71 err = binary.Read(b, binary.BigEndian, &ihdr.BitDepth) 72 log.PanicIf(err) 73 74 err = binary.Read(b, binary.BigEndian, &ihdr.ColorType) 75 log.PanicIf(err) 76 77 err = binary.Read(b, binary.BigEndian, &ihdr.CompressionMethod) 78 log.PanicIf(err) 79 80 err = binary.Read(b, binary.BigEndian, &ihdr.FilterMethod) 81 log.PanicIf(err) 82 83 err = binary.Read(b, binary.BigEndian, &ihdr.InterlaceMethod) 84 log.PanicIf(err) 85 86 return ihdr, nil 87 }