10

I am generating a PDF where all the graphics are drawn in \DeviceRGB in the sRGB color space. I would like to convert the PDF into a different Color Profile using an ICC profile and embed the ICC profile, but I can't find a good tool to do this.

I have tried ImageMagick, but that rasterizes the PDF which is undesirable, and I have tried using Ghostscript. But while that converts the colors, it doesn't embed the ICC profile.

Is there any tool or library (preferably Java or Scala) available for Linux that does what I want?

The Ghostscript commands I have tried are:

gs -o cmyk.pdf -sColorConversionStrategy=CMYK -sDEVICE=pdfwrite \
   -dOverrideICC=true -sOutputICCProfile=CoatedFOGRA27.icc \
   -dRenderIntent=3 in.pdf

and

gs -dSAFER -dBATCH -dNOPAUSE -sDEVICE=pdfwrite -ColorConversionStrategy=CMYK \
   -dProcessColorModel=/DeviceCMYK -sOutputICCProfile=CoatedFOGRA27.icc \
   -sOutputFile=cmyk.pdf in.pdf 

and several variations of the above. I have tried both Ghostscript version 9.10 and 9.16.

Tae-Sung Shin
  • 20,215
  • 33
  • 138
  • 240
Thayne
  • 6,619
  • 2
  • 42
  • 67
  • You profile, `CoatedFOGRA27.icc`, is indeed located in the directory where you execute your shell command? Otherwise, it must be in one of Ghostscript's default search paths, as reported by `gs -h`. – Kurt Pfeifle Jul 24 '15 at 11:59
  • yes, it is int he directory where I execute the command. – Thayne Jul 27 '15 at 17:35

2 Answers2

7

Use Ghostscript v9.16 or higher:

Read its documentation about ICC color profile support, available here:

Here's a possible command to convert the color space and embed the ICC profile:

gs -o cmyk-doc.pdf      \
   -sDEVICE=pdfwrite    \
   -dOverrideICC=true   \
   -sDefaultCMYKProfile=/path/to/mycmykprofile.icc \
   -sOutputICCProfile=/path/to/mydeviceprofile.icc \
   -dRenderIntent=3     \
   -dDeviceGrayToK=true \
    input-doc.pdf

(-dRenderIntent : possible arguments are 0 (Perceptual), 1 (Colorimetric), 2 (Saturation), and 3 (Absolute Colorimetric).)

Caveats

If you look at a PDF file on screen (or on paper, when printed) converted with above command and use a:

  • non-calibrated monitor/screen;
  • non-calibrated print device;
  • non-calibrated room illumination; or
  • PDF reader which cannot handle embedded ICC profiles, then

you may be disappointed. Using the wrong ICC profile or paper type that does not match the one expected by the output profile can also lead to issues.

Dave Jarvis
  • 30,436
  • 41
  • 178
  • 315
