bugzilla #40676: patch 29132 with changes, support for sRGB and iCCP chunks

git-svn-id: https://svn.apache.org/repos/asf/xmlgraphics/fop/trunk@1400536 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/lib/xmlgraphics-commons-1.5svn.jar b/lib/xmlgraphics-commons-1.5svn.jar
index e0cf7b1..317ab33 100644
--- a/lib/xmlgraphics-commons-1.5svn.jar
+++ b/lib/xmlgraphics-commons-1.5svn.jar
Binary files differ
diff --git a/src/java/org/apache/fop/render/pdf/AbstractImageAdapter.java b/src/java/org/apache/fop/render/pdf/AbstractImageAdapter.java
index 46e8ebe..2840ea1 100644
--- a/src/java/org/apache/fop/render/pdf/AbstractImageAdapter.java
+++ b/src/java/org/apache/fop/render/pdf/AbstractImageAdapter.java
@@ -88,11 +88,12 @@
 
     /** {@inheritDoc} */
     public void setup(PDFDocument doc) {
-
         ICC_Profile prof = getEffectiveICCProfile();
         PDFDeviceColorSpace pdfCS = toPDFColorSpace(getImageColorSpace());
         if (prof != null) {
             pdfICCStream = setupColorProfile(doc, prof, pdfCS);
+        } else if (issRGB()) {
+          pdfICCStream = setupsRGBColorProfile(doc);
         }
         if (doc.getProfile().getPDFAMode().isPDFA1LevelB()) {
             if (pdfCS != null
@@ -116,6 +117,34 @@
         return image.getICCProfile();
     }
 
+    protected boolean issRGB() {
+        return false;
+    }
+
+    private static PDFICCStream getDefaultsRGBICCStream(PDFICCBasedColorSpace cs, PDFDocument doc, 
+            String profileDesc) {
+        if (cs == null) {
+            if (profileDesc == null || !profileDesc.startsWith("sRGB")) {
+                log.warn("The default sRGB profile was indicated,"
+                    + " but the profile description does not match what was expected: "
+                    + profileDesc);
+            }
+            //It's the default sRGB profile which we mapped to DefaultRGB in PDFRenderer
+            cs = (PDFICCBasedColorSpace)doc.getResources().getColorSpace(new PDFName("DefaultRGB"));
+        }
+        if (cs == null) {
+            // sRGB hasn't been set up for the PDF document
+            // so install but don't set to DefaultRGB
+            cs = PDFICCBasedColorSpace.setupsRGBColorSpace(doc);
+        }
+        return cs.getICCStream();
+    }
+
+    private static PDFICCStream setupsRGBColorProfile(PDFDocument doc) {
+        PDFICCBasedColorSpace cs = doc.getResources().getICCColorSpaceByProfileName("sRGB");
+        return getDefaultsRGBICCStream(cs, doc, "sRGB");
+    }
+
     private static PDFICCStream setupColorProfile(PDFDocument doc,
                 ICC_Profile prof, PDFDeviceColorSpace pdfCS) {
         boolean defaultsRGB = ColorProfileUtil.isDefaultsRGB(prof);
@@ -134,22 +163,7 @@
                 pdfICCStream = cs.getICCStream();
             }
         } else {
-            if (cs == null) {
-                if (desc == null || !desc.startsWith("sRGB")) {
-                    log.warn("The default sRGB profile was indicated,"
-                            + " but the profile description does not match what was expected: "
-                            + desc);
-                }
-                //It's the default sRGB profile which we mapped to DefaultRGB in PDFRenderer
-                cs = (PDFICCBasedColorSpace)doc.getResources().getColorSpace(
-                        new PDFName("DefaultRGB"));
-            }
-            if (cs == null) {
-                // sRGB hasn't been set up for the PDF document
-                // so install but don't set to DefaultRGB
-                cs = PDFICCBasedColorSpace.setupsRGBColorSpace(doc);
-            }
-            pdfICCStream = cs.getICCStream();
+            pdfICCStream = getDefaultsRGBICCStream(cs, doc, desc);
         }
         return pdfICCStream;
     }
diff --git a/src/java/org/apache/fop/render/pdf/ImageRawPNGAdapter.java b/src/java/org/apache/fop/render/pdf/ImageRawPNGAdapter.java
index b9f5e1d..9742036 100644
--- a/src/java/org/apache/fop/render/pdf/ImageRawPNGAdapter.java
+++ b/src/java/org/apache/fop/render/pdf/ImageRawPNGAdapter.java
@@ -49,7 +49,7 @@
 import org.apache.fop.pdf.PDFFilter;

 import org.apache.fop.pdf.PDFFilterException;

 import org.apache.fop.pdf.PDFFilterList;

