跳到內容
getnextpdf.com

產出可付印的 CMYK 與專色

螢幕色彩是 RGB。付印色彩則不是。當印刷機或打樣 RIP 消費你的 PDF 時,它要的是製程油墨(CMYK)、偶爾的具名油墨(一種專色或 Separation 色彩),以及它應假設之生產條件的宣告。本範例展示 NextPDF 為那個受眾提供的三條色彩發出路徑:

  • 裝置 CMYK 填色與描邊——setFillColorCmyk() / setDrawColorCmyk()
  • 以某個墨量繪製的專色/Separation 油墨——先 registerSpotColor()setSpotFillColor() / setSpotDrawColor()
  • 為整份文件宣告一個 RGB 工作/輸出條件的 ICC 輸出意圖——Config::withOutputColorProfile()。隨附的 profile 是 RGB 工作空間;這並不會宣告一個真正的 CMYK 印刷機/PDF/X 付印條件。

先說範圍:這是色彩發出。NextPDF 會寫入你要求的 CMYK 數值、Separation 空間與輸出意圖宣告。它不會執行色彩管理轉換——它不會把你的 RGB 美術稿重新算繪成目標 CMYK 色域、不會軟體打樣,也不保證視覺相符。請提供已針對你的條件指定好的色彩。

Terminal window
composer require nextpdf/core:^3

不需要任何選用擴充。色彩 API 自 1.2.0 起即穩定,並在 8.1–8.4 backport 矩陣上執行。

CMYK 是平版與數位製程印刷的預設:四個通道,青/洋紅/黃/黑(即「key」)。先設定填色或描邊色彩,然後照常繪製。

<?php
declare(strict_types=1);
require_once __DIR__ . '/vendor/autoload.php';
use NextPDF\Core\Document;
$doc = Document::createStandalone();
$doc->addPage();
// Components are percentages, 0–100 (cyan, magenta, yellow, key).
$doc->setFillColorCmyk(0, 95, 100, 0); // a process "red"
$doc->rect(20, 30, 60, 40, 'F');
$doc->setDrawColorCmyk(100, 0, 0, 0); // pure cyan rule
$doc->setLineWidth(1.0);
$doc->rect(20, 30, 60, 40, 'S');
$doc->setTextColorCmyk(0, 0, 0, 100); // rich-free 100% K text
$doc->setFont('helvetica', '', 12);
$doc->text(20, 85, 'Process CMYK');
$doc->save(getenv('NEXTPDF_COOKBOOK_OUTPUT') ?: __DIR__ . '/cmyk.pdf');

每次呼叫都會把一個 DeviceCMYK 色彩運算子發出到內容串流中:k 用於非描邊(填色/文字)色彩,K 用於描邊色彩,四個成分皆縮放至 PDF 內部使用的 0.0–1.0 範圍。ISO 32000-2 §8.6.8(色彩運算子,表 73)把 kK 定義為 DeviceCMYK 的色彩設定運算子;§8.6.4.4 則定義 DeviceCMYK 色彩空間本身。

底層的值物件是 NextPDF\Graphics\Color。如果你直接建立色彩,Color::cmyk($c, $m, $y, $k) 接受相同的 0–100 百分比,而它正是每個 …Cmyk 文件方法所呼叫的。

專色是單一具名油墨——一個 Pantone、一個 HKS、一層上光、一塊模切「刀」版——印刷機把它當作自己的印版裝載,而非由製程油墨建構。在 PDF 中它是一個 Separation 色彩空間:一個著色劑名稱,加上一個替代空間(這裡是 DeviceCMYK),以及一個把 [0, 1] 中的墨量值映射到該替代空間的墨量轉換,因此非專色算繪器仍可顯示一個近似值。

以其 CMYK 回退色註冊油墨一次,然後以某個墨量百分比把它設為填色或描邊色彩:

<?php
declare(strict_types=1);
require_once __DIR__ . '/vendor/autoload.php';
use NextPDF\Core\Document;
$doc = Document::createStandalone();
$doc->addPage();
// Register the ink and its CMYK fallback (percentages, 0–100).
$doc->registerSpotColor('PANTONE 485 C', 0, 95, 100, 0);
// Full-strength fill.
$doc->setSpotFillColor('PANTONE 485 C'); // tint defaults to 100
$doc->rect(20, 30, 50, 30, 'F');
// 40% tint of the same ink.
$doc->setSpotFillColor('PANTONE 485 C', 40);
$doc->rect(80, 30, 50, 30, 'F');
// Same ink as a stroke at 75%.
$doc->setSpotDrawColor('PANTONE 485 C', 75);
$doc->setLineWidth(1.5);
$doc->line(20, 75, 130, 75);
$doc->save(getenv('NEXTPDF_COOKBOOK_OUTPUT') ?: __DIR__ . '/spot.pdf');

