Skip to content

Commit b20eb30

Browse files
committed
Added 2 build tags (jpeg and turbojpeg) to build the native jpeg operations; otherwise, default go image/jpeg library is build by default.
1 parent 4aa0bcd commit b20eb30

9 files changed

+158
-45
lines changed

.travis.yml

+3
Original file line numberDiff line numberDiff line change
@@ -3,4 +3,7 @@ go:
33
- 1.2
44
env:
55
- GOARCH=amd64
6+
before_install:
7+
- sudo apt-get -qq jpeg-turbo
8+
script: go test -v && go test -v -tags jpeg & go test -v -tags turbojpeg
69

cr2parser.go

+1-1
Original file line numberDiff line numberDiff line change
@@ -283,5 +283,5 @@ func (n Cr2Parser) decodeAndWriteJpeg(f *os.File, j *jpegInfo, destDir string, q
283283
// NewCr2Parser creates an instance of Cr2Parser.
284284
// Returns a pointer to a Cr2Parser instance.
285285
func NewCr2Parser(hostIsLittleEndian bool) (RawParser, string) {
286-
return RawParser(&Cr2Parser{hostIsLittleEndian}), Cr2ParserKey
286+
return &Cr2Parser{hostIsLittleEndian}, Cr2ParserKey
287287
}

jpeg_wrapper.c

+2
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
// +build jpeg turbojpeg
2+
13
/*
24
Copyright (c) 2013 Jeremy Torres, https://github.com/jeremytorres/rawparser
35

jpeg_wrapper.h

+2
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
// +build jpeg turbojpeg
2+
13
/*
24
Copyright (c) 2013 Jeremy Torres, https://github.com/jeremytorres/rawparser
35

jpeggo.go

+82
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
// +build !jpeg,!turbojpeg
2+
3+
/*
4+
Copyright (c) 2013 Jeremy Torres, https://github.com/jeremytorres/rawparser
5+
6+
Permission is hereby granted, free of charge, to any person obtaining
7+
a copy of this software and associated documentation files (the
8+
"Software"), to deal in the Software without restriction, including
9+
without limitation the rights to use, copy, modify, merge, publish,
10+
distribute, sublicense, and/or sell copies of the Software, and to
11+
permit persons to whom the Software is furnished to do so, subject to
12+
the following conditions:
13+
14+
The above copyright notice and this permission notice shall be
15+
included in all copies or substantial portions of the Software.
16+
17+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
18+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
19+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
20+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
21+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
22+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
23+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24+
*/
25+
26+
package rawparser
27+
28+
import (
29+
"bytes"
30+
"image"
31+
"image/jpeg"
32+
"log"
33+
"os"
34+
)
35+
36+
func init() {
37+
log.Println("Using pure GO JPEG package")
38+
}
39+
40+
func decodeAndWriteJpeg(data []byte, quality int, filename string) error {
41+
jpegFile, err := os.Create(filename)
42+
defer jpegFile.Close()
43+
if err != nil {
44+
log.Printf("Error creating jpeg file: %v\n", err)
45+
return err
46+
}
47+
48+
// Decode image
49+
decodedImage, err := decodeJpeg(data)
50+
if err != nil {
51+
log.Printf("Error decoding embedded jpeg: %v\n", err)
52+
return err
53+
}
54+
55+
// Encode and write using specifid JPEG quality
56+
err = encodeAndWriteJpeg(jpegFile, decodedImage, quality)
57+
if err != nil {
58+
log.Printf("Error encoding embedded jpeg: %v\n", err)
59+
}
60+
return err
61+
}
62+
63+
func decodeJpeg(data []byte) (img image.Image, e error) {
64+
// Decode JPEG
65+
bReader := bytes.NewReader(data)
66+
img, e = jpeg.Decode(bReader)
67+
if e != nil {
68+
log.Printf("Error decoding embedded jpeg: %v\n", e)
69+
return nil, e
70+
}
71+
return img, e
72+
}
73+
74+
// encodeAndWriteJpeg encodes a JPEG image based on a JPEG quality parameter
75+
// from 1 to 100, where 100 is the best encoding quality.
76+
func encodeAndWriteJpeg(f *os.File, img image.Image, q int) error {
77+
e := jpeg.Encode(f, img, &jpeg.Options{q})
78+
if e != nil {
79+
log.Printf("Error encoding and writing embedded jpeg: %v\n", e)
80+
}
81+
return e
82+
}

jpeglibjpeg.go

+58
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
// +build jpeg
2+
3+
/*
4+
Copyright (c) 2013 Jeremy Torres, https://github.com/jeremytorres/rawparser
5+
6+
Permission is hereby granted, free of charge, to any person obtaining
7+
a copy of this software and associated documentation files (the
8+
"Software"), to deal in the Software without restriction, including
9+
without limitation the rights to use, copy, modify, merge, publish,
10+
distribute, sublicense, and/or sell copies of the Software, and to
11+
permit persons to whom the Software is furnished to do so, subject to
12+
the following conditions:
13+
14+
The above copyright notice and this permission notice shall be
15+
included in all copies or substantial portions of the Software.
16+
17+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
18+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
19+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
20+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
21+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
22+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
23+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24+
*/
25+
26+
package rawparser
27+
28+
// Note: modify these flags for your enviornment if required.
29+
30+
// #cgo CFLAGS: -O2
31+
// #cgo LDFLAGS: -ljpeg
32+
// #include "jpeg_wrapper.h"
33+
import "C"
34+
35+
import (
36+
"fmt"
37+
"log"
38+
"unsafe"
39+
)
40+
41+
func init() {
42+
log.Println("Using libjpeg native library")
43+
}
44+
45+
func decodeAndWriteJpeg(data []byte, quality int, filename string) error {
46+
var rc C.int
47+
f := C.CString(filename)
48+
defer C.cleanupString(f)
49+
50+
rc = C.decodeEncodeWrite((*C.uchar)(unsafe.Pointer(&data[0])),
51+
C.int(len(data)), C.int(quality), f)
52+
53+
if rc != 0 {
54+
return fmt.Errorf("Error re-encoding JPEG")
55+
}
56+
57+
return nil
58+
}

jpeg.go jpeglibturbo.go

+9-6
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
// +build turbojpeg
2+
13
/*
24
Copyright (c) 2013 Jeremy Torres, https://github.com/jeremytorres/rawparser
35
@@ -23,21 +25,23 @@
2325

2426
package rawparser
2527

26-
// Note: modify these flags for your enviornment if you
27-
// want to use TurboJpeg.
28+
// Note: modify these flags for your enviornment if required.
29+
2830
// #cgo CFLAGS: -I/usr/local/opt/jpeg-turbo/include -O2
2931
// #cgo LDFLAGS: -L/usr/local/opt/jpeg-turbo/lib -lturbojpeg
30-
31-
// #cgo CFLAGS: -O2
32-
// #cgo LDFLAGS: -ljpeg
3332
// #include "jpeg_wrapper.h"
3433
import "C"
3534

3635
import (
3736
"fmt"
37+
"log"
3838
"unsafe"
3939
)
4040

41+
func init() {
42+
log.Println("Using turbojpeg native library")
43+
}
44+
4145
func decodeAndWriteJpeg(data []byte, quality int, filename string) error {
4246
var rc C.int
4347
f := C.CString(filename)
@@ -49,6 +53,5 @@ func decodeAndWriteJpeg(data []byte, quality int, filename string) error {
4953
if rc != 0 {
5054
return fmt.Errorf("Error re-encoding JPEG")
5155
}
52-
5356
return nil
5457
}

nefparser.go

+1-1
Original file line numberDiff line numberDiff line change
@@ -274,5 +274,5 @@ func (n NefParser) decodeAndWriteJpeg(f *os.File, j *jpegInfo, destDir string, q
274274
// NewNefParser creates an instance of NEF-specific RawParser.
275275
// Returns an instance of a NEF-specific RawParser.
276276
func NewNefParser(hostIsLittleEndian bool) (RawParser, string) {
277-
return RawParser(&NefParser{hostIsLittleEndian}), NefParserKey
277+
return &NefParser{hostIsLittleEndian}, NefParserKey
278278
}

rawparser.go

-37
Original file line numberDiff line numberDiff line change
@@ -24,11 +24,7 @@
2424
package rawparser
2525

2626
import (
27-
"bytes"
2827
"fmt"
29-
"image"
30-
"image/jpeg"
31-
"log"
3228
"os"
3329
"path/filepath"
3430
"strings"
@@ -192,39 +188,6 @@ func toRfc822Date(dateTokens []string) (string, error) {
192188
return monthStr, e
193189
}
194190

195-
// decodeJpeg extracts the embedded jpeg bytes within a raw file and
196-
// decodes the JPEG data.
197-
// Returns the JPEG bytes or error.
198-
func decodeJpeg(f *os.File, j *jpegInfo) (img image.Image, e error) {
199-
cache := make([]byte, j.length)
200-
_, e = f.ReadAt(cache, j.offset)
201-
202-
if e != nil {
203-
log.Printf("Error reading jpeg file: %v\n", e)
204-
return nil, e
205-
}
206-
207-
// Decode JPEG using JPEG quality specified.
208-
bReader := bytes.NewReader(cache)
209-
img, e = jpeg.Decode(bReader)
210-
if e != nil {
211-
log.Printf("Error decoding embedded jpeg: %v\n", e)
212-
return nil, e
213-
}
214-
215-
return img, e
216-
}
217-
218-
// encodeAndWriteJpeg encodes a JPEG image based on a JPEG quality parameter
219-
// from 1 to 100, where 100 is the best encoding quality.
220-
func encodeAndWriteJpeg(f *os.File, img image.Image, q int) error {
221-
e := jpeg.Encode(f, img, &jpeg.Options{q})
222-
if e != nil {
223-
log.Printf("Error encoding and writing embedded jpeg: %v\n", e)
224-
}
225-
return e
226-
}
227-
228191
// genExtractedJpegName creates a full path name for an extracted JPEG
229192
// from a raw file.
230193
// The input file is the pointer to the raw file and its base name is used

0 commit comments

Comments
 (0)