summaryrefslogtreecommitdiff
path: root/src/image
diff options
context:
space:
mode:
authorNigel Tao <nigeltao@golang.org>2015-02-26 11:35:20 +1100
committerNigel Tao <nigeltao@golang.org>2015-02-26 02:08:45 +0000
commita32dd832530a176b5b45f06c3a97f52383227480 (patch)
treec0ab5641828633d8866f457558b2abe3d197c342 /src/image
parent9f4c25e2236617c27e5b430c774b4d9c4b86ba1b (diff)
downloadgo-git-a32dd832530a176b5b45f06c3a97f52383227480.tar.gz
image/jpeg: support 4:1:1 and 4:1:0 chroma subsampling.
The test data was generated by: convert video-001.png tmp.tga cjpeg -quality 50 -sample 4x2,1x1,1x1 tmp.tga > video-001.q50.410.jpeg cjpeg -quality 50 -sample 4x1,1x1,1x1 tmp.tga > video-001.q50.411.jpeg cjpeg -quality 50 -sample 4x2,1x1,1x1 -progressive tmp.tga > video-001.q50.410.progressive.jpeg cjpeg -quality 50 -sample 4x1,1x1,1x1 -progressive tmp.tga > video-001.q50.411.progressive.jpeg rm tmp.tga Change-Id: I5570389c462360f98c3160f3c6963d9466d511de Reviewed-on: https://go-review.googlesource.com/6041 Reviewed-by: Rob Pike <r@golang.org>
Diffstat (limited to 'src/image')
-rw-r--r--src/image/jpeg/reader.go17
-rw-r--r--src/image/jpeg/reader_test.go2
-rw-r--r--src/image/jpeg/scan.go13
-rw-r--r--src/image/testdata/video-001.q50.410.jpegbin0 -> 3259 bytes
-rw-r--r--src/image/testdata/video-001.q50.410.progressive.jpegbin0 -> 3125 bytes
-rw-r--r--src/image/testdata/video-001.q50.411.jpegbin0 -> 3362 bytes
-rw-r--r--src/image/testdata/video-001.q50.411.progressive.jpegbin0 -> 3251 bytes
7 files changed, 14 insertions, 18 deletions
diff --git a/src/image/jpeg/reader.go b/src/image/jpeg/reader.go
index 5d7fefc6cd..8fcb2e06c1 100644
--- a/src/image/jpeg/reader.go
+++ b/src/image/jpeg/reader.go
@@ -42,12 +42,6 @@ const (
maxTq = 3
maxComponents = 4
-
- // We only support 4:4:4, 4:4:0, 4:2:2 and 4:2:0 downsampling, and therefore the
- // number of luma samples per chroma sample is at most 2 in the horizontal
- // and 2 in the vertical direction.
- maxH = 2
- maxV = 2
)
const (
@@ -346,12 +340,13 @@ func (d *decoder) processSOF(n int) error {
d.comp[i].v = int(hv & 0x0f)
switch d.nComp {
case 3:
- // For YCbCr images, we only support 4:4:4, 4:4:0, 4:2:2 or 4:2:0 chroma
- // downsampling ratios. This implies that the (h, v) values for the Y
- // component are either (1, 1), (1, 2), (2, 1) or (2, 2), and the (h, v)
- // values for the Cr and Cb components must be (1, 1).
+ // For YCbCr images, we only support 4:4:4, 4:4:0, 4:2:2, 4:2:0,
+ // 4:1:1 or 4:1:0 chroma downsampling ratios. This implies that the
+ // (h, v) values for the Y component are either (1, 1), (1, 2),
+ // (2, 1), (2, 2), (4, 1) or (4, 2), and the (h, v) values for the Cr
+ // and Cb components must be (1, 1).
if i == 0 {
- if hv != 0x11 && hv != 0x21 && hv != 0x22 && hv != 0x12 {
+ if hv != 0x11 && hv != 0x21 && hv != 0x22 && hv != 0x12 && hv != 0x41 && hv != 0x42 {
return UnsupportedError("luma/chroma downsample ratio")
}
} else if hv != 0x11 {
diff --git a/src/image/jpeg/reader_test.go b/src/image/jpeg/reader_test.go
index 4de2e8ee73..c5a36cba21 100644
--- a/src/image/jpeg/reader_test.go
+++ b/src/image/jpeg/reader_test.go
@@ -23,6 +23,8 @@ import (
func TestDecodeProgressive(t *testing.T) {
testCases := []string{
"../testdata/video-001",
+ "../testdata/video-001.q50.410",
+ "../testdata/video-001.q50.411",
"../testdata/video-001.q50.420",
"../testdata/video-001.q50.422",
"../testdata/video-001.q50.440",
diff --git a/src/image/jpeg/scan.go b/src/image/jpeg/scan.go
index 4168936312..8fcf401dd8 100644
--- a/src/image/jpeg/scan.go
+++ b/src/image/jpeg/scan.go
@@ -26,6 +26,10 @@ func (d *decoder) makeImg(h0, v0, mxx, myy int) {
subsampleRatio = image.YCbCrSubsampleRatio422
case h0 == 2 && v0 == 2:
subsampleRatio = image.YCbCrSubsampleRatio420
+ case h0 == 4 && v0 == 1:
+ subsampleRatio = image.YCbCrSubsampleRatio411
+ case h0 == 4 && v0 == 2:
+ subsampleRatio = image.YCbCrSubsampleRatio410
default:
panic("unreachable")
}
@@ -175,13 +179,8 @@ func (d *decoder) processSOS(n int) error {
// 0 1 2
// 3 4 5
if nComp != 1 {
- bx, by = d.comp[compIndex].h*mx, d.comp[compIndex].v*my
- if h0 == 1 {
- by += j
- } else {
- bx += j % 2
- by += j / 2
- }
+ bx = d.comp[compIndex].h*mx + j%h0
+ by = d.comp[compIndex].v*my + j/h0
} else {
q := mxx * d.comp[compIndex].h
bx = blockCount % q
diff --git a/src/image/testdata/video-001.q50.410.jpeg b/src/image/testdata/video-001.q50.410.jpeg
new file mode 100644
index 0000000000..4cebd1eb25
--- /dev/null
+++ b/src/image/testdata/video-001.q50.410.jpeg
Binary files differ
diff --git a/src/image/testdata/video-001.q50.410.progressive.jpeg b/src/image/testdata/video-001.q50.410.progressive.jpeg
new file mode 100644
index 0000000000..fb7140217e
--- /dev/null
+++ b/src/image/testdata/video-001.q50.410.progressive.jpeg
Binary files differ
diff --git a/src/image/testdata/video-001.q50.411.jpeg b/src/image/testdata/video-001.q50.411.jpeg
new file mode 100644
index 0000000000..b90de18721
--- /dev/null
+++ b/src/image/testdata/video-001.q50.411.jpeg
Binary files differ
diff --git a/src/image/testdata/video-001.q50.411.progressive.jpeg b/src/image/testdata/video-001.q50.411.progressive.jpeg
new file mode 100644
index 0000000000..1ddb22b8b0
--- /dev/null
+++ b/src/image/testdata/video-001.q50.411.progressive.jpeg
Binary files differ