你必須在選取某個專色前先 registerSpotColor() 它;未註冊的名稱會拋出 PageLayoutException。註冊會寫入 Separation 資源與墨量轉換;setSpotFillColor() / setSpotDrawColor() 接著會對那個已註冊的 Separation 資源,為填色發出 /CS_<token> cs <tint> scn(或大寫的描邊形式 /CS_<token> CS <tint> SCN)。這裡牽涉兩個不同的名稱,而引擎分別處理它們:

  • 資源鍵——內容串流運算子所參照、且頁面的 /Resources /ColorSpace 字典所依的那個 /CS_… 標記——是把油墨名稱中每個非字元字元替換為 _ 而衍生的,因此 'PANTONE 485 C' 選取資源 /CS_PANTONE_485_C。(對於含有字面 _、連字號或其他標點的油墨名稱,會附加一個簡短的決定性後綴以保持鍵的無衝突,因此兩個近乎相同的名稱絕不會共用一個色彩空間。)
  • Separation 著色劑名稱本身——攜帶在 [/Separation /<name> …] 色彩空間陣列內的名稱——會被原樣保留,並由寫入器編碼為一個 PDF name 物件,對任何分隔符或非列印位元組做十六進位跳脫(#XX)。它不會被扁平化為 CS_… 標記;資源鍵與著色劑名稱是各自獨立計算的。

你傳入的墨量引數是一個百分比,0(紙張)到 100(滿墨),但寫入內容串流的運算元是正規化後0.0–1.0 值,因此一個 40 的墨量會發出 /CS_PANTONE_485_C cs 0.400000 scn。ISO 32000-2 §8.6.6.4 涵蓋 Separation 色彩空間及其墨量轉換。

預設的墨量轉換是從 [0 0 0 0](墨量 0 的紙張)到已註冊 CMYK 回退色(墨量 1 的滿墨)的線性內插。那對於一般的專色油墨是正確的;非線性的油墨或一個量測得到的 profile 需要自訂轉換,而那超出本範例的範圍。

PDF 可攜帶一個文件層級的宣告,說明其色彩是為哪個色彩條件而準備的——一個輸出意圖:一個指名生產條件的字典,並把目標 ICC profile 以一個 ICCBased 串流嵌入。在一個真正的印刷/PDF-X 工作流程中,這是一個 CMYK 印刷機條件(例如一個塗佈的 FOGRA 或 GRACoL profile)。然而,NextPDF 隨附的 profile 是 RGB 工作空間——因此 Config::withOutputColorProfile() 所宣告的,是一個 RGB 檢視/工作空間輸出條件,而非一個 CMYK 目標。在你依賴它做印刷輸出之前,請見範例下方的備註。

NextPDF 透過文件的 Config 揭露這項功能。挑選一個隨附的工作空間 profile、建立 config,然後從它建立文件:

<?php
declare(strict_types=1);
require_once __DIR__ . '/vendor/autoload.php';
use NextPDF\Core\Config;
use NextPDF\Core\Document;
use NextPDF\Core\OutputColorProfile;
// Declare an explicit, embedded output intent for the document.
$config = (new Config())
->withOutputColorProfile(OutputColorProfile::Srgb);
$doc = Document::createStandalone($config);
$doc->addPage();
$doc->setFillColorCmyk(0, 95, 100, 0);
$doc->rect(20, 30, 60, 40, 'F');
$doc->save(getenv('NEXTPDF_COOKBOOK_OUTPUT') ?: __DIR__ . '/with-intent.pdf');

OutputColorProfile 是引擎隨附 profile 之工作空間的列舉。所有由 profile 支援的案例都是三成分的 RGB 工作空間;DeviceRGB 是預設哨兵,且不發出輸出意圖。 沒有隨附的 CMYK 目標 profile:

  • DeviceRGB——預設值。發出輸出意圖:不宣告任何 PDF 層級的輸出條件,而 PDF/A 管線(若作用中)保有對 /OutputIntents 陣列的獨佔控制。當你不想宣告任何意圖時使用它。(沒有輸出意圖的 PDF DeviceRGB 內容是裝置相依的——它並非一個已宣告的 sRGB。)
  • Srgb——發出一個嵌入隨附 sRGB.icc 的輸出意圖字典,帶有標準條件識別碼 sRGB IEC61966-2.1
  • DisplayP3Rec2020A98RGBProphotoRGB——廣色域 RGB 工作空間,各自在一個自訂(NextPDF wide-gamut …)條件識別碼下嵌入其隨附的 ICC profile。

DeviceRGB 以外的任何案例,都會讓寫入器發出一個參照所嵌入 ICCBased 串流(帶其 /N 3 成分計數)的輸出意圖字典。ISO 32000-2 §14.11.5 定義輸出意圖字典;§8.6.5.5 定義攜帶嵌入 profile 的 ICCBased 色彩空間。在目前的引擎中,無論你挑選哪個隨附 profile,這個字典都以 PDF/X 輸出意圖子類型 /GTS_PDFX 寫入(PDF/A 封存路徑使用它自己的 /GTS_PDFA1 子類型,並另行發出)。

重要的告誡:由於所有隨附 profile 都是 RGB,這宣告的是文件的 RGB 工作空間與檢視意圖——它並非一個 CMYK 目標 profile,也不會把任何東西轉換成 CMYK。引擎不允許你透過 withOutputColorProfile() 提供自訂的 CMYK 目標 ICC。一個真正的印刷/PDF-X CMYK 輸出意圖需要一個把你自己的 CMYK ICC profile 嵌為目標的工作流程;至於接入同一個 /OutputIntents 陣列的封存輸出意圖,請見 PDF/A-4 輸出

  • 裝置 CMYK——任何要送往製程印刷機之美術稿的預設。請從一開始就以 CMYK 指定你的色彩,讓下游不會發生任何 RGB→CMYK 的臆測。
  • 專色/Separation——必須命中確切油墨的品牌色彩,外加非製程印版(上光、白墨、金屬色、模切、燙金)。註冊一次,以任何墨量繪製。
  • 輸出意圖——當你想要檔案就其 RGB 工作/輸出條件自我描述,或當某個消費者(一個檢視器、一個色彩管理的 RIP、一個驗證器)預期一個已宣告的輸出條件時設定它。隨附的 profile 只宣告一個 RGB 工作/輸出條件;它們不宣告一個真正的 CMYK 印刷機/PDF/X 付印條件。
  • CMYK 成分是百分比(0–100),不是 0–1。 …Cmyk 文件方法與 Color::cmyk() 把每個通道當作 0–100 百分比,並在寫入運算子時除以 100;內容串流運算元是正規化後的 0.0–1.0 值。滿墨請傳 100,而非 1.0(引擎會把它視為 1% 的墨)。
  • 在選取專色之前先註冊。 若名稱從未註冊,setSpotFillColor() / setSpotDrawColor() 會拋出例外。名稱以精確方式比對,包含大小寫與空格。
  • 色彩狀態會持續。 一個 CMYK 或專色色彩會持續生效,直到你改變它。在一個不相關的區塊之前先重設。
  • CMYK 回退色是一個近似值。 Separation 墨量轉換之所以存在,是為了讓非專色算繪器能顯示某些東西;它並非印刷機輸出。真正的油墨是那塊具名印版所產生的。
  • 輸出意圖是一個宣告,不是一個轉換。 宣告 OutputColorProfile::Srgb 不會把你的色彩轉換成 sRGB;它陳述的是預期的條件。色彩準確度是你在上游的責任。

每次色彩選取都是單一的內容串流運算子;專色另外為每種已註冊油墨寫入一個 Separation 資源。一個嵌入的輸出意圖 profile 每份文件寫入一次。所有路徑都遠在 2000 ms / 64 MB 的預算之內。

本範例只發出你程式碼所指定的色彩與 profile。它不剖析任何不受信任的輸入,也不進行任何網路存取。如果著色劑名稱或 CMYK 成分來自外部資料,請驗證它們:把成分夾限至 0–100,並拒絕專色名稱中的控制字元(Separation 名稱中的 NUL 位元組會被引擎拒絕)。

陳述規範條款
kK 是設定 DeviceCMYK 非描邊/描邊色彩的色彩運算子。ISO 32000-2§8.6.8
DeviceCMYK 是減色式的四成分製程色彩空間。ISO 32000-2§8.6.4.4
一個 Separation 色彩空間指名一個著色劑,其墨量經由墨量轉換映射至一個替代空間。ISO 32000-2§8.6.6.4
一個 ICCBased 色彩空間嵌入一個帶 /N 成分計數的 ICC profile 串流。ISO 32000-2§8.6.5.5
一個輸出意圖宣告目標生產條件;GTS_PDFX 指名付印子類型。ISO 32000-2§14.11.5

可重現性 profile——structural。 色彩發出本身沒有熵,但每份儲存的文件都攜帶一個 trailer /ID 與日期原子,而一個嵌入的 ICC 串流只有在固定的隨附 profile 下才是位元組穩定的。所支援的主張是 qpdf 正規化後的結構相等。本範例描述 NextPDF 如何產出該結構;它不斷言全面的 ISO 32000-2 規範性。

不適用。裝置 CMYK、專色/Separation 色彩與輸出意圖宣告都是 Core 功能,無 Premium 閘門。Core 支援此處所示的隨附 RGB 輸出意圖宣告;自訂 CMYK 付印條件 ICC 工作流程不在本範例的主張之內。