|
@@ -10,13 +10,9 @@ import (
|
|
|
)
|
|
|
|
|
|
var (
|
|
|
- ps3Header = []byte("Photoshop 3.0\x00")
|
|
|
- ps3BlockHeader = []byte("8BIM")
|
|
|
- ps3IptcRecourceID = []byte("\x04\x04")
|
|
|
- iptcTagHeader = byte(0x1c)
|
|
|
+ iptcTagHeader = byte(0x1c)
|
|
|
|
|
|
- errInvalidPS3Header = errors.New("invalid Photoshop 3.0 header")
|
|
|
- errInvalidDataSize = errors.New("invalid IPTC data size")
|
|
|
+ errInvalidDataSize = errors.New("invalid IPTC data size")
|
|
|
)
|
|
|
|
|
|
type IptcMap map[TagKey][]TagValue
|
|
@@ -69,7 +65,7 @@ func (m IptcMap) MarshalJSON() ([]byte, error) {
|
|
|
return json.Marshal(mm)
|
|
|
}
|
|
|
|
|
|
-func ParseTags(data []byte, m IptcMap) error {
|
|
|
+func Parse(data []byte, m IptcMap) error {
|
|
|
buf := bytes.NewBuffer(data)
|
|
|
|
|
|
// Min tag size is 5 (2 tagHeader)
|
|
@@ -114,52 +110,7 @@ func ParseTags(data []byte, m IptcMap) error {
|
|
|
return nil
|
|
|
}
|
|
|
|
|
|
-func ParsePS3(data []byte, m IptcMap) error {
|
|
|
- buf := bytes.NewBuffer(data)
|
|
|
-
|
|
|
- if !bytes.Equal(buf.Next(14), ps3Header) {
|
|
|
- return errInvalidPS3Header
|
|
|
- }
|
|
|
-
|
|
|
- // Read blocks
|
|
|
- // Minimal block size is 12 (4 blockHeader + 2 resoureceID + 2 name + 4 blockSize)
|
|
|
- for buf.Len() >= 12 {
|
|
|
- if !bytes.Equal(buf.Bytes()[:4], ps3BlockHeader) {
|
|
|
- buf.Next(1)
|
|
|
- continue
|
|
|
- }
|
|
|
-
|
|
|
- // Skip block header
|
|
|
- buf.Next(4)
|
|
|
-
|
|
|
- resoureceID := buf.Next(2)
|
|
|
-
|
|
|
- // Skip name
|
|
|
- // Name is zero terminated string padded to even
|
|
|
- for buf.Len() > 0 && buf.Next(2)[1] != 0 {
|
|
|
- }
|
|
|
-
|
|
|
- if buf.Len() < 4 {
|
|
|
- break
|
|
|
- }
|
|
|
-
|
|
|
- blockSize := int(binary.BigEndian.Uint32(buf.Next(4)))
|
|
|
-
|
|
|
- if buf.Len() < blockSize {
|
|
|
- break
|
|
|
- }
|
|
|
- blockData := buf.Next(blockSize)
|
|
|
-
|
|
|
- // 1028 is IPTC tags block
|
|
|
- if bytes.Equal(resoureceID, ps3IptcRecourceID) {
|
|
|
- return ParseTags(blockData, m)
|
|
|
- }
|
|
|
- }
|
|
|
-
|
|
|
- return nil
|
|
|
-}
|
|
|
-
|
|
|
-func (m IptcMap) DumpTags() []byte {
|
|
|
+func (m IptcMap) Dump() []byte {
|
|
|
buf := new(bytes.Buffer)
|
|
|
|
|
|
for key, values := range m {
|
|
@@ -187,19 +138,3 @@ func (m IptcMap) DumpTags() []byte {
|
|
|
|
|
|
return buf.Bytes()
|
|
|
}
|
|
|
-
|
|
|
-func (m IptcMap) Dump() []byte {
|
|
|
- tagsDump := m.DumpTags()
|
|
|
-
|
|
|
- buf := new(bytes.Buffer)
|
|
|
- buf.Grow(26)
|
|
|
-
|
|
|
- buf.Write(ps3Header)
|
|
|
- buf.Write(ps3BlockHeader)
|
|
|
- buf.Write(ps3IptcRecourceID)
|
|
|
- buf.Write([]byte{0, 0})
|
|
|
- binary.Write(buf, binary.BigEndian, uint32(len(tagsDump)))
|
|
|
- buf.Write(tagsDump)
|
|
|
-
|
|
|
- return buf.Bytes()
|
|
|
-}
|