-import org.apache.fop.pdf.PDFICCStream;

+import org.apache.fop.pdf.PDFName;

 import org.apache.fop.pdf.PDFReference;

 

 public class ImageRawPNGAdapter extends AbstractImageAdapter {

@@ -57,7 +57,11 @@
     /** logging instance */

     private static Log log = LogFactory.getLog(ImageRawPNGAdapter.class);

 

-    private PDFICCStream pdfICCStream;

+    private static final PDFName RI_PERCEPTUAL = new PDFName("Perceptual");

+    private static final PDFName RI_RELATIVE_COLORIMETRIC = new PDFName("RelativeColorimetric");

+    private static final PDFName RI_SATURATION = new PDFName("Saturation");

+    private static final PDFName RI_ABSOLUTE_COLORIMETRIC = new PDFName("AbsoluteColorimetric");

+

     private PDFFilter pdfFilter;

     private String maskRef;

     private PDFReference softMask;

@@ -241,20 +245,41 @@
     }

 

     /** {@inheritDoc} */

-    public PDFICCStream getICCStream() {

-        return pdfICCStream;

-    }

-

-    /** {@inheritDoc} */

     public String getFilterHint() {

         return PDFFilterList.PRECOMPRESSED_FILTER;

     }

 

     public void populateXObjectDictionary(PDFDictionary dict) {

+        int renderingIntent = ((ImageRawPNG) image).getRenderingIntent();

+        if (renderingIntent != -1) {

+            switch (renderingIntent) {

+            case 0:

+                dict.put("Intent", RI_PERCEPTUAL);

+                break;

+            case 1:

+                dict.put("Intent", RI_RELATIVE_COLORIMETRIC);

+                break;

+            case 2:

+                dict.put("Intent", RI_SATURATION);

+                break;

+            case 3:

+                dict.put("Intent", RI_ABSOLUTE_COLORIMETRIC);

+                break;

+            default:

+                // ignore

+            }

+        }

         ColorModel cm = ((ImageRawPNG) image).getColorModel();

         if (cm instanceof IndexColorModel) {

             IndexColorModel icm = (IndexColorModel) cm;

             super.populateXObjectDictionaryForIndexColorModel(dict, icm);

         }

     }

+

+    protected boolean issRGB() {

+        if (((ImageRawPNG) image).getRenderingIntent() != -1) {

+            return true;

+        }

+        return false;

+    }

 }

diff --git a/test/java/org/apache/fop/render/pdf/ImageRawPNGAdapterTestCase.java b/test/java/org/apache/fop/render/pdf/ImageRawPNGAdapterTestCase.java
index 885821f..9577e2e 100644
--- a/test/java/org/apache/fop/render/pdf/ImageRawPNGAdapterTestCase.java
+++ b/test/java/org/apache/fop/render/pdf/ImageRawPNGAdapterTestCase.java
@@ -19,31 +19,38 @@
 
 package org.apache.fop.render.pdf;
 
+import java.awt.color.ColorSpace;
+import java.awt.color.ICC_Profile;
 import java.awt.image.ComponentColorModel;
 import java.awt.image.IndexColorModel;
 import java.io.ByteArrayInputStream;
 import java.io.ByteArrayOutputStream;
 import java.io.IOException;
-import java.util.zip.Deflater;
-import java.util.zip.DeflaterOutputStream;
 
 import org.junit.Test;
 
+import static org.junit.Assert.assertArrayEquals;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.verify;
+import static org.mockito.Mockito.when;
+
 import org.apache.xmlgraphics.image.loader.ImageSize;
 import org.apache.xmlgraphics.image.loader.impl.ImageRawPNG;
+import org.apache.xmlgraphics.java2d.color.profile.ColorProfileUtil;
 
 import org.apache.fop.pdf.FlateFilter;
 import org.apache.fop.pdf.PDFAMode;
+import org.apache.fop.pdf.PDFDictionary;
 import org.apache.fop.pdf.PDFDocument;
+import org.apache.fop.pdf.PDFICCBasedColorSpace;
+import org.apache.fop.pdf.PDFICCStream;
+import org.apache.fop.pdf.PDFName;
 import org.apache.fop.pdf.PDFProfile;
+import org.apache.fop.pdf.PDFResources;
 import org.apache.fop.render.RawPNGTestUtil;
 