Kurt Pfeifle
  • 86,724
  • 23
  • 248
  • 345
  • gs -version: `GPL Ghostscript 9.16 (2015-03-30)` To check for the ICC profile I uncompressed the pdf and searched for ICCBased and the name of the profile I used. – Thayne Jul 23 '15 at 18:57
  • 1
    @KurtPfeifle [This](https://bugs.ghostscript.com/show_bug.cgi?id=692780#c1) looks like this command should not embed the color profile. Also, I can confirm [this method](https://answers.acrobatusers.com/Is-it-possible-in-Acrobat-to-check-profiles-that-are-embedded-in-images-q276640.aspx) shows just "ColorSpace: DeviceCMYK" (for a table cell fill color that was RGB before the conversion). Also, I had to add `-sProcessColorModel=DeviceCMYK` for the command to finish without an error and `-sColorConversionStrategy=CMYK` to actually convert RGB colors I had. I use gs version 9.26 . – Igor Mar 09 '19 at 19:22
  • @VarunJoshi, I doubt I can add anything useful to [that](https://stackoverflow.com/a/56490703/1032586) answer by KenS. Indeed, only a small subset of color management options [is supported for pdf output](http://git.ghostscript.com/?p=ghostpdl.git;a=blob;f=doc/VectorDevices.htm;h=c939fddfa3f59bf73023f904b7e8d0c7e27729ff;hb=refs/heads/master#l566). – Igor Jun 12 '19 at 16:37
  • `-sDefaultCMYKProfile` has no effect - it is related to the *input* (which is not CMYK); `-sOutputICCProfile` and `-dRenderIntent` [have no effect](https://stackoverflow.com/a/56941566/1032586) unless rasterization would happen; `-dDeviceGrayToK` - just the same, probably; `-dOverrideICC=true` is generally undesirable and has no effect since the question is about `DeviceRGB` input. – Igor Jul 08 '19 at 19:39
1

AFAIU, Ghostscript 9.12-9.27 is unable to do what you expect.
But you might be able to partially achieve your goals:

  • Try UseDeviceIndependentColor.
    This won't embed your profile, and won't convert colors to your profile. But it would make you colors "colorimetrically defined" and would embed some icc profile. If your aim is to "preserve" colors, that might work for you.

  • Try PDF/X-3 output, embed "Output Intent" icc profile.

  • Try to adjust the DefaultRGB colorspace - note the following phrase in the docs:

    If a user needs an non trivial color adjustment, a non trivial DefaultRGB color space must be defined

    (I've never tried this.)

  • Try collink. (I've never managed to make this work.)

A toy example

Original file:

Colorbar foxit.PNG

The gs command:

 gswin64c -dPDFX -dBATCH -dNOPAUSE -dHaveTransparency=false -r20 
  -dProcessColorModel=/DeviceCMYK -sColorConversionStrategy=UseDeviceIndependentColor 
  -sDefaultRGBProfile="default_rgb.icc" -sOutputICCProfile="cmyk_des_renderintent.icc" 
  -dRenderIntent=1 -dDefaultRenderingIntent=/Perceptual -sDEVICE=pdfwrite 
  -sOutputFile=colorbar_v1.pdf PDFX_IntCmyk.ps Colorbar.pdf

The output looks like this in Adobe Acrobat (it honors embedded "Output Intent" icc profile): enter image description here

Same file in Foxit Reader (it ignores embedded "Output Intent"): enter image description here

What's happening here:

  • The cmyk_des_renderintent.icc profile, as documented in "Ghostscript 9.21 Color Management", is designed such that different intents output different colors:
    • "Perceptual" rendering intent (0) outputs cyan only,
    • "RelativeColorimetric" intent (1) outputs magenta only
    • "Saturation" rendering intent (2) outputs yellow only.
  • -dHaveTransparency=false makes sure that the 2nd page would get rasterized (due to the presence of a tikz pic with transparency)
  • -r20 makes sure rasterization would be clearly visible (due to just 20dpi)
  • -sOutputICCProfile="cmyk_des_renderintent.icc" -dRenderIntent=1 makes rasterizer produce magenta output.
    • Note that OutputICCProfile parameter is not mentioned in current docs, since this (9.27 docs are a bit outdated).
    • RenderIntent is also undocumented in this context. It only affects rasterization as well.
  • -dDefaultRenderingIntent=/Perceptual puts said intent to metadata, alongside "Output Intent icc profile". This makes Acrobat draw everything in cyan.
  • -sDefaultRGBProfile="default_rgb.icc" is a placeholder for possible experiments with input icc profiles. Same default is set if this parameter is omitted.
    If you know that your input profile is sRGB (but it is not embeded - the pdf is plain \DefaultRGB), it might be a good idea to explicitly specify the profile here. Even though sRGB is the default.
  • I use modified gs/lib/PDFX_def.ps from the Ghostscript repo, which embeds cmyk_des_renderintent.icc as the "Output Intent".

You can find all files used in this experiment here. There are several other experiments as well. I've created them trying to understand how Color Management works in gs. I hope they shed some light on the subject. There's also a comparison with Adobe Acrobat "Convert Colors" tool. AFAIU, it does exactly what you expect.

When it comes to Color Management for pdf output, KenS (gs dev) usually says "the pdfwrite device goes to extreme lengths to maintain color specifications from the input unchanged in the output". It looks like they do not really focus on things like conversion from one profile to another in this case. Well... This is hardly "the most requested" feature.

Igor
  • 1,359
  • 19
  • 34