-import static org.junit.Assert.assertArrayEquals;
-import static org.junit.Assert.assertEquals;
-
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.when;
-
 public class ImageRawPNGAdapterTestCase {
 
     @Test
@@ -56,6 +63,7 @@
         ImageSize is = RawPNGTestUtil.getImageSize();
 
         when(irpng.getColorModel()).thenReturn(cm);
+        when(irpng.getRenderingIntent()).thenReturn(-1);
         // when(cm.hasAlpha()).thenReturn(false);
         when(doc.getProfile()).thenReturn(profile);
         when(profile.getPDFAMode()).thenReturn(PDFAMode.PDFA_1A);
@@ -75,6 +83,7 @@
         ImageSize is = RawPNGTestUtil.getImageSize();
 
         when(irpng.getColorModel()).thenReturn(cm);
+        when(irpng.getRenderingIntent()).thenReturn(-1);
         when(cm.getNumComponents()).thenReturn(3);
         // when(cm.hasAlpha()).thenReturn(false);
         when(doc.getProfile()).thenReturn(profile);
@@ -117,6 +126,7 @@
         ImageSize is = RawPNGTestUtil.getImageSize();
 
         when(irpng.getColorModel()).thenReturn(cm);
+        when(irpng.getRenderingIntent()).thenReturn(-1);
         when(cm.getNumComponents()).thenReturn(numComponents);
         // when(cm.hasAlpha()).thenReturn(false);
         when(doc.getProfile()).thenReturn(profile);
@@ -139,4 +149,55 @@
         }
     }
 
+    @Test
+    public void testPopulateXObjectDictionaryWithComponentColorModelAndsRGB() {
+        ComponentColorModel cm = mock(ComponentColorModel.class);
+        ImageRawPNG irpng = mock(ImageRawPNG.class);
+        PDFDictionary pdfDic = mock(PDFDictionary.class);
+        ImageRawPNGAdapter irpnga = new ImageRawPNGAdapter(irpng, "mock");
+
+        when(irpng.getColorModel()).thenReturn(cm);
+        when(irpng.getRenderingIntent()).thenReturn(0);
+        irpnga.populateXObjectDictionary(pdfDic);
+        verify(pdfDic).put("Intent", new PDFName("Perceptual"));
+        when(irpng.getRenderingIntent()).thenReturn(1);
+        irpnga.populateXObjectDictionary(pdfDic);
+        verify(pdfDic).put("Intent", new PDFName("RelativeColorimetric"));
+        when(irpng.getRenderingIntent()).thenReturn(2);
+        irpnga.populateXObjectDictionary(pdfDic);
+        verify(pdfDic).put("Intent", new PDFName("Saturation"));
+        when(irpng.getRenderingIntent()).thenReturn(3);
+        irpnga.populateXObjectDictionary(pdfDic);
+        verify(pdfDic).put("Intent", new PDFName("AbsoluteColorimetric"));
+    }
+
+    @Test
+    public void testRenderingIntentImpliessRGBColorProfile() {
+        ComponentColorModel cm = mock(ComponentColorModel.class);
+        ImageRawPNG irpng = mock(ImageRawPNG.class);
+        PDFDocument doc = mock(PDFDocument.class);
+        PDFProfile profile = mock(PDFProfile.class);
+        PDFResources resources = mock(PDFResources.class);
+        PDFICCBasedColorSpace cs = mock(PDFICCBasedColorSpace.class);
+        PDFICCStream stream = mock(PDFICCStream.class);
+        ICC_Profile iccprof = ICC_Profile.getInstance(ColorSpace.CS_sRGB);
+        ImageRawPNGAdapter irpnga = new ImageRawPNGAdapter(irpng, "mock");
+        ImageSize is = RawPNGTestUtil.getImageSize();
+
+        when(irpng.getColorModel()).thenReturn(cm);
+        when(irpng.getRenderingIntent()).thenReturn(0);
+        when(cm.getNumComponents()).thenReturn(3);
+        // when(cm.hasAlpha()).thenReturn(false);
+        when(doc.getProfile()).thenReturn(profile);
+        when(doc.getResources()).thenReturn(resources);
+        when(resources.getICCColorSpaceByProfileName("sRGB")).thenReturn(cs);
+        when(profile.getPDFAMode()).thenReturn(PDFAMode.PDFA_1A);
+        when(irpng.getSize()).thenReturn(is);
+        when(cs.getICCStream()).thenReturn(stream);
+        when(stream.getICCProfile()).thenReturn(iccprof);
+
+        irpnga.setup(doc);
+        PDFICCStream iccStream = irpnga.getICCStream();
+        assertTrue(ColorProfileUtil.isDefaultsRGB(iccStream.getICCProfile()));
+    }
 }