また、翻訳もご覧ください。
Copyright © 1996-2025 World Wide Web Consortium. W3C® liability, trademark and permissive document license rules apply.
本書はPNG(ポータブル・ネットワーク・グラフィックス)について説明します。PNGは、ロスレスで移植性に優れ、高効率に圧縮された静止画およびアニメーションラスタ画像の拡張可能なファイルフォーマットです。PNGはGIFの特許フリーな代替となり、TIFFの多くの一般的な用途も置き換えることができます。インデックスカラー、グレースケール、トゥルーカラー画像、およびオプションのアルファチャンネルをサポートします。サンプルのビット深度は1〜16ビットです。
PNGは、ワールド・ワイド・ウェブなどオンラインでの閲覧アプリケーションでの利用を想定して設計されており、プログレッシブ表示オプション付きで完全なストリーム配信に対応しています。PNGは堅牢で、ファイル全体の整合性チェックや、一般的な伝送エラーの簡易検出を提供します。また、異種プラットフォーム間での色再現性向上のためカラースペース情報の格納も可能です。
本仕様では、Internet Media Types「image/png」と「image/apng」の2種類を定義します。
このセクションは、本書が公開された時点での文書のステータスを示します。現在のW3Cの公開文書や本技術レポートの最新版は、W3C 標準・草案インデックス(https://www.w3.org/TR/)でご覧いただけます。
本仕様は国際規格となることを意図していますが、現時点ではまだ国際規格ではありません。本仕様を国際規格として参照することは適切ではありません。
本書は、Portable Network Graphics (PNG) ワーキンググループによって、勧告プロセスを用いて勧告として公開されました。
W3C勧告は、十分な合意形成の後、W3Cとそのメンバーにより承認され、ワーキンググループのメンバーによるロイヤリティフリー・ライセンスでの実装へのコミットメントがあります。
W3Cは本仕様をWebの標準として広く展開することを推奨します。
本書は、W3C特許ポリシーの下で運営されているグループによって作成されました。 W3Cは、グループ成果物に関連してなされた公開特許開示リストを維持しています。このページには、特許開示の方法も記載されています。ある特許について「必須クレーム」を含むと信じる個人は、W3C特許ポリシー第6節に従い、その情報を開示しなければなりません。
この文書は、2023年11月3日版 W3Cプロセス文書に準拠しています。
本仕様の設計目標は以下の通りです:
本仕様は、個々のコンピュータグラフィックス画像やフレームベースアニメーションを、ロスレスで移植性があり圧縮された形でインターネット上で伝送するための、データストリームおよび関連ファイルフォーマットであるPortable Network Graphics(PNG、発音は「ピン」)を規定します。
本仕様で使用する用語の定義は次の通りです。
色度は輝度を問わず色の質を示す指標です。
前景画像は背景に対して合成されると言う。
出典: [RFC1951]
ソフトウェアは画像をフレームバッファに読み込むことで画面に表示させます。
0および2bit depth -
1に対応する画像。
輝度と色度の両方で色を完全に定義できます。正式な定義は[COLORIMETRY]を参照。
0および2bit depth - 1に対応しない画像。
PNGではRGBのみ利用可能であり、ICtCpはサポートされません。
0〜231-1の範囲に制限された4バイトの符号なし整数。
一部言語で4バイト符号なし値の扱いが困難なため、この制限があります。
ネットワークバイト順の2バイト符号なし整数。
スタンダードダイナミックレンジはプライマリ(色域)と独立しており、PNGは広色域SDR形式もサポートします。
deflate系の圧縮方式。
出典: [rfc1950]
この方式のサンプル実装を含むライブラリ名も意味します。
伝送エラーのほとんどを検出できるチェック値の一種。
デコーダは受信データのCRCを計算し、エンコーダが付加したCRCと比較してチェックします。一致しない場合はデータまたはCRCが破損していることを示します。
すべてのPNG画像には1つの静止画像が含まれます。
一部のPNG画像(Animated PNG(APNG)と呼ばれる)には、フレームベースのアニメーションシーケンス、すなわちアニメーション画像も含まれます。これは最初のフレームが—そうである場合も、そうでない場合もあります—静止画像であることがあります。アニメーション非対応の表示装置(プリンタなど)は、アニメーションシーケンスではなく静止画像を表示します。
本仕様はPNGデータストリームを規定し、PNGデータストリームを生成するPNGエンコーダ、PNGデータストリームを解釈するPNGデコーダ、および一つのPNGデータストリームを別のPNGデータストリームに変換するPNGエディタに対していくつかの要件を課します。アプリケーションとPNGエンコーダ/デコーダ/エディタ間のインタフェースは規定しません。エンコーダに提示される、またはデコーダにより出力される画像の正確な形式も規定しません。ここでは4種類の画像を区別します。
この4種類の画像の関係は、Figure 1に示します。
サンプル、チャネル、ピクセル、およびサンプル深度の関係は、Figure 2に示します。
色サンプルが位置付けられるRGBカラースペースは、次の4つの方法のいずれかで指定できます。
ハイエンド用途では、最初の2つの方法が最も柔軟性と制御性を提供します。3つ目の方法は特定の(しかし非常に一般的な)カラースペースを示すのに有効です。4つ目の方法はICCプロファイルが広く採用される以前に標準化されたもので、RGBデータの正確な色度をガンマ補正とともに指定できます(C. ガンマと色度参照)。ただし、色管理対応アプリケーションは通常、最初の3つのいずれかを優先し、色管理非対応アプリケーションは通常、これら4つすべてを無視します。
Table 1は、カラースペース情報を提供するチャンクタイプの一覧で、それぞれに優先度(Priority)を割り当てています。単一の画像にこれらのチャンクタイプが複数含まれる場合、最も小さい優先度番号のチャンクが優先され、番号が大きいチャンクタイプは無視されるべきです。
| チャンクタイプ | 優先度 |
|---|---|
| cICP | 1 |
| iCCP | 2 |
| sRGB | 3 |
| cHRM と gAMA | 4 |
ガンマ補正は、アルファチャネルが存在してもアルファチャネルには適用されません。アルファサンプルは常にフルレンジで、完全不透明に対する線形の割合を表します。
マスタリング用のメタデータを提供してもかまいません。
エンコード対象のPNG画像を作成するために、参照画像に複数の変換を適用します(Figure 3参照)。変換は次の順序で適用され、角括弧は任意であることを示します。
[alpha separation]
indexing or ( [RGB merging] [alpha compaction] )
sample depth scaling
すべてのピクセルが完全透過または完全不透明のいずれかである場合、アルファ分離、アルファ圧縮、および インデックス化の変換により、復元された参照画像のアルファのサンプル深度が元の参照画像と異なる、またはアルファチャネルがなくなることがあります。これはどのピクセルの不透明度の程度にも影響しません。両者の参照画像は等価と見なされ、これらの変換はロスレスと見なされます。それでもアルファのサンプル深度を保持したいエンコーダは、アルファのサンプル深度を変更する変換を行わない選択ができます。
参照画像内のすべてのアルファサンプルが最大値である場合、アルファチャネルは省略でき、よりコンパクトにエンコード可能な等価の画像になります。
異なるピクセル値の数が256以下で、RGBのサンプル深度が8を超えず、かつアルファチャネルが存在しない、またはちょうど8ビット長である、またはすべてのピクセルが完全透過か完全不透明のいずれかである場合、インデックスカラー表現(インデックス化変換により得られる)がエンコードにおいてより効率的となることがあります。 インデックスカラー表現では、各ピクセルはパレットへのインデックスに置き換えられます。パレットは、8ビットのサンプル(赤・緑・青)3つを含むエントリのリストです。アルファチャネルが存在する場合、8ビットのアルファサンプルからなる並行の表(アルファテーブル)も存在します。
PNG画像がインデックスカラーでない場合でも、限られた色数しか表示できないビューアを支援するために、推奨パレットを作成してもかまいません。
インデックスカラー画像では、エンコーダはアルファ値が最大のテーブルエントリが末尾にまとまるようにパレットを並べ替えることができます。この場合、これらのエントリを省いた短縮形式でテーブルをエンコードできます。
インデックスカラーのPNGを作成するエンコーダは、パレットテーブルの実際の長さを超えるインデックス値を挿入してはなりません。これはエラーであり、デコーダのエラー処理はまちまちです。
赤・緑・青のチャネルのサンプル深度が同じで、かつ各ピクセルにおいて赤・緑・青サンプルの値が等しい場合、これら3つのチャネルは単一のグレースケールチャネルに結合できます。
非インデックス画像において、あるRGB(またはグレースケール)値を持つすべてのピクセルが完全に透過で、それ以外のすべてのピクセルが完全に不透明であるような値が存在する場合、アルファチャネルは、その透過となるRGB(またはグレースケール)値を特定するだけで、よりコンパクトに表すことができます。
PNG画像では、すべてのサンプル深度がサポートされているわけではありません(6.1 カラータイプと値参照)。また、すべてのチャネルは同じサンプル深度でなければなりません。PNG画像のすべてのチャネルは、参照画像内のいずれのサンプル深度よりも小さくない最小の許容サンプル深度を使用し、参照画像の可能なサンプル値をPNG画像での次の許容範囲に線形に写像します。Figure 5は、深度3のサンプルが深度4のサンプルにどのように写像されるかを示します。
許容されるサンプル深度を少数に限定することで、デコーダが対処すべきケース数を減らせます。サンプル深度のスケーリングは可逆でデータ損失はありません。これは参照画像のサンプル深度をPNGデータストリームに記録できるためです。サンプル深度の記録がない場合、参照画像のサンプル深度はPNG画像のサンプル深度に等しくなります。12.4 サンプル深度スケーリングおよび13.12 サンプル深度の再スケーリングを参照してください。
参照画像の変換結果は、5種類のPNG画像のいずれかになります(Figure 6参照):
各ピクセルのフォーマットは、PNG画像タイプとビット深度に依存します。インデックスカラー以外のPNG画像タイプでは、ビット深度はピクセルあたりの総ビット数ではなく、サンプルあたりのビット数を指定します。インデックスカラー画像では、ビット深度はパレットインデックスのビット数を指定し、パレット内の色やアルファテーブルのサンプル深度を指定するものではありません。ピクセル内でのサンプルの順序は、PNG画像タイプに応じて次の通りです。
PNG画像をエンコードするプロセスの概念モデルをFigure 7に示します。各ステップは、PNG画像内のピクセルまたはインデックスの配列に対する操作を指します。パレットやアルファテーブルは、この方法ではエンコードされません。
パス抽出(Figure 7参照)は、PNG画像を縮小画像の列に分割します。最初の画像が粗いビューを定義し、後続の画像がそれを順次改善し、最後の画像でPNG画像が完成します。縮小画像の集合はインターレースPNG画像とも呼ばれます。本仕様では2つのインターレース方式を定義します。1つ目はヌル方式で、ピクセルは左から右へ、スキャンラインは上から下へ順に格納されます。2つ目は画像に対して複数回の走査を行い、7つの縮小画像列を生成します。サンプル画像の7つのパスはFigure 7に示します。8. インターレースとパス抽出を参照してください。
スキャンラインと呼ばれる各ピクセル行は、バイト列として表現されます。
PNGでは、圧縮前に画像データにフィルタ処理を適用できます。フィルタ処理はデータの圧縮効率を高める場合があります。フィルタ操作は決定的で可逆かつロスレスです。これにより、伸長後のデータを逆フィルタすることで元のデータを得られます。7.3 フィルタ処理を参照してください。
PNG画像の各パス(複数パスがある場合はそれら)のフィルタ済みスキャンライン列は、定義された圧縮方式のいずれかで圧縮されます(Figure 9参照)。連結されたフィルタ済みスキャンラインが圧縮段階への入力となり、圧縮段階の出力は単一の圧縮データストリームになります。10. 圧縮を参照してください。
チャンク化は、圧縮データストリームを扱いやすいサイズのチャンクに分割するための便利な手段です(Figure 9参照)。各チャンクには独自の冗長性チェックが付与されます。11. チャンク仕様を参照してください。
画像には補助情報を関連付けることができます。デコーダは、補助情報の全部または一部を無視してもかまいません。提供される補助情報の種類は、Table 2に記載しています。
| 情報の種類 | 説明 |
|---|---|
| アニメーション情報 | フレームの連なりと、それに関連するタイミング、位置、処理情報で定義されるアニメーション画像。ビューアが対応している場合に表示されます。プリンタなどの他のケースでは、静止画像が代わりに表示されます。 |
| 背景色 | より適切な選択肢がない場合に画像表示に用いる単色の背景色。 |
| コーディング非依存コードポイント | 伝達関数や色の原色などのメタデータを列挙してカラースペースを識別します。 もとはSDRやHDRビデオ向けですが、静止画像やアニメーション画像にも使用されます。 |
| コンテンツ光度情報 | 画像(または画像列)中で最も明るいピクセルの輝度と、列の中で最も明るいフレームの平均輝度レベル。 |
| EXIF情報 | シャッタースピード、絞り、向きなどのExchangeable image file formatメタデータ。 |
| ガンマと色度 | 望ましい出力強度に対する画像のガンマ値、および画像で使用されるRGB値の色度特性。 |
| ICCプロファイル | 画像内のサンプルが準拠するカラースペース(International Color Consortium(ICC)プロファイルの形)の記述。 |
| 画像ヒストグラム | 各パレットエントリが画像でどの程度使用されるかの推定。 |
| マスタリングディスプレイ色域 | コンテンツの制作に用いられたディスプレイの絶対的な3次元カラーボリューム(マスタリングディスプレイが再現可能な最も明るい色と暗い色を含む)の記述。表示装置上での画像提示に役立ちます。 |
| 物理ピクセル寸法 | PNG画像の提示に用いる意図したピクセルサイズとアスペクト比。 |
| 有効ビット | サンプル内で有効なビット数。 |
| sRGBカラースペース | (International Color Consortiumで定義される)レンダリングインテントと、画像サンプルがこのカラースペースに準拠していることの指示。 |
| 推奨パレット | 表示装置が画像の全色域を表示できない場合に使用できる縮小パレット。 |
| テキストデータ | 画像に関連付けられた(圧縮されている場合がある)テキスト情報。 |
| 時刻 | PNG画像が最後に変更された時刻。 |
| 透過 | PNG画像にアルファチャネルが保持されない場合に、参照画像の再構成を可能にするアルファ情報。 |
PNGデータストリームは、PNGシグネチャ(5.2 PNGシグネチャ参照)に続くチャンクの列(11. チャンク仕様参照)で構成されます。各チャンクには、その機能を指定するチャンクタイプがあります。
チャンクタイプは4バイトの並びで、ISO 646.IRV:1991([ISO646])文字集合として解釈したときに可読ラベルに対応するように選ばれます。最初の4つはクリティカルチャンクと呼ばれ、本仕様の規定に従って理解され、正しく解釈されなければなりません。これらは次の通りです。
残りのチャンクタイプは補助チャンクタイプと呼ばれ、エンコーダは生成でき、デコーダは解釈してもかまいません。
Animated PNG(APNG)は、元の静止のみのPNGフォーマットを拡張し、フレームベースのアニメーション画像をサポートします。これは従来GIFフォーマット([GIF])が用いられてきた単純なアニメーション画像の代替を意図しており、GIFにはない24ビット画像や8ビット透過もサポートします。
APNGはPNGの以前のバージョンとの後方互換性を備えています。非アニメーション対応のPNGデコーダは、APNG特有の補助チャンクを無視して静止画像を表示します。
APNGストリームは、PNG仕様の以前の版で定義された通常のPNGストリームに、アニメーションを記述し追加のフレームデータを提供する3種類のチャンクタイプを追加したものです。
APNGとして認識されるためには、acTLチャンクがストリーム中の任意のIDATチャンクより前に現れなければなりません。acTLの構造は後述します。
各再生の開始時点では、概念的に出力バッファは、IHDRチャンクの幅と高さに基づく寸法の、完全に透過な黒の長方形として完全に初期化されます。
IDATの前に単一のfcTLチャンクが存在することにより、静止画像をアニメーションの最初のフレームとして含めることができます。そうでない場合、静止画像はアニメーションの一部ではありません。
後続フレームはfdATチャンクにエンコードされ、これはIDATチャンクと同じ構造ですが、前にシーケンス番号が付きます。各フレームの配置とレンダリングに関する情報はfcTLチャンクに格納されます。fdATおよびfcTLチャンクの詳細な構造は後述します。
アニメーション全体の境界は、デフォルト画像がアニメーションの一部かどうかに関係なく、IHDRチャンクの幅と高さのパラメータで指定されます。デフォルト画像は、後続フレームに追加のスペースが必要になる場合、完全に透過な黒のピクセルで適切にパディングされるべきです。
各フレームは各再生において同一であるため、アプリケーションがフレームをキャッシュしても安全です。
fcTLおよびfdATチャンクには、ゼロ基準の4バイトのシーケンス番号があります。両チャンクタイプは同じ番号系列を共有します。この番号の目的は、補助チャンクの順序に制限を課さない本仕様において、Animated PNGのシーケンスエラーを検出(および任意に修正)することです。
最初のfcTLチャンクはシーケンス番号0を含み、残りのfcTLおよびfdATチャンクのシーケンス番号は、欠落や重複なしに昇順でなければなりません。
以下の表は、複数フレームを持つ画像や、2番目のフレームに複数のfdATチャンクがある場合のシーケンス番号の使用例を示します。(明瞭さのため、IHDRおよびIENDチャンクは省略しています。)
| シーケンス番号 | チャンク |
|---|---|
| (なし) | acTL |
| 0 | fcTL 最初のフレーム |
| (なし) | IDAT 最初のフレーム/静止画像 |
| 1 | fcTL 2番目のフレーム |
| 2 | 2番目のフレームの最初のfdAT |
| 3 | 2番目のフレームの2番目のfdAT |
| シーケンス番号 | チャンク |
|---|---|
| (なし) | acTL |
| (なし) | IDAT 静止画像 |
| 0 | fcTL 最初のフレーム |
| 1 | 最初のフレームの最初のfdAT |
| 2 | 最初のフレームの2番目のfdAT |
| 3 | fcTL 2番目のフレーム |
| 4 | 2番目のフレームの最初のfdAT |
| 5 | 2番目のフレームの2番目のfdAT |
出力バッファは、PNGのIHDRチャンクの幅と高さパラメータで指定される寸法のピクセル配列です。概念的には、各フレームはキャンバスへ合成される前に出力バッファ内で構築されます。出力バッファの内容はデコーダから参照可能です。出力バッファの四隅はキャンバスの四隅に対応付けられます。
キャンバスは、フレームを表示する出力装置上の領域です。キャンバスの内容は、必ずしもデコーダから参照できるとは限りません。bKGDチャンクが存在する場合、より望ましい背景がないときにキャンバスの塗りつぶしに使用してもよいです。
PNGデータストリームのエラーは、一般に次の2つのクラスに分類されます。
PNGデコーダは、可能な限り早期にエラーを検出し、可能な場合はエラーから回復し、そうでない場合は穏やかに失敗すべきです。エラー処理の考え方については、13.1 エラー処理で詳述します。
この節は参考(非規範)です。
PNG形式はいくつかの拡張ポイントを公開しています。
これらの拡張ポイントの一部はW3Cにより予約されており、他は私的利用に開放されています。
PNGデータストリームは、PNGシグネチャに続くチャンク列で構成されます。これはPNG画像をエンコードした結果です。
「ファイル」ではなくデータストリームという用語を用いるのは、バイト列がファイルの一部に過ぎない場合があるためです。また、バイト列が保存ファイルに全く現れず、「オンザフライ」で生成・消費される可能性を強調するためでもあります。
PNGデータストリームの最初の8バイトは常に、次の16進値を含みます。
89 50 4E 47 0D 0A 1A 0A
このシグネチャは、データストリームの残りが単一のPNG画像を含み、IHDRチャンクで始まりIENDチャンクで終わる一連のチャンクから構成されていることを示します。
このシグネチャにより、PNGデータストリームは他の種類のデータストリームと区別され、いくつかの伝送エラーを早期に検出できるようになります。
各チャンクは3つまたは4つのフィールドで構成されます(Figure 10参照)。各フィールドの意味はTable 5に記載されています。チャンクデータフィールドは空であっても構いません。
| 名称 | 説明 |
|---|---|
| 長さ | PNG 4バイト符号なし整数で、チャンクのデータフィールド内のバイト数を示します。長さはデータフィールドのみを数え、長さ自身、チャンクタイプ、CRCは含みません。ゼロも有効な長さです。エンコーダとデコーダは長さを符号なしとして扱うべきですが、その値は231-1バイトを超えてはなりません。 |
| チャンクタイプ |
チャンクタイプを定義する4バイトの並びです。チャンクタイプの各バイトは、16進値41〜5Aおよび61〜7Aに制限されます。これは、説明やPNGデータストリームの検査の便宜上、ISO
646 [ISO646]の大文字・小文字に対応します(A-Zおよびa-z)。エンコーダおよびデコーダは、チャンクタイプを文字列ではなく固定のバイナリ値として扱わなければなりません。例えば、チャンクタイプIDATをUCS
2文字集合内のそれらの文字に相当するもので表現するのは正しくありません。チャンクタイプの追加の命名規則については、5.4
チャンクの命名規則で述べます。
|
| チャンクデータ | 該当する場合、チャンクタイプに応じたデータバイト。 このフィールドは長さゼロであり得ます。 |
| CRC | チャンク内の直前のバイト(チャンクタイプフィールドおよびチャンクデータフィールドを含むが、長さフィールドは含まない)に対して計算される4バイトのCRCです。CRCはデータの破損チェックに利用できます。データを含まないチャンクでも、CRCは常に存在します。5.5 CRCアルゴリズムを参照してください。 |
チャンクデータの長さは最大値まで任意のバイト数になり得るため、実装者はバイトより大きな境界にチャンクが整列していると仮定してはなりません。
チャンクタイプは、そのバイトをISO 646の文字 [ISO646]として解釈したときに意味のある名称になるように選ばれます。チャンクタイプは、タイプが認識されない場合でもデコーダがチャンクの性質をある程度判断できるように割り当てられています。これらの規則により、PNGデコーダが未知のチャンクに遭遇した際の扱いを決定できるため、PNG形式の安全で柔軟な拡張が可能になります。
命名規則は通常、13. PNGデコーダとビューアで規定されるように、デコーダがチャンクタイプを認識しない場合にのみ関心の対象となります。
チャンクタイプの4つのビット、すなわち各バイトの第5ビット(値32)がプロパティビットとして、チャンクの性質を伝えるために使用されます。この選択により、人間がチャンクタイプの各バイトに対応する文字が大文字(ビット5が0)か小文字(ビット5が1)かによって、割り当てられた性質を読み取れます。
プロパティビットはチャンクタイプ固有の一部であり、したがって任意のチャンクタイプに対して固定です。したがって、CHNKとcHNkは、同じチャンクが異なる性質を持つのではなく、関連のない別個のチャンクタイプです。
プロパティビットの意味はTable 6に定義されています。
| 名称と位置 | 定義 | 説明 |
|---|---|---|
| 補助ビット:1バイト目 | 0(大文字)=クリティカル、 1(小文字)=補助。 |
クリティカルチャンクは、データストリームの内容を正しく表示するために必要です(例:画像ヘッダチャンク(IHDR))。デコーダが画像を抽出しようとして、補助ビットが0の未知のチャンクタイプに遭遇した場合、当該画像に安全に解釈できない情報が含まれていることをユーザに示さなければなりません。 補助チャンクは、データストリームの内容を意味のある形で表示するのに厳密には必要ではありません(例:時刻チャンク(tIME))。補助ビットが1の未知のチャンクタイプに遭遇したデコーダは、そのチャンクを安全に無視して画像の表示を続行できます。 |
| プライベートビット:2バイト目 | 0(大文字)=パブリック、 1(小文字)=プライベート。 |
パブリックチャンクはW3Cが定義のために予約しています。プライベートチャンクの定義は、12.10.1 プライベートチャンクの利用に規定されています。プライベートチャンク名の2文字目は小文字、パブリックチャンク名の2文字目は大文字です。 |
| 予約ビット:3バイト目 | この版のPNGでは0(大文字)。 予約ビットが1の場合、そのデータストリームはこの版のPNGに適合しません。 |
チャンク名の3文字目の大文字・小文字の意味は、将来の拡張のために予約されています。この国際規格では、すべてのチャンク名は3文字目が大文字でなければなりません。 |
| コピー安全ビット:4バイト目 | 0(大文字)=コピー非安全、 1(小文字)=コピー安全。 |
このプロパティビットは純粋なデコーダには関係ありませんが、PNGエディタには必要です。このビットは、修正されているデータストリーム内の未認識チャンクの適切な取り扱いを定義します。PNGエディタの規則は、14.2 PNGエディタの動作でさらに議論します。 |
仮想的なチャンクタイプ「cHNk」のプロパティビットは次のとおりです。
cHNk <-- 32 bit chunk type represented in text form
||||
|||+- Safe-to-copy bit is 1 (lower case letter; bit 5 is 1)
||+-- Reserved bit is 0 (upper case letter; bit 5 is 0)
|+--- Private bit is 0 (upper case letter; bit 5 is 0)
+---- Ancillary bit is 1 (lower case letter; bit 5 is 1)
したがって、この名称は、補助・パブリック・コピー安全なチャンクを表します。
CRCフィールドは、[ISO-3309]および[ITU-T-V.42]で定義される事前・事後条件付きの標準化されたCRC手法を用いて計算されます。採用されるCRC多項式(GZIPファイル形式仕様 [RFC1952]で使用されるものと同一)は次の通りです。
x32 + x26 + x23 + x22 + x16 + x12 + x11 + x10 + x8 + x7 + x5 + x4 + x2 + x + 1
PNGでは、32ビットCRCはすべて1で初期化され、各バイトのデータは最下位ビット(1)から最上位ビット(128)へ処理されます。すべてのデータバイトが処理された後、CRCは反転されます(1の補数が取られます)。この値はMSBから順に送信(データストリームに格納)されます。バイトへの分割と順序付けのため、32ビットCRCの最下位ビットは、x31項の係数であると定義されます。
CRCの実用的な計算では、計算を高速化するためにあらかじめ計算されたテーブルがよく用いられます。D. サンプルCRC実装を参照してください。
各チャンクの配置に関する制約はTable 7に一覧し、静止画像についてはFigure 11およびFigure 12に模式的に示します。静止画像が最初のフレームを構成するアニメーション画像については、Figure 13およびFigure 14に、静止画像がアニメーションの一部でない場合はFigure 15およびFigure 16に示します。これらのラティス図は、本仕様によって課される配置上の制約を表します。図中の線は部分順序関係を定義します。上にあるチャンクは下にあるチャンクよりも前に現れなければなりません。水平方向に整列し、他の2種類のチャンク(その水平方向に整列したチャンクよりも上と下にある)に挟まれて現れるチャンクは、それら上位および下位のチャンクタイプの間で、任意の順序で現れて構いません。チャンクタイプに付された上付き文字の意味はTable 8で定義されます。これは、チャンクが必須か任意か、複数回現れ得るかを示します。2つのチャンクタイプの間の縦棒は代替を示します。
| クリティカルチャンク (この順序で現れなければならない。PLTEは任意) |
||
|---|---|---|
| チャンク名 | 複数可 | 順序制約 |
| IHDR | いいえ | 最初でなければならない |
| PLTE | いいえ | 最初のIDATの前 |
| IDAT | はい | 複数のIDATチャンクは連続していなければならない |
| IEND | いいえ | 最後でなければならない |
| 補助チャンク (この順序で現れる必要はない) |
||
| チャンク名 | 複数可 | 順序制約 |
| acTL | いいえ | IDATの前 |
| cHRM | いいえ | PLTEおよびIDATの前 |
| cICP | いいえ | PLTEおよびIDATの前 |
| gAMA | いいえ | PLTEおよびIDATの前 |
| iCCP | いいえ | PLTEおよびIDATの前。iCCPチャンクが存在する場合、sRGBチャンクは存在すべきではありません。 |
| mDCV | いいえ | PLTEおよびIDATの前 |
| cLLI | いいえ | PLTEおよびIDATの前 |
| sBIT | いいえ | PLTEおよびIDATの前 |
| sRGB | いいえ | PLTEおよびIDATの前。sRGBチャンクが存在する場合、iCCPチャンクは存在すべきではありません。 |
| bKGD | いいえ | PLTEの後;IDATの前 |
| hIST | いいえ | PLTEの後;IDATの前 |
| tRNS | いいえ | PLTEの後;IDATの前 |
| eXIf | いいえ | IDATの前 |
| fcTL | はい | 1つはIDATの前に現れてもよい;他はすべてIDATの後でなければならない |
| pHYs | いいえ | IDATの前 |
| sPLT | はい | IDATの前 |
| fdAT | はい | IDATの後 |
| tIME | いいえ | なし |
| iTXt | はい | なし |
| tEXt | はい | なし |
| zTXt | はい | なし |
| 記号 | 意味 |
|---|---|
| + | 1回以上 |
| 1 | 1回のみ |
| ? | 0回または1回 |
| * | 0回以上 |
| | | 代替 |
すべてのチャンク(プライベートおよびパブリック)は、[PNG-EXTENSIONS]に一覧化されるSHOULDです。
パブリックチャンクはW3Cが定義のために予約しています。
パブリックチャンクは、PNGの理念に合致する広範な利用を意図しています。
組織やアプリケーションは、上記の基準を満たす任意のチャンクをPNGワーキンググループにパブリックチャンクとして定義するため提出することが推奨されます。
パブリックチャンクとしての定義は自動的でも即時でもありません。提案されたパブリックチャンクタイプは、そのように定義されるまでは、公的に利用可能なソフトウェアやデータストリームで使用SHALLありません。
新たなクリティカルチャンクタイプの定義は、必要な場合を除き非推奨です。
組織およびアプリケーションは、プライベートおよび実験的な用途のためにプライベートチャンクを定義することMAYです。
プライベートチャンクは、人間のユーザにとってのみ関心のあるテキスト情報を運ぶためだけに定義SHOULD NOTです。代わりにiTXtチャンクを使用SHOULD BEし、対応するキーワードを使用SHOULD BEし、適切なキーワードを定義してください。
プライベートチャンクを[PNG-EXTENSIONS]に一覧化することは、同じプライベートチャンクが異なるアプリケーションで非互換な目的に使われる可能性を減らしますが、完全には排除しません。プライベートチャンクタイプを使用する場合、競合のリスクをさらに減らすために、追加の識別情報をチャンクデータの先頭に保存SHOULD BEです。
画像の表示に絶対不可欠ではない情報を保存するすべてのプライベートチャンクには、クリティカルチャンクタイプではなく補助チャンクタイプを使用SHOULDです。
プライベートクリティカルチャンクは定義SHOULD NOTです。なぜなら、そのようなチャンクを含むPNGデータストリームは移植性がなく、公的に利用可能なソフトウェアやデータストリームで使用SHOULD NOTだからです。プライベートクリティカルチャンクがアプリケーションにとって不可欠な場合は、標準デコーダがデータストリームを処理できないと早い段階で判明するように、データストリームの先頭付近に現れるSHOULDです。
プライベートチャンクの定義に関する追加の指針については、B. プライベートチャンクタイプに関するガイドラインを参照してください。
次のフィールドにおいて、128以上の値はプライベートフィールド値です。
これらのプライベートフィールド値は、本仕様では定義も予約もされていません。
プライベートフィールド値は、実験的またはプライベートな意味のために使用MAYです。
プライベートフィールド値は、PNGデコーダで読み取り不能なデータストリームを生じ得るため(13. PNGデコーダとビューア参照)、公的に利用可能なソフトウェアやデータストリームには出現SHOULD NOTです。
4.5 PNG画像で説明したように、PNG画像には5種類があります。 各タイプに対応して、カラータイプがあり、これは次の値の総和です:1(パレット使用)、2(トゥルーカラー使用)、4(アルファ使用)。グレースケールおよびトゥルーカラー画像は明示的なアルファチャネルを持つことがあります。PNG画像タイプと対応するカラータイプはTable 9に示します。
| PNG画像タイプ | カラータイプ |
|---|---|
| グレースケール | 0 |
| トゥルーカラー | 2 |
| インデックスカラー | 3 |
| グレースケール(アルファ付き) | 4 |
| トゥルーカラー(アルファ付き) | 6 |
各PNG画像タイプで許可されるビット深度とサンプル深度は、画像ヘッダに示します。
グレースケールサンプルは、転送曲線が(gAMA、 sRGB、iCCP、またはcICPにより)示されている場合は輝度を表し、示されていない場合はデバイス依存のグレースケールを表します。 RGBサンプルは、カラースペースが(gAMAとcHRM、sRGB、iCCP、またはcICPにより)示されている場合はキャリブレーション済みの色情報を表し、示されていない場合は非キャリブレーションのデバイス依存色を表します。
サンプル値は必ずしも光強度に比例しません。gAMAチャンクは、サンプル値と表示出力強度の関係を指定します。ビューアは適切に補正することが強く推奨されます。4.3 カラースペース、13.13 デコーダのガンマ処理、およびC. ガンマと色度を参照してください。
PNGデータストリームにおける透明性の表現は、PNG画像タイプに応じて4通りあります(4.4.1 アルファ分離および4.4.4 アルファ圧縮参照)。
画像配列に含まれるアルファチャネルは、他のサンプルと同じサイズの8ビットまたは16ビットのサンプルを持ちます。各ピクセルのアルファサンプルは、そのピクセルのグレースケールまたはRGBサンプルの直後に格納されます。アルファ値0は完全透過を表し、2sampledepth - 1の値は完全不透明を表します。 中間の値は部分的に透過なピクセルを示し、背景画像に合成することで出力画像を得られます。
ピクセル内の色値は、そのピクセルに割り当てられたアルファ値で事前乗算(premultiplied)されていません。この規則は「非関連(unassociated)」あるいは「非プリマルチプライド(non-premultiplied)アルファ」と呼ばれることがあります。(別の一般的な手法として、サンプル値をアルファ値で事前乗算して格納する方法があります。この場合、その画像は事実上黒背景に合成済みです。PNGはプリマルチプライドアルファを使用しません。その結果、画像エディタはPNG画像の透明度を容易に変更できます。)12.3 アルファチャネルの作成および13.16 アルファチャネル処理を参照してください。
1バイトを超える整数はすべてネットワークバイト順(Figure 17参照)でなければなりません。すなわち、最上位バイトが先で、その後に重要度の低いバイトが重要度の降順で続きます(2バイト整数ではMSB LSB、4バイト整数ではMSB B2 B1 LSB)。バイトの最上位ビット(値128)はビット7とし、最下位ビット(値1)はビット0とします。特に断りがない限り値は符号なしです。符号付きと明示された値は、2の補数表現で表されます。
PNG 4バイト符号なし整数は、符号なし4バイト値の扱いが困難な言語に配慮して、0から231-1の範囲に制限されています。
PNG画像(またはパス。8. インターレースとパス抽出参照)は長方形のピクセル配列であり、各スキャンライン内ではピクセルは左から右へ、スキャンラインは上から下へ並びます。各ピクセルのサイズは、ピクセルあたりのビット数によって決まります。
スキャンライン内のピクセルは常に、ピクセル間に無駄なビットが生じないようバイト列に詰められます。スキャンラインは常にバイト境界から始まります。許可されるビット深度とカラータイプは、いずれの場合もパッキングが単純かつ効率的になるよう制限されています。
カラータイプ0(グレースケール)のPNG画像では、各ピクセルは1つのサンプルであり、1バイト未満の精度(1、2、または4ビット)を持つことがあります。これらのサンプルは、スキャンラインの左端のサンプルがバイトの上位ビットになるように、続くサンプルとともにバイトに詰められます。
カラータイプ3(インデックスカラー)のPNG画像では、各ピクセルは単一のパレットインデックスです。これらのインデックスは、カラータイプ0のサンプルと同様にバイトへ詰められます。
1バイトあたり複数のピクセルが含まれる場合、スキャンラインの最後のバイトの下位ビットの一部が未使用となることがあります。これら未使用ビットの内容は規定されません。
インデックスカラーでないPNG画像では、ビット深度16のサンプル値を持つことがあります。これらのサンプル値はネットワークバイト順(MSBが先、LSBが後)です。PNGでは複数サンプルのピクセルは8ビットまたは16ビットのサンプルに限られるため、単一ピクセルの複数サンプルが1バイトに詰められることはありません。
フィルタ方式は、スキャンライン配列に適用され、圧縮効率の向上を目的とした変換です。
PNGは1つのフィルタ方式と、圧縮に備えて画像データを準備するために使用できる複数のフィルタタイプを標準化しています。この変換は、フィルタタイプのバイトを先頭に付けた、同じ長さのバイト列へと変換します(例はFigure 18参照)。
エンコーダは、インターレースPNG画像に対して単一のフィルタ方式のみを使用しなければなりませんが、縮小画像の各スキャンラインごとに異なるフィルタタイプを使用しても構いません。賢いエンコーダはスキャンラインごとにフィルタを切り替えることができます。どのフィルタを使用するかの選択方法はエンコーダに委ねられます。
フィルタタイプのバイトは画像データの一部とは見なされませんが、圧縮ステップに送られるデータストリームには含まれます。9. フィルタ処理を参照してください。
パス抽出(Figure 4.8参照)は、PNG画像を縮小画像(インターレースPNG画像)の列に分割します。最初の画像が粗いビューを定義し、続く画像がこの粗いビューを順次改善し、最後の画像でPNG画像が完成します。これにより、デコーダはインターレースPNG画像をプログレッシブに表示でき、オンザフライ表示時に画像が「フェードイン」することを可能にします。平均すると、インターレースはデータストリームサイズをわずかに増加させますが、より迅速に意味のある表示をユーザに提供できます。
この国際規格では、インターレース方式として0と1の2つを定義します。その他の値は将来の標準化のために予約されています。
インターレース方式0(ヌル方式)では、ピクセルは左から右へ順に抽出され、スキャンラインは上から下へ順に抽出されます。インターレースPNG画像は単一の縮小画像です。
インターレース方式1(Adam7として知られる)では、画像に対して7つの明確なパスを定義します。各パスは参照画像内のピクセルの部分集合を送信します。各ピクセルが送信されるパス(1から7までの番号)は、左上隅から画像全体に次の8×8パターンを繰り返すことで定義されます。
1 6 4 6 2 6 4 6
7 7 7 7 7 7 7 7
5 6 5 6 5 6 5 6
7 7 7 7 7 7 7 7
3 6 4 6 3 6 4 6
7 7 7 7 7 7 7 7
5 6 5 6 5 6 5 6
7 7 7 7 7 7 7 7
Figure 4.8は、インターレース方式1の7つのパスを示します。各パス内では、選択されたピクセルはスキャンライン内で左から右へ送信され、選択されたスキャンラインは上から下へ順に送信されます。例えば、パス2にはスキャンライン0、8、16、…のピクセル4、12、20、…が含まれます(スキャンライン0、ピクセル0は左上隅)。最後のパスにはスキャンライン1、3、5、…がすべて含まれます。送信順序は、各パスで送信されるすべてのスキャンラインが同じピクセル数になるように定義されています。これは一部のフィルタを適切に適用するために必要です。インターレースPNG画像は、7つの縮小画像の列で構成されます。例えば、PNG画像が16×16ピクセルの場合、第3パスは4ピクセルを含む2本のスキャンラインからなる縮小画像になります(Figure 4.8参照)。
スキャンラインが整数個のバイトを完全に満たさない場合、そのパディングは7.2 スキャンラインで定義されるとおりです。
注:参照画像の列数が5未満、または行数が5未満の場合、一部のパスは空になります。
フィルタ処理は、圧縮の改善を目的としてPNG画像を変換します。全体のプロセスはFigure 7に示され、スキャンラインの直列化とフィルタ処理の詳細はFigure 18に示されます。
PNGは複数のフィルタ方式を許容します。インターレース画像のすべての縮小画像は単一のフィルタ方式を使用しなければなりません。本仕様で定義されるのはフィルタ方式0のみです。他のフィルタ方式は将来の標準化のために予約されています。フィルタ方式0は5種類のフィルタタイプを提供し、各縮小画像内のスキャンラインごとに異なるフィルタタイプを使用できます。
PNGは、インターレースPNG画像に適用できるフィルタタイプに追加の制限を課しません。ただし、フィルタタイプはデータの種類によって効果が等しくはありません。12.7 フィルタ選択を参照してください。
フィルタ処理は、スキャンライン内のバイト列を、フィルタタイプを先頭に付けた同じ長さのバイト列へと変換します。フィルタタイプのバイトは非空のスキャンラインにのみ関連付けられます。空のパスにはフィルタタイプのバイトは存在しません。13.10 インターレースとプログレッシブ表示を参照してください。
フィルタは、画像のビット深度やカラータイプに関わらず、ピクセルではなくバイトに対して適用されます。フィルタは、7.2 スキャンラインで説明された表現に従って構成されたスキャンラインのバイト列に対して動作します。画像にアルファチャネルが含まれる場合、アルファデータは画像データと同様にフィルタ処理されます。
フィルタは、新しいバイト値を生成するために、以下のバイトの元の値を使用することがあります。
| 名称 | 定義 |
|---|---|
| x | フィルタ対象のバイト; |
| a | xを含むピクセルの直前のピクセルにおけるxに対応するバイト(ビット深度が8未満の場合はxの直前のバイト); |
| b | 前のスキャンラインにおけるxに対応するバイト; |
| c | bを含むピクセルの直前のピクセルにおけるbに対応するバイト(ビット深度が8未満の場合はbの直前のバイト)。 |
Figure 19は、x、a、b、cの相対位置を示します。
フィルタ方式0は、Table 11に示す5つの基本フィルタタイプを定義します。Orig(y)はバイトyの元の(非フィルタ)値を表します。Filt(y)はフィルタタイプを適用した後の値を表します。Recon(y)は対応する再構成関数を適用した後の値を表します。PaethフィルタタイプのPaethPredictor
[Paeth]は後述します。
フィルタ方式0は、ちょうどこの5つのフィルタタイプの集合を規定しており、これを拡張してはなりません。これにより、デコーダはデータを伸長しなくても、未サポートのフィルタタイプが含まれているかどうかを判断できます。11.2.1 IHDR 画像ヘッダ内のフィルタ方式を確認するだけで十分です。
| タイプ | 名称 | フィルタ関数 | 再構成関数 |
|---|---|---|---|
| 0 | None | Filt(x) = Orig(x)
|
Recon(x) = Filt(x)
|
| 1 | Sub | Filt(x) = Orig(x) - Orig(a)
|
Recon(x) = Filt(x) + Recon(a)
|
| 2 | Up | Filt(x) = Orig(x) - Orig(b)
|
Recon(x) = Filt(x) + Recon(b)
|
| 3 | Average | Filt(x) = Orig(x) - floor((Orig(a) + Orig(b)) / 2)
|
Recon(x) = Filt(x) + floor((Recon(a) + Recon(b)) / 2)
|
| 4 | Paeth | Filt(x) = Orig(x) - PaethPredictor(Orig(a), Orig(b), Orig(c))
|
Recon(x) = Filt(x) + PaethPredictor(Recon(a), Recon(b), Recon(c))
|
すべてのフィルタにおいて、スキャンラインの最初のピクセルの「左にある」バイトは0として扱われなければなりません。前のスキャンラインを参照するフィルタでは、縮小画像の最初のスキャンラインにおいて、前のスキャンライン全体とその最初のピクセルの「左にある」バイトは0として扱われなければなりません。
フィルタの効果を逆にするには、同じスキャンライン上の直前のピクセルの復号値、前のスキャンラインで現在のピクセルの直上にあるピクセルの復号値、そしてその直上のピクセルの左隣のピクセルの復号値が必要です。
入出力の両方をバイトに収めるため、256を法とする符号なし算術を用います。フィルタはビット深度に関係なく各バイトに適用されます。Filt値の列が、フィルタ済みスキャンラインとして送信されます。
Orig(a) + Orig(b)の和はオーバーフローなし(少なくとも9ビットの算術)で実行されなければなりません。floor()は、除算の結果が小数であれば次に小さい整数に切り下げることを示します。言い換えれば、これは整数除算または右シフト演算です。
Paethフィルタタイプは、3つの隣接ピクセル(左、上、左上)の単純な線形関数を計算し、その値に最も近い隣接ピクセルを予測値として選択します。本仕様で用いるアルゴリズムは、Alan W. Paethによる手法の改変です([Paeth])。
PaethPredictor関数は以下のコードで定義されます。関数のロジックと、バイトa、b、c、xの位置はFigure 20に示します。Prはバイトxの予測値です。
p = a + b - c
pa = abs(p - a)
pb = abs(p - b)
pc = abs(p - c)
if pa <= pb and pa <= pc then Pr = a
else if pb <= pc then Pr = b
else Pr = c
return Pr
PaethPredictor関数内の計算は、オーバーフローなしで厳密に実行されなければなりません。
比較の実行順序は重要であり、変更してはなりません。この関数は、(垂直、水平、対角の)3方向のうち、画像の勾配が最も小さい方向を見つけようとします。
エンコーダとデコーダは、まったく同一のPaethPredictor関数を使用します。
本国際規格で定義されるPNGの圧縮方式は方式0のみです。その他の圧縮方式の値は将来の標準化のために予約されています。PNG圧縮方式0は、スライディングウィンドウ(deflateストリームに現れる距離の上限)最大32768バイトのdeflate圧縮です。Deflate圧縮はLZ77に由来します。
PNG内のdeflate圧縮データストリームはzlibフォーマットで格納され、その構造は次のとおりです。
| zlib 圧縮方式/フラグコード | 1 byte |
| 追加フラグ/チェックビット | 1 byte |
| 圧縮データブロック | n bytes |
| チェック値 | 4 bytes |
PNG圧縮方式0では、zlibの圧縮方式/フラグコードは方式コード8(deflate圧縮)および32768バイト以下のLZ77ウィンドウサイズを指定しなければなりません。なお、zlibの圧縮方式番号は、IHDRチャンクにおけるPNGの圧縮方式番号と同一ではありません。追加フラグでプリセット辞書を指定してはなりません。
圧縮対象データが16384バイト以下である場合、PNGエンコーダはウィンドウサイズを2の累乗(最小256)に切り上げて設定してもかまいません。これは圧縮率に悪影響を与えることなく、エンコードおよびデコードの両方に必要なメモリを削減します。
zlibデータストリーム内の圧縮データは、一連のブロックとして格納されます。各ブロックは生(非圧縮)データ、固定ハフマン符号で符号化されたLZ77圧縮データ、またはカスタムハフマン符号で符号化されたLZ77圧縮データのいずれかを表します。最終ブロックのマーカビットはそれが最後のブロックであることを示し、デコーダが圧縮データストリームの終端を認識できるようにします。圧縮アルゴリズムと符号化の詳細は、deflate仕様[rfc1951]に記載されています。
zlibデータストリーム末尾に格納されるチェック値は、そのデータストリームが表す非圧縮データに対して計算されます。この計算に用いられるアルゴリズムは、PNGのチャンクCRCフィールド値に用いられるCRC計算と同一ではありません。zlibのチェック値は、主としてdeflateアルゴリズムが正しく実装されていることを相互確認するために有用です。各PNGチャンクのCRCを検証することで、PNGデータストリームが損傷なく伝送されたことに確信が持てます。
フィルタ済みスキャンラインの列は圧縮され、その結果得られたデータストリームはIDATチャンクに分割されます。すべてのIDATチャンクの内容を連結したものが1つのzlibデータストリームとなります。このデータストリームは伸長されるとフィルタ済みの画像データになります。
IDATチャンク間の境界は任意であり、zlibデータストリームのどこにでも置かれ得ることを強調しておくことが重要です。IDATチャンク境界とdeflateブロック境界、またはその他のzlibデータの特徴との間に相関があるとは限りません。例えば、終端のzlibチェック値がIDATチャンクにまたがって分割されることも十分あり得ます。
同様に、画像データの構造(すなわちスキャンライン境界)とdeflateブロック境界やIDATチャンク境界との間に必要な相関はありません。完全なフィルタ済みPNG画像は、複数のIDATチャンクに格納された単一のzlibデータストリームで表現されます。
PNGはiTXt、iCCP、およびzTXtチャンクにおいても圧縮方式0を使用します。画像データとは異なり、これらのデータストリームはチャンクをまたいで分割されません。各チャンクは独立したzlibデータストリームを含みます(10.1 圧縮方式0参照)。
本節では本仕様で使用されるチャンクを定義します。
クリティカルチャンクは、PNGデータストリームからPNG画像を正常にデコードするために絶対に必要なチャンクです。拡張チャンクはクリティカルチャンクとして定義される場合があります(14. エディタ参照)が、この運用は強く非推奨です。
妥当なPNGデータストリームはPNGシグネチャで始まり、直後にIHDRチャンク、続いて1つ以上のIDATチャンクが続き、最後はIENDチャンクで終わらなければなりません。PNGデータストリーム内において、IHDRチャンクとIENDチャンクはそれぞれ1つのみ許可されます。
4バイトのチャンクタイプフィールドには次の16進値が含まれます。
49 48 44 52
IHDRチャンクはPNGデータストリーム内の最初のチャンクでなければなりません。内容は次のとおりです。
| 幅 | 4 bytes |
| 高さ | 4 bytes |
| ビット深度 | 1 byte |
| カラータイプ | 1 byte |
| 圧縮方式 | 1 byte |
| フィルタ方式 | 1 byte |
| インターレース方式 | 1 byte |
幅と高さはピクセル単位の画像寸法を与えます。これらはPNG 4バイト符号なし整数です。0は不正な値です。
ビット深度は、サンプルまたはパレットインデックス(ピクセル単位ではない)あたりのビット数を与える1バイト整数です。有効な値は1、2、4、8、16ですが、すべての値がすべてのカラータイプで許可されるわけではありません。6.1 カラータイプと値を参照してください。
カラータイプは1バイト整数です。
各カラータイプに対するビット深度の制限は、実装を簡素化し、圧縮効率の低い組合せを禁止するために設けられています。許可される組合せはTable 12で定義されます。
| PNG画像タイプ | カラータイプ | 許可されるビット深度 | 解釈 |
|---|---|---|---|
| グレースケール | 0 | 1, 2, 4, 8, 16 | 各ピクセルはグレースケールサンプル |
| トゥルーカラー | 2 | 8, 16 | 各ピクセルは R,G,B 三つ組 |
| インデックスカラー | 3 | 1, 2, 4, 8 | 各ピクセルはパレットインデックス;PLTEチャンクが現れなければならない。 |
| グレースケール(アルファ付き) | 4 | 8, 16 | 各ピクセルはグレースケールサンプルに続いてアルファサンプル。 |
| トゥルーカラー(アルファ付き) | 6 | 8, 16 | 各ピクセルは R,G,B 三つ組に続いてアルファサンプル。 |
サンプル深度は、インデックスカラーPNG画像(カラータイプ3)の場合を除きビット深度と同じです。この場合、サンプル深度は常に8ビットです(4.5 PNG画像参照)。
圧縮方式は、画像データの圧縮に用いられた方式を示す1バイト整数です。本仕様で定義されるのは方式0(最大32768バイトのスライディングウィンドウを用いるdeflate圧縮)のみです。すべての準拠PNG画像はこの方式で圧縮されなければなりません。
フィルタ方式は、圧縮前に画像データに適用された前処理方式を示す1バイト整数です。本仕様で定義されるのはフィルタ方式0(5種類の基本フィルタタイプを用いた適応フィルタリング)のみです。詳細は9. フィルタ処理を参照してください。
インターレース方式は、画像データの伝送順序を示す1バイト整数です。本仕様では2つの値が定義されています:0(非インターレース)および1(Adam7インターレース)。詳細は8. インターレースとパス抽出を参照してください。
4バイトのチャンクタイプフィールドには次の16進値が含まれます。
50 4C 54 45
PLTEチャンクには1~256個のパレットエントリが含まれ、各エントリは次の形式の3バイト系列です。
| 赤 | 1 byte |
| 緑 | 1 byte |
| 青 | 1 byte |
エントリ数はチャンク長から決定されます。チャンク長が3で割り切れない場合はエラーです。
このチャンクはカラータイプ3では現れなければならず、カラータイプ2および6では現れてもかまいません。カラータイプ0および4では現れてはなりません。PLTEチャンクは2個以上存在してはなりません。
カラータイプ3(インデックスカラー)では、PLTEチャンクは必須です。PLTEの最初のエントリはピクセル値0、2番目はピクセル値1、というように参照されます。パレットエントリ数は、画像のビット深度で表現できる範囲(例えばビット深度4では24=16)を超えてはなりません。ビット深度が許す数より少ないエントリ数であってもかまいませんが、その場合、範囲外のピクセル値が画像データ内で見つかった場合はエラーとなります。
カラータイプ2および6(トゥルーカラーおよびトゥルーカラー(アルファ付き))では、PLTEチャンクは任意です。存在する場合、直接表示できないときにトゥルーカラー画像を量子化するための(1~256の)推奨色セットを提供します。ただし、この目的にはPLTEチャンクではなくsPLTチャンクを使用することが推奨されます。PLTEおよびsPLTのいずれのチャンクも存在せず、画像を直接表示できない場合、量子化はビューイングシステム側で行う必要があります。しかし、しばしば色の選択はPNGエンコーダが一度行っておく方が望ましいことがあります(12.5 推奨パレット参照)。
パレットは、画像のビット深度に関わらずサンプルあたり8ビット(1バイト)を使用することに注意してください。特に、16ビットのトゥルーカラー画像を量子化した推奨パレットであっても、パレット自身は8ビット深度です。
パレットエントリがすべて画像で使用されている必要はなく、またすべてが相互に異なる必要もありません。
4バイトのチャンクタイプフィールドには次の16進値が含まれます。
49 44 41 54
IDATチャンクには、圧縮アルゴリズムの出力ストリームである実際の画像データが含まれます。詳細は9. フィルタ処理および10. 圧縮を参照してください。
IDATチャンクは複数存在してもかまいません。その場合、間に他のチャンクを挟まず連続して現れなければなりません。圧縮データストリームは、すべてのIDATチャンクのデータフィールドの内容を連結したものです(データフィールドは長さゼロであり得ることに注意)。
一部の画像では、最後のIDATチャンクの末尾に未使用の余剰バイトが存在する場合があります。これは、使用されたバッファの一部だけでなくバッファ全体を格納した場合に起こり得ます。これは望ましくありません。可能であれば、エンコーダはこれら未使用バイトを含めないべきです。どうしても含める必要がある場合は、それらのバイトをゼロに設定することで偶発的なデータ共有を防げます。デコーダはこれらの末尾バイトを無視すべきです。
4バイトのチャンクタイプフィールドには次の16進値が含まれます。
49 45 4E 44
IENDチャンクはPNGデータストリームの終端を示します。このチャンクのデータフィールドは空です。
本仕様で定義される補助チャンクは、4.8.2 チャンクタイプに示した順序で列挙されています。これはPNGデータストリーム中に現れる順序を意味するものではありません。補助チャンクはデコーダによって無視されてもかまいません。各補助チャンクについて、ここで記述する動作はデコーダがそのチャンクを無視しないことを前提としています。
4バイトのチャンクタイプフィールドには次の16進値が含まれます。
74 52 4E 53
tRNSチャンクは、(インデックスカラー画像に対する)パレットエントリに対応するアルファ値、または(グレースケールおよびトゥルーカラー画像に対する)単一の透過色を指定します。tRNSチャンクの内容は次のとおりです。
| カラータイプ 0 | |
|---|---|
| グレーサンプル値 | 2 bytes |
| カラータイプ 2 | |
| 赤サンプル値 | 2 bytes |
| 緑サンプル値 | 2 bytes |
| 青サンプル値 | 2 bytes |
| カラータイプ 3 | |
| パレットインデックス0のアルファ | 1 byte |
| パレットインデックス1のアルファ | 1 byte |
| …等… | 1 byte |
カラータイプ3(インデックスカラー)の場合、tRNSチャンクはPLTEチャンクの各エントリに対応する1バイトのアルファ値の系列を含みます。各エントリは、対応するパレットインデックスのピクセルが指定のアルファ値を持つものとして扱われることを示します。アルファ値の解釈は8ビットのフルアルファチャネルと同じで、0は完全透過、255は完全不透明を意味し、画像のビット深度に依存しません。tRNSチャンクはパレットエントリ数を超える数のアルファ値を含んではなりませんが、パレットエントリ数より少ない値を含んでいてもかまいません。この場合、残りのすべてのパレットエントリのアルファ値は255と見なされます。一般的なケースとしてパレットインデックス0のみを透過にしたい場合は、1バイトのtRNSチャンクだけで十分であり、すべてのパレットインデックスが不透明である場合にはtRNSチャンクは省略できます。
カラータイプ0または2の場合、画像のビット深度にかかわらずサンプルあたり2バイトが使用されます(7.1 整数とバイト順参照)。指定されたグレーサンプル値またはRGBサンプル値のピクセルは透過(アルファ値0と同等)として扱い、それ以外のピクセルは完全不透明(アルファ値 2bitdepth-1)として扱います。画像のビット深度が16未満の場合は下位ビットが使用されます。エンコーダは残りのビットを0に設定すべきであり、デコーダは値を使用する前に残りのビットを0にマスクしなければなりません。
カラータイプ4および6では、すでにフルアルファチャネルが存在するため、tRNSチャンクを出現させてはなりません。
16ビットのグレースケールまたはトゥルーカラーデータでは、13.12 サンプル深度の再スケーリングで述べるように、tRNSチャンク内の16ビット値全体に一致するピクセルのみが透過になります。デコーダは透過性の判定が終わるまで、サンプル深度の再スケーリングを延期しなければなりません。
4バイトのチャンクタイプフィールドには次の16進値が含まれます。
63 48 52 4D
cHRMチャンクは、PNG画像で使用される赤・緑・青の表示基本色の1931 CIEのx,y色度および参照されるホワイトポイントを指定するために使用できます。詳細はC. ガンマと色度を参照してください。より高度な色管理と制御のためには、iCCPおよびsRGBチャンクが提供されています。
cHRMチャンクの内容は次のとおりです。
| 名称 | サイズ |
|---|---|
| ホワイトポイント x | 4 bytes |
| ホワイトポイント y | 4 bytes |
| 赤 x | 4 bytes |
| 赤 y | 4 bytes |
| 緑 x | 4 bytes |
| 緑 y | 4 bytes |
| 青 x | 4 bytes |
| 青 y | 4 bytes |
各値は、PNG 4バイト符号なし整数としてエンコードされ、xまたはyの値に100000を掛けたものを表します。
0.3127 の値は整数 31270 として格納されます。
cHRMチャンクはすべてのPNGデータストリームで許可されていますが、グレースケール画像では有用性は低くなります。
このチャンクは、デコーダが理解する最優先の色チャンクでない限り無視されます。
4バイトのチャンクタイプフィールドには次の16進値が含まれます。
67 41 4D 41
実際には、望ましい表示出力の強度を指定するだけでは不十分です。望ましい出力が得られる視聴条件も指定する必要があります。gAMAにおける視聴条件は、sRGB仕様 [SRGB] の参照視聴条件です。異なる視聴条件への調整は通常カラーマネジメントシステムによって処理されます。調整が行われない場合でも、誤差は通常小さくなります。高い色忠実度を望むアプリケーションは、sRGBやiCCPチャンクの利用を検討してもよいでしょう。
gAMAチャンクの内容は次のとおりです。
| 画像ガンマ | 4 bytes |
値はPNG 4バイト符号なし整数としてエンコードされ、ガンマ値に100000を掛けたものを表します。
ガンマ値 1/2.2 は整数 45455 として格納されます。
12.1 エンコーダのガンマ処理および13.13 デコーダのガンマ処理も参照してください。
このチャンクは、デコーダが理解する最優先の色チャンクでない限り無視されます。
4バイトのチャンクタイプフィールドには次の16進値が含まれます。
69 43 43 50
iCCPチャンクの内容は次のとおりです。
| プロファイル名 | 1-79 bytes(文字列) |
| ヌル区切り | 1 byte(ヌル文字) |
| 圧縮方式 | 1 byte |
| 圧縮済みプロファイル | n bytes |
プロファイル名は、そのプロファイルを参照するための任意の分かりやすい名称でよく、大文字小文字は区別されます。プロファイル名には印字可能なLatin-1文字と空白のみを含めなければなりません(使用可能なコードポイントは 0x20-7E と 0xA1-FF のみ)。先頭・末尾・連続する空白は許可されません。本仕様で定義される圧縮方式は方式0(deflate圧縮によるzlibデータストリーム。10.3 その他の圧縮の用途参照)のみです。圧縮方式のエントリに続いて、チャンクの残り全体を構成する圧縮済みプロファイルが続きます。このデータストリームを伸長すると、埋め込みICCプロファイルが得られます。
iCCPチャンクが存在する場合、画像サンプルはInternational Color Consortium [ICC][ISO_15076-1]で定義される埋め込みICCプロファイルが表すカラースペースに準拠します。ICCプロファイルのカラースペースは、カラー画像(カラータイプ2、3、6)の場合はRGBカラースペース、グレースケール画像(カラータイプ0、4)の場合はグレースケールカラースペースでなければなりません。iCCPチャンクを書き出すPNGエンコーダは、iCCPチャンクを使用しないアプリケーションとの互換性のため、ICCプロファイルを近似するgAMAおよびcHRMチャンクも併せて書き出すことが推奨されます。
このチャンクは、デコーダが理解する最優先の色チャンクでない限り無視されます。
cICPチャンクが存在しない限り、PNGデータストリームに含める埋め込みプロファイルは、iCCPで明示的に指定するかsRGBチャンクで暗黙的に指定するかのいずれか一つにとどめるのが望ましいです。
4バイトのチャンクタイプフィールドには次の16進値が含まれます。
73 42 49 54
デコーダを簡素化するため、PNGは使用可能なサンプル深度を限定し、さらにサンプル値がサンプル深度における可能な値の全域へスケーリングされるべきであると規定しています。sBITチャンクは元の有効ビット数(サンプル深度以下)を定義します。これにより、データがPNGで直接サポートされないサンプル深度であっても、PNGデコーダは元のデータをロスレスに復元できます。
sBITチャンクの内容は次のとおりです。
| カラータイプ 0 | |
|---|---|
| 有効グレースケールビット数 | 1 byte |
| カラータイプ 2 および 3 | |
| 有効赤ビット数 | 1 byte |
| 有効緑ビット数 | 1 byte |
| 有効青ビット数 | 1 byte |
| カラータイプ 4 | |
| 有効グレースケールビット数 | 1 byte |
| 有効アルファビット数 | 1 byte |
| カラータイプ 6 | |
| 有効赤ビット数 | 1 byte |
| 有効緑ビット数 | 1 byte |
| 有効青ビット数 | 1 byte |
| 有効アルファビット数 | 1 byte |
sBITで指定される各深度は0より大きく、サンプル深度(インデックスカラー画像では8、その他のカラータイプではIHDRで与えられるビット深度)以下でなければなりません。なお、sBITは、tRNSチャンクによって暗示されるアルファチャネルのサンプル深度は提供しません。その場合、アルファチャネルのすべてのサンプルビットは有効と見なされます。sBITチャンクが存在しない場合、すべてのチャネルのすべてのサンプルビットは有効と見なされます。
4バイトのチャンクタイプフィールドには次の16進値が含まれます。
73 52 47 42
sRGBチャンクが存在する場合、画像サンプルは sRGB カラースペース [SRGB] に準拠し、International Color Consortium [ICC] または [ICC-2]で定義される指定のレンダリングインテントを用いて表示されるべきです。
sRGBチャンクの内容は次のとおりです。
| 名称 | サイズ |
|---|---|
| レンダリングインテント | 1 byte |
レンダリングインテントには次の値が定義されています。
| 値 | 名称 | 説明 |
|---|---|---|
| 0 | 知覚(Perceptual) | 写真など、測色的な正確さを犠牲にしても出力デバイスの色域への良好な適応を優先する画像。 |
| 1 | 相対測色(Relative colorimetric) | ロゴなど、出力デバイスのホワイトポイントに相対的な色外観の一致を要する画像。 |
| 2 | 彩度(Saturation) | チャートやグラフなど、色相や明度よりも彩度の保持を優先する画像。 |
| 3 | 絶対測色(Absolute colorimetric) | 別の出力デバイス向け画像のプルーフなど、絶対的な測色の保持を要する画像。 |
sRGBチャンクを書き出すPNGエンコーダは、sRGBチャンクを使用しないデコーダとの互換性のため、gAMAチャンク(および任意でcHRMチャンク)も書き出すことが推奨されます。使用すべき値は次のみです。
| gAMA | |
|---|---|
| ガンマ | 45455 |
| cHRM | |
| ホワイトポイント x | 31270 |
| ホワイトポイント y | 32900 |
| 赤 x | 64000 |
| 赤 y | 33000 |
| 緑 x | 30000 |
| 緑 y | 60000 |
| 青 x | 15000 |
| 青 y | 6000 |
このチャンクは、デコーダが理解する最優先の色チャンクでない限り無視されます。
4バイトのチャンクタイプフィールドには次の16進値が含まれます。
63 49 43 50
存在する場合、cICPチャンクは、[ITU-T-H.273]で規定されるコードポイントを用いて、画像のカラースペース(原色)、伝達関数、行列係数およびスケーリング係数を指定します。ビデオフォーマットのシグナリングは、デコーダやレンダリング時を含めて、画像の処理において使用することがSHOULDです。
cICPチャンクは、上述の特性を識別する4つの1バイト符号なし整数から構成されます。
cICPチャンクの構文は次のとおりです。
| 名称 | サイズ |
|---|---|
| 色度点(Color Primaries) | 1 byte |
| 伝達関数(Transfer Function) | 1 byte |
| 行列係数(Matrix Coefficients) | 1 byte |
| フルレンジフラグ(Video Full Range Flag) | 1 byte |
cICPチャンクの各フィールドは、[ITU-T-H.273]における同名のパラメータに対応します。
PNGで現在サポートされるカラーモデルはRGBのみであるため、
Matrix Coefficientsは0に設定しなければなりません(shall)。
Video Full Range Flagが0(ナローレンジ画像)の場合、推奨される実践は、負の値を含むように、EOTFまたは逆のOETFなどの伝達関数を拡張範囲にわたって定義することです。
これは次のように行います。
out = sign(in) * TransferFunction(abs(in))
cICPチャンクはPLTEおよびIDATチャンクより前に置かなければなりません(MUST)。
このチャンクは、デコーダが理解する場合、最優先の色チャンクです。
sRGBチャンクを用いてsRGB画像を簡潔にシグナルするのと同様に、cICPはDisplay P3画像 [Display-P3] を簡潔にシグナルするためにも使用できます。
4バイトのチャンクタイプフィールドには次の16進値が含まれます。
6D 44 43 56
存在する場合、mDCVチャンクは、[SMPTE-ST-2086]で規定される、コンテンツ制作時点で用いられたマスタリングディスプレイのカラーボリューム(mDCV)を特徴付けます。mDCVチャンクは情報的な静的メタデータを提供し、ターゲット(視聴者側)ディスプレイが自身の能力と元のマスタリングディスプレイの能力を比較してトーンマッピングを最適化できる可能性を与えます。
mDCVは一般に、PQ [ITU-R-BT.2100] の伝達関数および追加のcLLIメタデータと共に使用され、この組合せは一般に [HDR10](PQ + ST 2086 静的メタデータ、MaxFALL、MaxCLL)と呼ばれます。mDCVチャンクはHLG [ITU-R-BT.2100]や SDR画像形式(例:[ITU-R-BT.709])にも含めることができます。
mDCVはもともと、ビデオ表示ターゲット上での画像のトーンマッピング最適化を目的とした補助的な静的メタデータとして作られたため、mDCVを使用する際は、画像コンテンツの基本特性を確立するためにcICPチャンクを伴わせる必要があります。色度点およびホワイトポイントの特性はcICPチャンクの形式から導出できます。HDR [ITU-R-BT.2100] と SDR [ITU-R-BT.709] の双方を用いる画像に関する代表的ユースケースは [ITU-T-Series-H-Supplement-19]に示されています。基本(cICP)の特性に加え、補助(mDCV)の静的メタデータは、トーンマッピングの最適化に有用な情報となり得ます。
Issue #319は、mDCVチャンクが存在する場合のトーンマッピング動作について議論しています。
SDR画像において、mDCVの表示最小/最大輝度が不明な場合、デフォルト特性は [ITU-T-Series-H-Supplement-19] 表11の値、または関連するSDR仕様から導出できます。現時点では、SDR画像信号をデフォルトの視聴条件(表示輝度と周囲照明)からmDCVチャンクでシグナルされる条件へ変換する標準化された公開手法はありません。
以下にmDCVチャンクの構文を示します。
| 名称 | サイズ | 除数値 |
|---|---|---|
| マスタリングディスプレイの色度点(CIE 1931 x,y の R,G,B) | 12 bytes | 0.00002 |
| マスタリングディスプレイのホワイトポイント色度(CIE 1931 x,y) | 4 bytes | 0.00002 |
| マスタリングディスプレイの最大輝度(cd/m2) | 4 bytes | 0.0001 |
| マスタリングディスプレイの最小輝度(cd/m2) | 4 bytes | 0.0001 |
色度点は、順にx、yの順で、各々が除数値で割られた x または y の基本色度値を表す、3組のPNG 2バイト符号なし整数としてエンコードされます。並び順は、x色度が最大の原色、次にy色度が最大の原色、最後に残る原色の順です。RGBカラースペースではR、G、Bの順に対応します。
ホワイトポイントは、順にx、yの順で、各々が除数値で割られた x または y のホワイト色度値を表す、1組のPNG 2バイト符号なし整数としてエンコードされます。
最大および最小輝度値は、cd/m2の絶対輝度値を除数値で割った値を表すPNG 4バイト符号なし整数としてエンコードされます。
除数は実際の値から格納値への写像を与えます。例えば、原色およびホワイトポイントに対する単位なしの除数 0.00002 の場合、色度 (0.6800, 0.3200) は {34000, 16000} として格納されます。
mDCVチャンクはPLTEおよびIDATチャンクより前に置かなければなりません(MUST)。
以下に [ITU-R-BT.2100] HDR の mDCV 例を示します。
以下に [Display-P3] のSDRに関する mDCV の例を示します。
4バイトのチャンクタイプフィールドには次の16進値が含まれます。
63 4C 4C 49
存在する場合、cLLIチャンクはHDRコンテンツの2つの特性を識別します:
cLLIチャンクは静的メタデータを追加し、関連コンテンツのトーンマッピングを特定のターゲットディスプレイに最適化する機会を提供します。これは、コンテンツ自体のトーンマッピングをターゲットディスプレイのピーク輝度能力に合わせて調整し、クリッピングを防ぐことで達成されます。トーンマッピングの最適化手法は現時点では主観的です。
MaxCLL(Maximum Content Light Level)は、再生シーケンス全体における単一ピクセルの最大光度(cd/m2、ニトとも)の静的メタデータ値を用います。処理やノイズに起因する誤検出が下流の意図されたトーンマッピングに悪影響を与えるのを防ぐため、しばしばアルゴリズム的なフィルタが用いられます。
MaxFALL(Maximum Frame Average Light Level)は、再生シーケンス全体におけるフレーム平均光度(cd/m2、ニトとも)の最大値を静的メタデータ値で示します。MaxFALLは、まず各フレームのすべてのピクセルの復号輝度値を平均し、その後、最大の値を持つフレームの値を用いて算出します。
MaxCLL と MaxFALL の値は、PNG 4バイト符号なし整数としてエンコードされます。
[CTA-861.3-A] はcLLI値を生成するための計算方法を記述していますが、フィルタリングについては規定していません。[HDR-Static-Meta] は、統計的外れ値やノイズ、リサンプリングフィルタによるリンギングから生じる極端な値を排除する改良手法を記述しており、実装において推奨されます。
[SMPTE-ST-2067-21] セクション7.5は、cLLIの値が不明で未計算の場合に追加情報を提供します。
Issue #319は、cLLIチャンクが存在する場合のトーンマッピング動作について議論しています。
各フレームが分析されます。
MaxCLL または MaxFALL の値がゼロの場合、その値は不明、または現在計算できないことを意味します。
この値が計算不能となる例として、ライブのアニメーションPNGストリームを作成している場合が挙げられます。このとき、ストリームが終了するまで全フレームが利用可能にならないため、値を計算できません。エンコーダは当初ゼロを用い、ストリーム終了時に計算値へ置き換えることを望むかもしれません。
以下にcLLIチャンクの構文を示します。
| 名称 | サイズ | 除数値 |
|---|---|---|
| Maximum Content Light Level(MaxCLL) | 4 bytes | 0.0001 cd/m2 |
| Maximum Frame-Average Light Level(MaxFALL) | 4 bytes | 0.0001 cd/m2 |
PNG は、画像の説明や著作権表示など、画像に関連付けられたテキスト文字列を格納するために、tEXt、iTXt、および zTXt チャンクを提供します。各テキスト文字列が何を表しているかを示すためにキーワードが使用されます。任意の数のそのようなテキストチャンクが出現することができ、同じキーワードを持つ複数のチャンクも許容されます。
次のキーワードは事前定義されており、適切な場面で使用されるべきです。
| Keyword value | Description |
|---|---|
| Title | Short (one line) title or caption for image |
| Author | Name of image's creator |
| Description | Description of image (possibly long) |
| Copyright | Copyright notice |
| Creation Time | Time of original image creation |
| Software | Software used to create the image |
| Disclaimer | Legal disclaimer |
| Warning | Warning of nature of content |
| Source | Device used to create the image |
| Comment | Miscellaneous comment |
| XML:com.adobe.xmp | Extensible Metadata Platform (XMP) information, formatted as required by the XMP specification [XMP]. The use of iTXt, with Compression Flag set to 0, and both Language Tag and Translated Keyword set to the null string, are recommended for XMP compliance. |
| Collection | Name of a collection to which the image belongs. An image may belong to one or more collections, each named by a separate text chunk. |
その他のキーワードは、プライベートまたは一般的な用途のために任意のアプリケーションによって定義されることが MAY あります。
キーワードは SHOULD 以下のようにすることが望まれます。
一般的に有用なキーワードは SHOULD で [PNG-EXTENSIONS] に登録されるべきです。
キーワードには印字可能な Latin-1 [ISO_8859-1] の文字とスペースのみを含めるものとします。すなわち、許可されるコードポイントは 0x20-7E および 0xA1-FF のみです。キーワードの先頭や末尾のスペース、連続するスペースは許可されません。また、視覚的に通常のスペースと区別できない U+00A0 NON-BREAKING SPACE も許可されません。
キーワードは登録されたとおりに正確に綴られるべきであり、デコーダは特定のキーワードを探す際に単純なリテラル比較を使用できるようにします。特にキーワードは大文字小文字を区別するとみなされます。キーワードは長さが 1 〜 79 バイトの範囲でなければなりません。
Creation Time キーワードについては、日付形式は RFC 3339 [rfc3339] の日付時刻形式、または RFC 1123 のセクション 5.2.14 で定義される日付形式のいずれかであることが SHOULD です。RFC3339 の日付時刻形式が推奨されます。実際のフィールドの形式は未定義です。
iTXt チャンクは UTF-8 エンコーディング [rfc3629] を使用し、任意の言語の文字を伝えるために使用できます。iTXt チャンクにはテキスト文字列を圧縮するオプションがあります。Unicode をサポートするため、すべてのテキスト文字列に対して iTXt の使用が推奨されます。また、印字可能な Latin-1 文字集合と U+000A LINE FEED (LF) に制限される tEXt および zTXt チャンクも存在します。zTXt 内のテキスト文字列は、zlib データストリームに圧縮され、deflate 圧縮を用います(10.3 Other uses of compression参照)。
4バイトのチャンクタイプフィールドには次の16進値が含まれます
74 45 58 74
各 tEXt チャンクはキーワードとテキスト文字列を次の形式で含みます。
| Keyword | 1-79 bytes (character string) |
| Null separator | 1 byte (null character) |
| Text string | 0 or more bytes (character string) |
キーワードとテキスト文字列はゼロバイト(ヌル文字)で区切られます。キーワードもテキスト文字列もヌル文字を含んではなりません。テキスト文字列はヌル終端ではなく(チャンク長が終了位置を定義します)、長さはゼロバイトからキーワードとヌル区切り文字の長さを差し引いた最大許容チャンク長まで任意です。
キーワードは 11.3.3.1 Keywords and text strings に記述されたとおり、テキスト文字列が表す情報の種類を示します。
テキストは Latin-1 文字集合に従って解釈されます [ISO_8859-1]。テキスト文字列は任意の Latin-1 文字を含むことができます。テキスト内の改行は単一の linefeed 文字(10)で表すべきです。Latin-1 に定義される文字と linefeed 文字以外の文字は tEXt チャンク内では定義された意味を持ちません。Latin-1 のレパートリー外の文字を含むテキストは iTXt チャンクを使用してエンコードすべきです。
4バイトのチャンクタイプフィールドには次の16進値が含まれます
7A 54 58 74
zTXt と tEXt チャンクは意味的に同等ですが、zTXt は大きなテキストブロックを格納するのに推奨されます。
zTXt チャンクは次を含みます。
| Keyword | 1-79 bytes (character string) |
| Null separator | 1 byte (null character) |
| Compression method | 1 byte |
| Compressed text datastream | n bytes |
キーワードとヌル文字は tEXt チャンクと同じ形式です。キーワードは圧縮されません。圧縮方式フィールドは使用された圧縮方式を定義します。本国際規格で定義される唯一の値は 0(deflate 圧縮)です。他の値は将来の標準化のために予約されています。圧縮方式フィールドの後に、チャンクの残りを構成する圧縮されたテキストデータストリームが続きます。圧縮方式 0 の場合、このデータストリームは zlib データストリーム(deflate 圧縮)です(10.3 Other uses of compression参照)。このデータストリームを伸長すると、同等の tEXt チャンクに格納されるテキストと同一の Latin-1 テキストが得られます。
4バイトのチャンクタイプフィールドには次の16進値が含まれます
69 54 58 74
各 iTXt チャンクは次を含みます。
| Keyword | 1-79 bytes (character string) |
| Null separator | 1 byte (null character) |
| Compression flag | 1 byte |
| Compression method | 1 byte |
| Language tag | 0 or more bytes (character string) |
| Null separator | 1 byte (null character) |
| Translated keyword | 0 or more bytes |
| Null separator | 1 byte (null character) |
| Text | 0 or more bytes |
キーワードは 11.3.3.1 Keywords and text strings に記述されています。
圧縮フラグは、非圧縮テキストであれば 0、圧縮テキストであれば 1 です。圧縮できるのはテキストフィールドのみです。圧縮方式フィールドは使用された圧縮方式を定義します。本仕様で定義される唯一の圧縮方式は 0(zlib データストリームと deflate 圧縮)です(10.3 Other uses of compression参照)。非圧縮テキストの場合、エンコーダは圧縮方式を 0 に設定し、デコーダはそれを無視しなければなりません。
言語タグは [BCP47]
によって定義される正しい言語タグでなければなりません。キーワードとは異なり、言語タグは大文字小文字を区別しません。サブタグは
IANA
language subtag registry に存在する必要があります。言語タグが空の場合、言語は未指定です。言語タグの例には en,
en-GB, es-419, zh-Hans, zh-Hans-CN,
tlh-Cyrl-AQ, ar-AE-u-nu-latn, および x-private などがあります。
翻訳されたキーワードとテキストは両方とも UTF-8 エンコーディング [rfc3629] を使用し、いずれもゼロバイト(ヌル文字)を含んではなりません。テキストは、このチャンク内の他のテキストデータと異なりヌル終端ではなく、長さはチャンク長から導出されます。
翻訳キーワードには改行を含めてはなりません。テキスト内の改行は単一の linefeed(16進 0A)で表すべきです。残りの制御文字(01-09, 0B-1F, 7F-9F)は、翻訳キーワードおよびテキストの両方で使用が推奨されません。UTF-8 では、文字としての 80-9F(使用が推奨されない)と、バイトとしての 80-9F(多くの場合必要となる)の間に差異がある点に注意してください。
翻訳キーワードが空でない場合、それは言語タグで示された言語へのキーワードの翻訳を含むべきであり、キーワードを表示するアプリケーションは翻訳キーワードも併せて表示することが望まれます。
4バイトのチャンクタイプフィールドには次の16進値が含まれます
62 4B 47 44
bKGD チャンクは、画像を提示するためのデフォルトの背景色を指定します。ユーザ指定の背景や、ブラウザのような大きなページの一部としての優先される背景がある場合は、bKGD チャンクは無視されるべきです。bKGD チャンクは次を含みます:
| Color types 0 and 4 | |
|---|---|
| Greyscale | 2 bytes |
| Color types 2 and 6 | |
| Red | 2 bytes |
| Green | 2 bytes |
| Blue | 2 bytes |
| Color type 3 | |
| Palette index | 1 byte |
color type 3(indexed-color)の場合、値は背景として用いる色のパレットインデックスです。
color types 0 および 4(greyscale, greyscale with alpha)では、値は背景に使うグレーのレベルで、範囲は 0 から (2bitdepth)-1 です。color types 2 および 6(truecolor, truecolor with alpha)では、値は背景に用いる色を RGB サンプルとして与え、範囲は 0 から (2bitdepth)-1 です。いずれの場合も、一貫性のためにサンプルあたり 2 バイトが使用され、画像のビット深度にかかわらず二バイトで格納されます。画像のビット深度が 16 未満の場合は下位ビットが使用されます。エンコーダは残りのビットを 0 に設定すべきであり、デコーダは値を使用する前に残りのビットを 0 にマスクしなければなりません。
4バイトのチャンクタイプフィールドには次の16進値が含まれます
68 49 53 54
hIST チャンクは一連の 2 バイト符号なし整数を含みます:
| Frequency | 2 bytes (unsigned integer) |
| ...etc... |
hIST チャンクはパレット中の各色の概略的な使用頻度を示します。ヒストグラムチャンクは PLTE チャンクが存在する場合にのみ出現できます。ビューアがパレットのすべての色を提供できない場合、ヒストグラムは表示用に色のサブセットを選択するのに役立つかもしれません。
PLTE の各エントリに対して正確に一つのエントリが存在しなければなりません。各エントリはそのパレットインデックスを持つピクセルの画像内での割合に比例します;正確なスケール係数はエンコーダが選びます。
ヒストグラムのエントリは概算であり、例外としてゼロのエントリは対応するパレットエントリが画像内で全く使用されていないことを示します。ある色のピクセルが存在するならば、そのヒストグラムエントリはゼロであってはなりません。
注:パレットが truecolor 画像を量子化した推奨パレットである場合、デコーダはエンコーダとは異なる方法でピクセルをパレットエントリにマップする可能性があるため、ヒストグラムは必然的に概算になります。この状況では、いかなるエントリも使用され得るため通常ゼロのエントリは現れないはずです。
4バイトのチャンクタイプフィールドには次の16進値が含まれます
70 48 59 73
pHYs チャンクは、画像の表示における意図されたピクセルサイズまたはアスペクト比を指定します。内容は次のとおりです:
| Name | Size |
|---|---|
| Pixels per unit, X axis | 4 bytes (PNG four-byte unsigned integer) |
| Pixels per unit, Y axis | 4 bytes (PNG four-byte unsigned integer) |
| Unit specifier | 1 byte |
unit specifier に対して定義される値は次のとおりです:
| Value | Description |
|---|---|
| 0 | unit is unknown |
| 1 | unit is the metre |
unit specifier が 0 の場合、pHYs チャンクはピクセルのアスペクト比のみを定義し、ピクセルの実際の物理サイズは未指定のままです。
pHYs チャンクが存在しない場合、ピクセルは正方形であると仮定され、各ピクセルの物理サイズは未指定です。
4バイトのチャンクタイプフィールドには次の16進値が含まれます
73 50 4C 54
sPLT チャンクは次を含みます:
| Name | Size |
|---|---|
| Palette name | 1-79 bytes (character string) |
| Null separator | 1 byte (null character) |
| Sample depth | 1 byte |
| Red | 1 or 2 bytes |
| Green | 1 or 2 bytes |
| Blue | 1 or 2 bytes |
| Alpha | 1 or 2 bytes |
| Frequency | 2 bytes |
| ...etc... |
各パレットエントリは 6 バイトまたは 10 バイトで、5 つの符号なし整数(red, blue, green, alpha, frequency)を含みます。
エントリ数は任意です。PNG デコーダは sample depth バイトの後に残るチャンク長からエントリ数を決定します。sPLT の sample depth が 8 の場合、残り長は 6 で割り切れるべきであり、sample depth が 16 の場合は 10 で割り切れるべきです。エントリは周波数の降順で現れるべきです。エントリがすべて画像で使用されている必要も、すべて異なる必要もありません。
パレット名はパレットを参照するための任意の分かりやすい名前(例えば "256 color including Macintosh default", "256 color including Windows-3.1 default", "Optimal 512")にできます。PNG データストリーム内に複数の推奨パレットが存在する場合、パレット名は適切なパレットの選択を助けます。
パレット名は大文字小文字を区別し、tEXt チャンクのキーワードパラメータと同じ制限を受けます。パレット名は印字可能な Latin-1 文字とスペースのみを含むべきで、許可されるコードポイントは 0x20-7E および 0xA1-FF のみです。先頭・末尾・連続するスペースは許可されません。
sPLT の sample depth は 8 または 16 でなければなりません。
red, green, blue, alpha のサンプルは sPLT の sample depth に応じて各々 1 または 2 バイトです。これは画像のビット深度に関係ありません。色サンプルはアルファで事前乗算されておらず、任意の背景と事前に合成されてもいません。アルファ値 0 は完全透過、アルファ値 255(sample depth が 8 の場合)または 65535(sample depth が 16 の場合)は完全不透明を意味します。sPLT チャンクは任意の color type に現れて構いません。sPLT エントリは PNG 画像と同じ gamma value と chromaticity 値を使いますが、PNG 画像のカラースペースで用いられる範囲外の値を取り得ます。例えばグレースケール PNG では各 sPLT エントリは通常 R,G,B が等しい値を持ちますが、それが必須というわけではありません。同様に、PNG 画像が透明度を使用していない場合でも sPLT エントリは不透明でないアルファ値を持ち得ます。
各 frequency 値は、そのパレットエントリが RGBA 空間で最も近い一致となるピクセルの割合に比例します(任意の背景に対して composited される前)。正確なスケール係数は PNG エンコーダが選びます;個々の値が 0 〜 65535 の範囲を適度に満たすようにすることが推奨されます。エンコーダはロゴや顔の特徴のような「重要」と考える色の周波数を人工的に大きくすることができます。ゼロは最も重要でない色、またはほとんど使われない色を意味する有効な周波数です。すべての周波数がゼロの場合、それらは意味を持たない、つまり PNG 画像における実際の出現頻度について何も推測できないことを意味します。
複数の sPLT チャンクは許容されますが、それぞれ異なるパレット名を持たなければなりません。
4バイトのチャンクタイプフィールドには次の16進値が含まれます
65 58 49 66
eXIf チャンクのデータセグメントは、[CIPA-DC-008] の "4.7.2 Interoperability Structure of APP1 in Compressed Data" で指定された形式の Exif プロファイルを含みます。ただし、JPEG APP1 マーカー、長さ、および 4.7.2(C) で記述される "Exif ID code"(すなわち "Exif", NULL, およびパディングバイト)は含まれません。
eXIf チャンクのサイズは PNG 仕様によって課される最大 231-1 バイトのみで制約されます。PNG データストリーム内には eXIf チャンクは 1 個のみ許可されます。
eXIf チャンクは元の image data に関するメタデータを格納します。画像が Exif プロファイル作成後に編集されている場合、このデータはもはや PNG の image data に適用されないかもしれません。デコーダが Exif データの有効性について独立した知識を持たない限り、そのデータは歴史的価値のみと見なすべきであることが推奨されます。eXIf チャンクと他の PNG チャンク内のデータ間の潜在的な矛盾を解決することは本仕様の範囲外です。
PNG 仕様はチャンクサイズを最大 231-1 バイトまで許容しますが、Exif プロファイルが JPEG [JPEG] データストリームに書き込まれる予定がある場合、Exif データ全体の長さを JPEG APP1 マーカー(Exif)セグメントに収まるように 216-9 バイトを超えないように調整する必要があることに注意すべきです。
データの最初の 2 バイトは、リトルエンディアン(Intel)の場合は "II"、ビッグエンディアン(Motorola)の場合は "MM" です。デコーダは最初の 4 バイトをチェックして次の16進値を持つことを確認すべきです:
49 49 2A 00 (ASCII "II", 16-bit little-endian integer 42)
または
4D 4D 00 2A (ASCII "MM", 16-bit big-endian integer 42)
その他の値は将来の定義のために予約されています。
画像編集アプリケーションは、Exif 仕様の付録 E.3 を検討すべきであり [CIPA-DC-008]、画像が変更されたときに Exif データを更新するための要件について議論されている箇所を参照すべきです。エンコーダはこれらの要件に従うべきですが、デコーダは必ずしもそれが実行されていると仮定してはなりません。
エンコーダがサムネイルを更新することを選択する場合もありますが、メイン画像が変更された場合に Exif プロファイル内のサムネイルが更新されているかどうかは保証されません。
4バイトのチャンクタイプフィールドには次の16進値が含まれます
74 49 4D 45
tIME チャンクは、画像の最終変更時刻(初回作成時刻ではありません)を与えます。内容は次のとおりです:
| Name | Size |
|---|---|
| Year | 2 bytes (完全な年; たとえば 1995、95 ではない) |
| Month | 1 byte (1-12) |
| Day | 1 byte (1-31) |
| Hour | 1 byte (0-23) |
| Minute | 1 byte (0-59) |
| Second | 1 byte (0-60)(うるう秒を許容するため) |
ローカル時刻ではなく協定世界時(UTC)を指定するべきです。
tIME チャンクは、image data が変更されるたびに自動的に適用・更新されるタイムスタンプとしての使用を意図しています。
4バイトのチャンクタイプフィールドには次の16進値が含まれます
61 63 54 4C
acTL チャンクはこれがアニメーションPNG画像であることを宣言し、フレーム数およびループ回数を与えます。内容は次のとおりです:
num_frames |
4 bytes |
num_plays |
4 bytes |
各値はPNG four-byte unsigned integerとしてエンコードされます。
num_frames はアニメーション内の総フレーム数を示します。これは fcTL
チャンクの数と等しくなければなりません。0 は無効な値です。単一フレームの PNG の場合は 1 が有効です。この値が実際のフレーム数と一致しない場合はエラーとして扱うべきです。
num_plays はこのアニメーションが再生される回数を示します;0 の場合は無限に再生すべきです。0
でない場合、最後の再生の終了時にアニメーションは最終フレームで停止すべきです。
acTL チャンクは有効な PNG ストリーム内で最初の IDAT チャンクの前に現れなければなりません。
Web 互換性のために、このチャンクの開発と展開の間に長い時間差があり PNG 仕様への組み込みが遅れたことから、このチャンク名は例外的にプライベートチャンクであるかのように定義されています。
4バイトのチャンクタイプフィールドには次の16進値が含まれます
66 63 54 4C
fcTL チャンクは個々のフレームの寸法、位置、表示遅延、および破棄動作を定義します。各フレームに対して正確に1つの fcTL チャンクが必要です。内容は次のとおりです:
| Name | Size |
|---|---|
sequence_number |
4 bytes |
width |
4 bytes |
height |
4 bytes |
x_offset |
4 bytes |
y_offset |
4 bytes |
delay_num |
2 bytes |
delay_den |
2 bytes |
dispose_op |
1 byte |
blend_op |
1 byte |
sequence_number はアニメーションチャンクのシーケンス番号を定義し、0
から始まります。これは PNG four-byte
unsigned integer としてエンコードされます。
width と height は続くフレームの幅と高さを定義します。これらは PNG four-byte unsigned integers
としてエンコードされ、0 より大きくなければなりません。
x_offset と y_offset は続くフレームの x および y 位置を定義します。これらは PNG four-byte unsigned integers
としてエンコードされます。0 は有効な値です。
フレームは x_offset, y_offset, width, height
で定義される領域内にレンダリングされなければなりません。この領域はデフォルト画像の外に出てはならないため、x_offset + width
は IHDR の幅を超えてはならず、同様に y_offset +
height は IHDR の高さを超えてはなりません。
delay_num と delay_den は遅延分数の分子と分母を定義し、現在のフレームを表示する時間(秒)を示します。分母が 0 の場合は
100 として扱われます(すなわち delay_num は 1/100 秒単位を指定します)。分子の値が 0
の場合、デコーダは可能な限り速やかに次のフレームをレンダリングするべきですが、ビューアは合理的な下限を課すことがあります。これらは2バイトの符号なし整数としてエンコードされます。
フレームのタイミングは各フレームのデコードや表示に要する時間に依存しないようにするべきであり、そうすることでデコーダの性能に関わらず同じ速度でアニメーションが再生されます。
dispose_op
はこのフレームのレンダリング後に行う領域の破棄方法を定義します。すなわち遅延終了時(次フレームをレンダリングする前)に出力バッファをどのように変更するかを指定します。これは1バイトの符号なし整数としてエンコードされます。
dispose_op の有効な値は次のとおりです:
| 0 | APNG_DISPOSE_OP_NONE |
| 1 | APNG_DISPOSE_OP_BACKGROUND |
| 2 | APNG_DISPOSE_OP_PREVIOUS |
APNG_DISPOSE_OP_NONEAPNG_DISPOSE_OP_BACKGROUNDAPNG_DISPOSE_OP_PREVIOUS最初の fcTL チャンクが dispose_op に
APNG_DISPOSE_OP_PREVIOUS を使用している場合、それは APNG_DISPOSE_OP_BACKGROUND
として扱うべきです。
blend_op
はフレームが現在の出力バッファ内容にアルファ合成されるか、あるいはその領域を完全に置き換えるかを指定します。これは1バイトの符号なし整数としてエンコードされます。
blend_op の有効な値は次のとおりです:
| 0 | APNG_BLEND_OP_SOURCE |
| 1 | APNG_BLEND_OP_OVER |
blend_op が APNG_BLEND_OP_SOURCE
の場合、アルファを含むフレームのすべての色成分がフレーム領域の現在の内容を上書きします。blend_op が
APNG_BLEND_OP_OVER の場合、フレームはそのアルファに基づいて出力バッファ上に合成され、単純な OVER
演算(Alpha Channel
Processing参照)を使用します。サンプルコードの第2のバリエーションが適用可能である点に注意してください。
最初のフレームについては、再生の開始時に出力バッファがクリアされるため、両方のブレンドモードは機能的に等価であることに注意してください。
デフォルト画像に対応する fcTL チャンク(存在する場合)には次の制約があります:
x_offset と y_offset フィールドは 0 でなければなりません。width と height フィールドは IHDR
チャンクの対応するフィールドと等しくなければなりません。前述のとおり、出力バッファは各再生の開始時に完全に透明な黒で初期化されなければなりません。これは各再生が同一になることを保証するためです。デコーダは結果が同一になる限り明示的なクリア手順を回避してもかまいません。例えば、デフォルト画像がアニメーションに含まれ、かつ
blend_op に APNG_BLEND_OP_SOURCE を使用する場合、出力バッファ全体が上書きされるためクリアは不要です。
Web 互換性のために、このチャンクの開発と展開の間に長い時間差があり PNG 仕様への組み込みが遅れたことから、このチャンク名は例外的にプライベートチャンクであるかのように定義されています。
4バイトのチャンクタイプフィールドには次の16進値が含まれます
66 64 41 54
fdAT チャンクはアニメーションにおいて IDAT チャンクが静止画像に対して果たす役割と同じ役割を持ちます;すなわち fdAT の集合はすべてのフレーム(または静止画像が最初のフレームとして含まれるアニメーションでは最初のフレーム以降のすべて)の image data を含みます。内容は次のとおりです:
| Name | Size |
|---|---|
sequence_number |
4 bytes |
frame_data |
n bytes |
各フレームに対して少なくとも1つの fdAT チャンクが必要です(ただし、そのフレームが IDAT チャンクで表現される最初のフレームである場合を除く)。
各フレームの圧縮データストリームは、同フレーム内のすべての fdAT チャンクの frame_data
フィールドの内容を sequence_number の昇順で連結したものになります。
シーケンス番号が存在するため、fdAT チャンクは長さゼロであってはなりません;ただし frame_data フィールドはゼロ長であり得ます。
伸長すると、このデータストリームは各スキャンラインの先頭にあるフィルタバイトを含む完全なピクセルデータとなり、すべての IDAT チャンクの非圧縮データと同様です。ビット深度、color type、圧縮方式、filter
method、インターレース方式、およびパレット(存在する場合)は static image と同じです。
各フレームは、ファイル内の最初の IDAT チャンクの前に現れる任意のクリティカルまたは補助チャンクによって指定されたすべてのプロパティを継承します。ただし幅と高さは fcTL チャンクから取得されます。
PNG に pHYs チャンクが存在する場合、APNG
画像とその x_offset および y_offset
の値はメイン画像と同様にスケーリングされなければなりません。概念的には、そのようなスケーリングは出力バッファを canvas にマップする際に行われます。
Web 互換性のために、このチャンクの開発と展開の間に長い時間差があり PNG 仕様への組み込みが遅れたことから、このチャンク名は例外的にプライベートチャンクであるかのように定義されています。
この節はエンコーダの動作に関する要件と推奨事項を示します。PNG エンコーダは、前節で規定された形式に準拠する PNG イメージから PNG データストリームを生成しなければなりません。ここに示す追加の推奨事項に従うことで、通常は最良の結果が得られます。
簡単なガンマの導入については C. Gamma and chromaticity を参照してください。
フルカラーマネジメント対応の PNG エンコーダは、ここで説明するよりも高度な計算を行い、iCCP チャンクを使用することを選択する場合があります。もしイメージのサンプルが sRGB 仕様 [SRGB] に準拠していることが分かっているなら、エンコーダは追加のガンマ処理を行わずに sRGB チャンクを書き込むことが強く推奨されます。どちらの場合でも、iCCP や sRGB チャンクを認識しない PNG デコーダ向けに、適切な gAMA チャンクを生成することが推奨されます。
PNG エンコーダは以下を決定する必要があります:
gAMA チャンクに書き込むべき値は、PNG デコーダが期待通りに動作するようにする値です。13.13 Decoder gamma handling を参照してください。
適用すべき変換は、イメージサンプルの性質とその精度に依存します。もしサンプルが浮動小数点や高精度整数で光強度を表している場合(たとえばコンピュータグラフィックスのレンダラから)、エンコーダは PNG データストリームに含めるために整数へ量子化する前に ガンマエンコーディング(指数が1未満のべき関数を適用)を実行することがあります。これにより与えられたサンプル深度でバンディングのアーティファクトが少なくなったり、同等の視覚品質を保ちながらより小さなサンプルを使えたりします。0 から 1 の範囲の浮動小数点値で表現された強度レベルは、次の式でデータストリームのイメージサンプルに変換できます:
integer_sample = floor((2sampledepth-1) * intensityencoding_exponent + 0.5)
式中の intensity が望ましい出力強度を表す場合、encoding_exponent は gAMA チャンクに使用する gamma value になります。
もしエンコーダが利用できる強度が元のシーン強度であるなら、別の変換が必要になることがあります。表示画像が元のソース画像よりコントラストを高くする必要がある場合があります。これは元のシーンから表示出力へのエンドツーエンドの 伝達関数 が 1 より大きい指数を持つことに対応します。この場合:
gamma = encoding_exponent/end_to_end_exponent
もし元の画像がキャプチャまたは計算された条件がそのようなコントラスト変化を正当化するか不明な場合、表示強度は元のシーン強度に比例すると仮定してよい(すなわち end_to_end_exponent は 1)ので:
gamma = encoding_exponent
もし画像がデータストリームにのみ書き込まれるのであれば、エンコーダはエンコーディング指数を自由に選べます。gAMA チャンクに 1/2.2 を与えるような値を選ぶことは、多くの場合妥当です。なぜなら典型的なビデオモニタ上で表示する PNG デコーダの負担を最小にするからです。
いくつかのイメージレンダラはイメージを PNG データストリームへ書き込むと同時に画面にも表示することがあります。表示されるピクセルは、その表示システムと視聴条件に合わせてガンマ補正されるべきであり、ユーザが意図したシーンの適切な表現を目にするようにすべきです。
もしレンダラが画面上に表示されたサンプル値を PNG データストリームへ書き込みたい(データストリームのために別個の ガンマエンコーディング ステップを回避したい)場合、レンダラは表示システムの 伝達関数 をべき関数で近似し、その指数の逆数を gAMA チャンクに書き込むべきです。これにより PNG デコーダはレンダリング中に作成者が画面で見たものを再現できます。
しかしながら、レンダラが表示デバイスに適した表示ピクセルを計算し、データ保存用に別途 ガンマエンコーディング を実行し、将来の使用により適した値を gAMA に入れるようにすることも同様に合理的です。
コンピュータグラフィックスのレンダラはしばしば ガンマエンコーディング を行わず、サンプル値をシーン光強度に直接比例させることが多いです。もし PNG エンコーダが既に整数に量子化されたサンプル値を受け取るなら、それに対して再び ガンマエンコーディング を行う意味はありません;単に情報損失を招くだけです。エンコーダはサンプル値をそのまま PNG データストリームへ書き込むべきです。これは gAMA チャンクに 1.0 を入れるべきだという意味ではありません。なぜならシーン強度から表示出力への望ましいエンドツーエンドの 伝達関数 が線形であるとは限らないからです。しかし望ましい gamma value はおそらく 1.0 に近いでしょう。これはレンダリングされているシーンが屋外の昼光シーンか室内シーンか等に依存するかもしれません。
サンプル値がハードウェアから直接来る場合、正しい gAMA 値は理論上ハードウェアの 伝達関数 とシーンの照明条件から推定できます。ビデオのフレームグラバのような場合、サンプルはおそらく sRGB カラースペースにあるでしょう。イメージスキャナの出力は予測しにくく、CCD センサ自体は線形であるため入力光強度に比例する場合もあれば、スキャナハードウェアが印刷でのドットゲイン補正用のべき関数を既に適用している場合(約 0.57 の指数)や、モニタ表示用に補正済みの場合もあります。特定のスキャナの特性を知るにはマニュアルや校正ターゲットのスキャンが必要になることがあります。gamma はサンプルと望ましい表示出力との関係を表すものであって、スキャナ入力そのものには関係しない点を忘れないでください。
データストリーム形式の変換器は、一般に供給された画像のガンマを別のものへ変換しようとするべきではありません。データは変換せずに PNG データストリームへ保存されるべきであり、可能ならソースデータストリームから gamma value を推定して書き込むべきです。データストリーム変換時のガンマ変更は、表現される強度レベル集合の再量子化を引き起こし、利点がほとんどないまま丸め誤差を追加します。入力から出力へサンプル値をそのままコピーする方がほとんどの場合良いでしょう。
もしソースデータストリームが画像の gamma 特性を記述しているなら、データストリーム変換器は gAMA チャンクを書くことが強く推奨されます。一部の形式は表示指数(画像サンプルを表示出力へマップする関数の指数)を指定します。もしソースファイルの gamma value が 1.0 より大きいなら、それはおそらく表示指数であり、その逆数を PNG の gamma value に使うべきです。もしソースファイルが画像サンプルと表示出力以外の量との関係を記録している場合、PNG の gamma value を推定するのはもっと複雑になります。
もし PNG エンコーダやデータストリーム変換器が、表示システムの 伝達関数 をべき関数で近似できることを知っているなら、その指数を display_exponent として、イメージには次の gamma value を付与できます:
gamma = 1/display_exponent
おおよそ正しい値の gAMA チャンクを書き込む方が、チャンクを省略して PNG デコーダに適当な gamma value を推測させるよりも望ましいです。もし PNG エンコーダが gamma value を推定できないなら、gAMA チャンクを省略する方が望ましいです。推測しなければならない場合は、それを PNG デコーダに任せるべきです。
gamma はアルファサンプルには適用されません;アルファは常に線形で表されます。
また 13.13 Decoder gamma handling も参照してください。
色に関する参考は C. Gamma and chromaticity を参照してください。
フルカラーマネジメント対応の PNG エンコーダは、ここで述べるより高度な計算を行い、iCCP チャンクを使用することを選ぶかもしれません。もしイメージサンプルが sRGB 仕様に準拠すると分かっているなら、PNG エンコーダは sRGB チャンクを使用することが強く推奨されます。
ソースの表示原色の色度を決定できる、または画像の起源や実行ハードウェアに基づいて強い推測ができる場合、エンコーダは cHRM チャンクを出力することが強く推奨されます。もしそれを行うなら、gAMA チャンクも併せて書き込むべきです;デコーダは cHRM だけではあまり利用できません。
原色や ホワイトポイント に関してはいくつかの推奨や標準があり、技術に結びつくものもあります。たとえば CCIR 709 [ITU-R-BT.709] や SMPTE-C [SMPTE-170M] などです。
考慮すべきケースは次の三つです:
手描きやデジタル編集された画像の場合、制作時にどのモニタで表示していたかを特定する必要があります。多くの画像編集プログラムは使用中のモニタ種別を指定でき、内部でデバイス非依存空間を使っていることが多いです。そのようなプログラムは有効な cHRM および gAMA チャンクを書き込むのに十分な情報を持っており、自動的にそれらを書き込むことが強く推奨されます。
エンコーダがフルスペクトルレンダリングを行うコンピュータレンダラの一部としてコンパイルされている場合、内部のデバイス非依存色空間から RGB へ変換するために使用したモニタ値を cHRM チャンクに書くべきです。選択した RGB デバイスのガモット外の色はガモット内にマップされるべきです;PNG はガモット外の色を格納しません。
もしコンピュータレンダラがデバイス依存の RGB 空間で直接計算を行うなら、シーン記述とレンダリングパラメータが特定のモニタに合わせて調整されていない限り cHRM チャンクは書くべきではありません。その場合は、そのモニタのデータを使って cHRM チャンクを構築すべきです。
一部のイメージ形式はキャリブレーション情報を格納しており、それを使って cHRM チャンクを埋めることができます。たとえば TIFF 6.0 [TIFF-6.0] はオプションでキャリブレーション情報を持ち、存在するなら cHRM チャンクの構築に使うべきです。
最近のビデオ機器で作成されたビデオはおそらく CCIR 709 の原色と D65 のホワイトポイントを使用しており、これらは Table 29 に示されています。
| R | G | B | White | |
|---|---|---|---|---|
| x | 0.640 | 0.300 | 0.150 | 0.3127 |
| y | 0.330 | 0.600 | 0.060 | 0.3290 |
古くから広く使われているビデオ標準の一つに SMPTE-C [SMPTE-170M] があり、これは Table 30 に示されています。
| R | G | B | White | |
|---|---|---|---|---|
| x | 0.630 | 0.310 | 0.155 | 0.3127 |
| y | 0.340 | 0.595 | 0.070 | 0.3290 |
データストリーム形式の変換器が供給された画像を別の RGB カラースペースへ変換しようとすることは推奨されません。データは変換せずに PNG データストリームに格納されるべきであり、ソースの原色色度が分かっていればそれを記録すべきです。データストリーム変換時の色空間変換は、ガモットの不一致や丸め誤差のために悪い考えです。ガンマ変換と同様に、データをロスレスに格納し、最終的な表示時に多くても一度だけ変換を行う方が良いのです。
また 13.14 Decoder color handling を参照してください。
アルファチャネルは、透明な部分を一時的に隠すマスクとして考えることも、非矩形イメージを構築する手段と考えることもできます。前者の場合、完全に透明なピクセルの色値は将来の利用のために保持するべきです。後者の場合、透明ピクセルは有用なデータを持たず、PNG が要求する矩形イメージ領域を満たすために存在するだけです。この場合、完全に透明なピクセルには圧縮のために同一の色値を割り当てるべきです。
イメージ作者は、デコーダが透明性制御を完全にはサポートしない可能性があることを念頭に置くべきです(13.16 Alpha channel processing を参照)。したがって、可能であれば透明ピクセルに割り当てる色は合理的な背景色にしておくべきです。
完全なアルファチャネルを必要としない、あるいは圧縮効率の面で許容できないアプリケーション向けに、tRNS 透過チャンクも利用可能です。
もしイメージに既知の背景色があるなら、その色は bKGD チャンクに書き込むべきです。透明性を無視するデコーダであっても、bKGD の色を未使用領域の塗りつぶしに使うことができます。
もし元の画像がプリマルチプライド(associated)アルファを持つ場合、それを PNG の非プリマルチプライド形式へ変換するには、各サンプル値を対応するアルファ値で割り、次に画像ビット深度の最大値を掛け、最も近い整数へ丸めればよいです。有効なプリマルチプライドデータでは、サンプル値が対応するアルファ値を超えることはないので、除算の結果は常に 0 〜 1 の範囲になるはずです。もしアルファ値がゼロなら、出力は黒(ゼロ)にしてください。
PNG で直接表現できないサンプル深度の入力サンプルをエンコードする場合、エンコーダはサンプルを PNG が許容するサンプル深度へ拡大スケールしなければなりません。最も正確なスケーリング方法は線形式です:
output = floor((input * MAXOUTSAMPLE / MAXINSAMPLE) + 0.5)
ここで入力サンプルは 0 から MAXINSAMPLE の範囲で、出力は 0 から MAXOUTSAMPLE(これは 2sampledepth-1)までの範囲です。
線形スケーリングに近い近似は「左ビット複製(left bit replication)」によって得られます。これは有効ビットを最上位ビットにシフトし、開いている下位ビットへ最上位ビットを繰り返して埋める方法です。この方法は線形スケーリングより計算が速いことが多いです。
例えば 5 ビットサンプルを 8 ビットへ拡大する場合を考えます。ソースサンプル値が 27(0-31 の範囲)であれば、元のビットは:
4 3 2 1 0
---------
1 1 0 1 1
左ビット複製は値 222 を与えます:
7 6 5 4 3 2 1 0
----------------
1 1 0 1 1 1 1 0
|=======| |===|
| Leftmost Bits Repeated to Fill Open Bits
|
Original Bits
これは線形式で計算した値と一致します。左ビット複製は通常線形スケーリングと同じ値を与え、最大でも 1 だけ差が出ることはありません。
より精度の低い近似は単に入力値を左シフトして下位ビットをゼロで埋める方法です。この方式は最大値が全て 1 にはならないため白を正確に再現できず、結果として画像がわずかに暗くなります。一般にはこの方法は推奨されませんが、特に 8 ビットより大きなサンプル深度を扱うときに圧縮が改善される効果があります。高いサンプル深度ではゼロフィルスケーリングによる相対誤差は小さいため、いくつかのエンコーダはこれを選ぶかもしれません。ただしアルファチャネルデータに対してゼロフィルは使用してはなりません。多くのデコーダはアルファ値が全ゼロや全 1 の場合を特別扱いするからです。スケーリング後のデータではこれらの値を正確に表現することが重要です。
エンコーダが sBIT チャンクを書き込む場合、格納されたサンプルの高位ビットが元のデータと一致するようにスケーリングを行うことが要求されます。すなわち、もし sBIT が S ビットのサンプル深度を示す場合、格納データの高位 S ビットは元の S ビット値と一致しなければなりません。これによりデコーダは右シフトして元のデータを復元できます。追加される下位ビットには制約がありません。上述のスケーリング方法はすべてこの制約を満たします。
ソースのイメージデータをスケールアップする際、下位ビットはすべてのサンプルで一貫して埋めることが推奨されます。すなわち同じソース値はどの画素位置でも同じ生成サンプル値を生むべきです。これにより異なるサンプル値の数が減り圧縮が改善されます。これは必須ではなく、一部のエンコーダはむしろ下位ビットにディザを施して表示品質を向上させる代わりにファイルサイズを増やすことを選ぶ場合があります。
一部の用途では元のソースデータのレンジが 2 の冪でないことがあります。その場合でも線形スケーリング式は機能しますが、シフト法は適しません。そのような画像では sBIT を書かないことが推奨されます。なぜなら sBIT は元のデータレンジが正確に 0..2S-1 であったことを示唆してしまうからです。
推奨パレットは任意の PNG データストリーム内で sPLT チャンクとして、あるいは PLTE チャンクとして(truecolor の PNG データストリームにおいて)出現することがあります。いずれの場合も、推奨パレットは image data の本質的な一部ではありませんが、インデックスカラ表示ハードウェア上でイメージを表示するために使われ得ます。推奨パレットは truecolor ハードウェア上で動作するビューアには興味がないことがあります。
sPLT チャンクを用いて推奨パレットを提供する場合、エンコーダは周波数フィールドを すべてゼロ(未定義)にせず、パレットエントリの相対的重要性を示すために使用することが推奨されます。周波数値は「最近傍」カウント、すなわちディザを適用しない場合に各 RGBA パレットエントリがどれだけ使われるかの概算として最も容易に計算できます。(これらのカウントは推奨パレットを作る過程で「無料で」得られることが多いです。)推奨パレットは透明情報を含むため、合成されていないイメージに対して計算するべきです。
インデックスカラー画像であっても、sPLT は表示可能色の少ないビューア向けの代替縮小パレットを定義するために使用できます。もし PLTE が bKGD なしで color type 6 のイメージに現れる場合、パレットがどのような状況で計算されたかは未定義です。
truecolor PNG データストリームに推奨パレットを含める古い方法として PLTE チャンクを用いるものがあります。この方法を使うならヒストグラム(周波数)は別の hIST チャンクに置くべきです。PLTE チャンクは透明情報を含まないため、color type 6(truecolor with alpha)の画像では、bKGD チャンクが現れること、そしてパレットとヒストグラムは指定された背景色に対して合成された後の画像を基準に計算されることが推奨されます。この定義は、分数アルファ値を持つピクセルに対して有用なパレットエントリを生成するために必要です。結果のパレットはおそらく同じ背景色で画像を提示するビューアにのみ有用でしょう。PNG エディタ が bKGD を変更または削除する場合、パレットを削除または再計算することが推奨されます(color type)。
color type 2(truecolor)の画像に対しては、PLTE と hIST は透明色の指定を無視して RGB データのみを基準に計算することが推奨されます。もしデータストリームが透過を使っている(tRNS を持つ)場合、ビューアは意図する背景色に合わせて生成されたパレットを容易に適応させることができます(13.17 Histogram and suggested palette usage を参照)。
推奨パレットを提供するにあたり、sPLT チャンクは PLTE チャンクより柔軟です:
sPLT を使う PNG エンコーダは、sPLT を認識しないデコーダとの互換性のために、PLTE と hIST を併せて書き込むことを選べます。
本仕様は 2 種類のインターレース方式(そのうち一つはインターレースなし)を定義します。インターレースはデコーダが画像をプログレッシブに表示するための便利な基盤を提供します(13.10 Interlacing and progressive display を参照)。
color type 3(インデックスカラー)の画像では、フィルタタイプ 0(None)が通常最も効果的です。色数が 256 以下のカラー画像はほとんど常に indexed-color 形式で保存されるべきであり、truecolor 形式ははるかに大きくなる傾向があります。
ビット深度が 8 未満の画像にもフィルタタイプ 0 が推奨されます。低ビット深度のグレースケール画像では、稀に画像をまず 8 ビット表現へ展開してからフィルタを適用することでより良い圧縮が得られることがあります。
truecolor および greyscale の画像では、5 種類のいずれのフィルタが最も効果的かは画像に依存します。固定フィルタを用いるなら Paeth フィルタが最も良いことが多いです。
truecolor および greyscale 画像の最高の圧縮を得るため、もし圧縮効率を速度より重視するなら、各スキャンラインごとにフィルタタイプを選ぶ適応フィルタリングが推奨されます。各画像はそれぞれ最適なフィルタの組合せを持ちます。エンコーダは全てのフィルタの組合せを試して最も圧縮されるものを見つけることもできますが、全探索が許容できない場合、次のような一般的ヒューリスティックが有効です:各スキャンラインについて 5 種類のフィルタすべてを適用して、出力バイトの絶対値の和が最小となるフィルタを選びます(このテストでは出力バイトを符号付き差分として扱ってください)。この方法は単一の固定フィルタを選ぶより通常優れます。
これらの推奨に基づくフィルタ適用は、本仕様で定義されたいずれのインターレース方式と組み合わせても効果的です。
エンコーダは圧縮データストリームを任意に IDAT チャンクへ分割できます。(複数の IDAT チャンクは、エンコーダが固定量のメモリで動作できるようにするために許可されています;通常チャンクサイズはエンコーダのバッファサイズに対応します。)各 IDAT チャンクが 1 バイトのみのデータを含むような PNG データストリームも有効ですが、著しく無駄です。(ゼロ長 の IDAT チャンクも有効ですが、さらに無駄です。)
各テキストチャンクには空でないキーワードを付ける必要があります。もし適切な説明がない場合は汎用キーワード "Comment" を使えます。ユーザ提供のキーワードを使う場合、エンコーダはそのキーワードがキーワードの制限に合致しているかをチェックすべきです。
iTXt チャンクは Unicode の UTF-8 エンコーディングを使うため任意の言語のテキストを格納できます。tEXt および zTXt は Latin-1(ISO 8859-1)を使い、これらのチャンクで使用できる文字の範囲を制限します。エンコーダは文字の範囲を広くしてデータ損失を避けるために iTXt を tEXt や zTXt より優先して使うべきです。エンコーダはローカルのレガシー文字エンコーディングを適切なエンコーディングへ変換してテキストを保存しなければなりません。
iTXt チャンクを作成する際、エンコーダは UTF-8 encode(Encoding Standard)に従うべきです。
エンコーダは 79 個を超える Unicode の code point からなる単一行テキストの作成を思いとどまらせるべきで、読みやすさを促進するべきです。1024 バイト未満のテキスト項目は非圧縮テキストチャンクで出力することが推奨されます。基本的なタイトルや作成者キーワードは非圧縮テキストチャンクで出力することが推奨されます。大きなテキストチャンクを 画像データ の後(すなわち IDAT チャンクの後)に置くと、状況によっては画像表示を速くできることがあります。小さなテキストチャンク(画像タイトルなど)は IDAT チャンクの前に置くことが推奨されます。
エンコーダは、他のアプリケーションが理解する必要のない情報を保持するためにプライベートチャンクを使用しても MAY です。
エンコーダは実験的またはプライベート利用のために非予約フィールド値を使用しても MAY です。
すべての補助チャンクは任意であり、エンコーダはそれらを書かなければならないわけではありません。しかし、情報が利用可能な場合は標準的な補助チャンクを書くことが推奨されます。
本節は PNG デコーダおよびビューアの振る舞いに関するいくつかの要件と推奨事項を示します。ビューアは復号された PNG イメージをユーザに提示します。ビューアとデコーダの振る舞いは密接に関連しているため、ここではデコーダとビューアを一緒に扱います。PNG デコーダに対する唯一の絶対的な要件は、前章で規定された形式に準拠する任意のデータストリームを正しく読み取ることができることです。ただし、通常は以下の追加の推奨事項に従うことでより良い結果が得られます。
PNG デコーダは、本国際規格で明示的に定義された、ビット深度、color type、圧縮方式、filter method、およびインターレース方式のすべての有効な組合せをサポートしなければなりません。
PNG データストリームのエラーは大きく二つのクラスに分かれます:伝送エラーと構文エラーです(4.10 Error handling を参照)。
伝送エラーの例としては、バイトコード 13 および/または 10 がデータストリーム全体にわたって追加・削除・変換される「text」や「ascii」モードでの伝送、データストリームが切断される予期しない終了、あるいは記憶装置上の物理エラーでブロック(通常 512 バイト単位)が乱れたりランダムな値になる場合などがあります。構文エラーの例としては、行フィルタの無効な値、無効な圧縮方式、無効なチャンク長、インデックス画像で最初の IDAT チャンクの前に PLTE チャンクがないこと、あるいは複数の gAMA チャンクの存在などがあります。PNG デコーダは次のようにエラーを処理するべきです:
この方針に関連する PNG チャンクのクラスは三種類あります。この分類における「未知のチャンク」とは、デコーダ作成者にとって真に型が不明なチャンク、あるいは作成者が扱いを既定の方法(デフォルトハンドリング)に任せたために「未知」と扱うことにしたチャンクを指します。他のチャンクは「既知のチャンク」と呼ばれます。この定義に基づく三つのクラスは次のとおりです:
チャンク命名規約の説明は 5.4 Chunk naming conventions を参照してください。
PNG チャンクの型は、表示可能なイメージを取り出すために重要かどうか(IHDR, PLTE, IDAT のように)あるいはデータストリーム構造を理解するために重要かどうか(IEND のように)に応じて「critical」または「ancillary」に分類されます。これは特定の種類の重要度であり、あらゆるデコーダに必ずしも関連するとは限りません。例えば注釈(例えば著作権情報)を抽出するだけのプログラムは表示可能なイメージを必要としませんが、UTF-8 を正しくデコードするべきです。別のデコーダは tRNS や gAMA チャンクを実行上必須と考えるかもしれません。
構文エラーは常に既知のチャンクに関するものです。未知チャンクの構文エラーは検出できないためです。PNG デコーダは状況と要件に応じて構文エラーが致命的(回復不能)かどうかを判断しなければなりません。例えば多くのデコーダは無効な IEND チャンクを無視できます;テキスト抽出プログラムは IDAT の欠如を無視できます;画像ビューアはインデックス画像における空の PLTE チャンクからは回復できませんが、truecolor 画像の無効な PLTE を無視することはできます;アルファチャネルを抽出するプログラムは無効な gAMA を無視できますが、複数の tRNS があることを致命的なエラーと見なすかもしれません。構文エラー以外の異常な状況は次のように扱うべきです:
致命的な状態が発生した場合、デコーダは直ちに失敗し、適切であればユーザにエラーを通知し、オプションとしてすでにユーザに表示されている image data の表示を継続すべきです(つまり「優雅に失敗」する)。アプリケーション全体が終了する必要はありません。
致命的でないエラーが発生した場合、デコーダは適切であればユーザに警告を出し、エラーから回復して通常の処理を継続すべきです。
インデックスカラ PNG をデコードする際に範囲外のインデックスが見つかった場合、その処理は歴史的にデコーダ間でばらつきがありました。ピクセルを不透明の黒として表示する は一般的な回復手段であり、本仕様ではこれを必須とします。古い実装では挙動が異なるため、この振る舞いをエンコーダが前提とすることはできません。
CRC を計算しないデコーダは、明らかな構文エラーを破損の兆候と解釈すべきです(13.2 Error checking も参照)。
圧縮チャンク(IDAT, zTXt, iTXt, iCCP)のエラーはバッファオーバーランにつながる可能性があります。deflate の伸長器を実装する者はこの可能性に備えるべきです。
APNG はデータストリームの全体が読み込まれる前にフレームを逐次表示できるように設計されています。したがって一部のエラーはアニメーションの途中まで検出されない可能性があります。いかなるエラーに遭遇した場合でも、デコーダは以後のすべてのフレームを破棄してアニメーションを停止し、静止画像の表示に戻ることを強く推奨します。アニメーションが開始する前にエラーを検出したデコーダは静止画像を表示すべきです。必要に応じてエラーメッセージをユーザに表示してもよいでしょう。
デコーダは順序が乱れた APNG チャンクをエラーとして扱わなければなりません。APNG 対応の PNG editors はシーケンス番号を用いて正しい順序に復元すべきです。
PNG のエラー処理方針は 13.1 Error handling に記述されています。
未知のチャンク型は、それがクリティカルチャンクでない限りエラーとして扱ってはなりません。
チャンク型の妥当性は、4 バイトすべてが 41-5A および 61-7A(16 進)範囲内かどうかを確認することで判定できます;これは未認識チャンク型に対してのみ行えばよいことに注意してください。もし総データストリームサイズが(ファイルシステム情報や HTTP プロトコル等から)既知であれば、チャンク長の妥当性もチェックできます。CRC をチェックしない場合、バイトの欠落/追加や誤ったチャンク長によりデコーダが同期を失い、以後のデータをチャンクヘッダと誤解する可能性があります。
既知長のチャンク(例えば IHDR)に対しては、予期しないチャンク長をエラーとして扱うべきです。本仕様の将来の拡張では既存チャンクへ新フィールドを追加するのではなく、新しいチャンク型を追加して新情報を運ぶ設計となります。
既知チャンクのフィールドにおける予期しない値(例えば IHDR の圧縮方式フィールドでの未確認値)は検出されエラーとして扱われるべきです。ただし、予期しないフィールド値は クリティカル なチャンクでのみ致命的なエラーとして扱うことが推奨されます。補助チャンクの予期しない値は、そのチャンク全体を未知のチャンク型と同様に無視することで扱うことができます(この推奨はチャンクの CRC が検証済みであることを前提とします。CRC をチェックしないデコーダでは、予期しない値を破損したデータストリームの兆候として扱う方が安全です)。
標準的な PNG 画像は圧縮方式 0 で圧縮されなければなりません。IHDR チャンクの圧縮方式フィールドは将来の標準化や独自拡張のために用意されています。デコーダはこのバイトをチェックし、未認識のコードであればエラーを報告すべきです。詳細は 10. Compression を参照してください。
PNG データストリームは明示的に型付けされたチャンクの集合で構成されます。仕様で内容が定義されたチャンクでも、実際には任意のデータ(悪意のあるコードを含む可能性)を含むことがあり得ます。同様に IEND チャンクの後にあるデータも任意のものであり、悪意あるコードを含む場合があります。そのような悪意あるコードが PNG 画像のデコードの結果として受信側のコンピュータ上で実行されるという既知のリスクはありません。しかしながら悪意のあるアプリケーションが無害に見える画像ファイル内にコードを隠し、その後それを実行する可能性はあります。
将来のチャンク型に関連する可能性のあるセキュリティリスクは現時点で特定できません。将来の公開チャンクを定義する際にはセキュリティ問題が考慮されます。未知または未実装のチャンク型には追加のセキュリティリスクはありません。なぜならそのようなチャンクは無視されるか、最大でも別の PNG データストリームへコピーされるだけだからです。
iTXt, tEXt, zTXt チャンクはキーワードと表示用のプレーンテキストを含みます。iCCP および sPLT もキーワードを含み、表示用テキストです。デコーダがこれらのテキストを制御文字、特に ESC(エスケープ)文字をフィルタリングせずに表示すると、一部のシステムや端末で望ましくない動作や安全上の問題を引き起こす可能性があります。デコーダはこのリスクを避けるために制御文字を除去することを推奨します;詳細は 13.7 Text chunk processing を参照してください。
eXIf チャンクについては、Exif 仕様 [CIPA-DC-008] において、タグの「value offset」ポインタが実際にファイル内の有効なアドレスを指すべきという明示的な要件は含まれていません。この要件は暗黙的に示唆されるのみです(Exif IFD 構造を説明するパラグラフ 4.6.2 を参照)。いずれにせよ、デコーダは無効なポインタに遭遇する可能性に備え、それらを適切に処理するべきです。
すべてのチャンクは長さフィールドで始まるため、バッファオーバーフローを試みるような不正なチャンクに対して脆弱でないデコーダを書くのが容易になります。各チャンク末尾の CRC は偶発的な破損に対する強力な防御手段を提供します。PNG シグネチャバイトは一般的なファイル伝送エラーを早期に検出するためのものです。
CRC をチェックしないデコーダはデータ破損に晒される可能性があります。その唯一のありそうな結果は画像内のピクセル表示の誤りです。もっと悪い事態としては、IHDR チャンクの CRC をチェックせず、幅や高さフィールドが破損していると重大な問題が発生することがあります。詳細は 13.2 Error checking を参照してください。
不適切に書かれたデコーダはチャンクが極めて大きく(最大 231-1 バイト)なり得ることからバッファオーバーフローの対象となるかもしれません。しかし、適切に書かれたデコーダは大きなチャンクを問題なく扱います。
一部の画像編集ツールは歴史的に、編集領域のアルファチャネルをゼロに設定するだけで実際の画像データを削除していないまま機密情報を抹消したつもりになることがありました。そのような画像を見た目だけで信頼すると、実際の画像データが容易に復元され得るためプライバシーリスクがあります。
同様に、一部の画像編集ツールは IHDR の幅と高さを書き換えることで切り取り(clipping)を行い、画像データ自体を再エンコードしないため、新しい幅と高さの外側に元のデータが残り復元される可能性があります。
eXIf チャンクを含む画像は、自動的に付加されるデータ(例えば写真の GPS 座標)を含んでいることがあり、ユーザが PNG にそのようなデータが含まれていることに気づいていないとプライバシー上のリスクになり得ます。(Exif を含む他の画像形式、例えば JPEG/JFIF も同様のリスクがあります。)
デコーダはチャンク型を単純な 4 バイトのリテラル比較で認識しなければなりません;チャンク型に対して大文字小文字変換を行うのは誤りです。補助ビットが 1 の未知チャンクに遭遇したデコーダは安全にそのチャンクを無視して画像表示を続行できます。補助ビットが 0(クリティカル)である未知チャンクに遭遇した画像抽出を試みるデコーダは、その画像に安全に解釈できない情報が含まれていることをユーザに示すべきです。
デコーダは未知のチャンク型の性質を指定されたビットを数値的にテストすることで検証すべきです。文字が大文字か小文字かをテストするのは非効率であり、ロケール特有の大文字小文字定義を用いた場合に誤りとなることがあります。
予約ビットが 1 に設定されている場合はエラーを報告すべきではありません。将来の PNG 仕様でこのビットに意味が定義される可能性があるためです。このビットがセットされたチャンクは他の未知チャンク型と同様に扱えば十分です。
チャンク型のプライベートビットは機能的な意味を持たず、W3C によって定義されたチャンクと個別定義のチャンクの衝突を避けるために使用されるものであるため、デコーダはこれをテストする必要はありません。
すべての補助チャンクは任意です;デコーダはそれらを無視できます。しかし、適切かつ可能であればデコーダはこれらのチャンクを解釈することが奨励されます。
非正方ピクセルは表現可能です(11.3.4.3 pHYs Physical pixel dimensions を参照)が、ビューアがそれを考慮する義務はありません;ビューアは任意の PNG データストリームをピクセルが正方形であるかのように提示できます。
表示のピクセルアスペクト比が PNG データストリームで定義された物理ピクセル寸法のアスペクト比と異なる場合、ビューアは適切な表示のために画像をリスケールすることが強く推奨されます。
pHYs チャンクの unit specifier が 0(単位不明)の場合、デコーダの挙動は 2 つの pixels-per-unit
値の比に依存してもよいですが、その大きさには依存すべきではありません。例えば pHYs が
(ppuX, ppuY, unit) = (2, 1, 0) を含む場合、それは (1000, 500, 0)
を含むものと同等です;どちらも画像のピクセルが幅の 2 倍の高さを持つことを示す有効な指示です。
ビューアが画像と表示装置のピクセルアスペクト比の違いを扱う一つの合理的な方法は、画像を水平方向か垂直方向のどちらか一方に拡大することです。スケール係数は次の浮動小数点計算で得られるかもしれません:
image_ratio = pHYs_ppuY / pHYs_ppuX
display_ratio = display_ppuY / display_ppuX
scale_factor_X = max(1.0, image_ratio/display_ratio)
scale_factor_Y = max(1.0, display_ratio/image_ratio)
面積維持など他の方法も合理的であり、pHYs チャンクを無視することも許容されるため、作成者はすべてのビューアがこのスケーリング方法を使うと仮定すべきではありません。
ピクセルアスペクト比の補正に加えて、ビューアは水平方向および垂直方向の追加スケーリングを行う理由があるかもしれません。例えばディスプレイに収まらないほど大きな画像を縮小したり、高解像度プリンタへ送る際に表示と同じ物理寸法に見えるよう拡大する場合などです。
現実的であれば、PNG デコーダはデータストリーム内で見つかったすべての iTXt、tEXt、および zTXt チャンクをユーザに表示する手段を持つべきです。デコーダが特定のテキストキーワードを認識しなくても、ユーザはそれを理解できるかもしれません。
tEXt および zTXt
を処理する際、デコーダは許可されていない文字に遭遇する可能性があります。一部は安全に表示できます(例えば TAB, FF, CR、16 進で 09, 0C, 0D)が、特に ESC 文字(16 進
1B)は表示ハードウェアやソフトウェアに予期せぬ動作を引き起こす可能性があり安全上の危険をもたらすかもしれません。デコーダは tEXt
または zTXt で見つかった非 Latin-1 文字(改行および場合によっては TAB
を除く)を直接表示しようとすべきではありません。代わりにそれらを無視するか、"\nnn" のような可視表記で表示するべきです。詳細は 13.3 Security
considerations を参照してください。
iTXt チャンクを処理する際、デコーダは UTF-8 decode(Encoding Standard)に従うべきです。
エンコーダは改行を linefeed(16 進 0A)で表すことが推奨されていますが、デコーダはこれに依存すべきではありません。CR, LF, CR-LF といった一般的な改行の組合せすべてを認識し、それぞれを単一の改行として表示するのが最良です。TAB は 8 の倍数の列に整列するために適切な数のスペースに展開できます。
非 Latin-1 のレガシー文字エンコーディングを持つシステム上で動作するデコーダは、Latin-1
文字が正しく表示されるよう文字コードをリマップすべきです。サポートされない文字はシステムに適した置換文字(例えば U+FFFD REPLACEMENT CHARACTER、U+003F QUESTION
MARK、または U+001A SUB)に置き換えるか、"\nn"
のような可視表記にマップするべきです。文字はデコードシステム上で印字可能な文字である場合にのみ表示されるべきです。一部のバイト値はデコードシステム上で制御文字として解釈され得るため、そのようなシステム上で動作するデコーダはこれらの制御文字を表示しないべきです(セキュリティのため)。
デコーダは、エンコーダが 79 文字を超える行を作らないよう推奨されているにもかかわらず、改行間に任意の数の印字文字を含むテキストチャンクを表示できる用意をしておくべきです。
本仕様で用いる圧縮技術は、伸長を開始する前に圧縮データストリーム全体が利用可能であることを要求しません。したがって伸長済みデータ全体が得られる前に表示を開始できます。将来の本仕様のバージョンで用いられる一般的な圧縮手法がこの性質を失う可能性は極めて低いと考えられます。
IDAT チャンク境界は意味的な重要性を持たず、圧縮データストリームの任意の点で現れ得ることを強調することが重要です。image data(例えばスキャンライン境界)と deflate ブロック境界や IDAT チャンク境界との間に必須の相関はありません。完全な image data は、複数の zlib データストリームとして表現され、それがいくつかの IDAT チャンクに格納されます;デコーダがこれ以上のものを仮定するのは誤りです。エンコーダの実装によってはこれらの構造が関連づけられる場合もありますが、デコーダはそれに依存してはなりません。
フィルタの効果を逆にするために、デコーダは同じ行の前のピクセル、前行の現在ピクセルのすぐ上のピクセル、および前行の左隣のピクセルの復号済み値を使う必要がある場合があります。これはデコーダが常に少なくとも 1 行分の image data を保持しておく必要があることを意味します。いくつかのフィルタタイプは前行を参照しないものもありますが、次の行がその参照を使うかもしれないため、デコーダは各スキャンラインをデコードするごとに格納する必要があります。詳細は 7.3 Filtering を参照してください。
デコーダはインターレースされた画像を読み取ることが要求されます。参照画像が 5 列未満または 5 行未満の場合、いくつかのパスは空になります。エンコーダとデコーダはこのケースを正しく扱わなければなりません。特に、フィルタタイプバイトは非空のスキャンラインにのみ関連付けられており、空の縮約画像にはフィルタタイプバイトは存在しません。
低速伝送リンク上で画像を受信する場合、ビューアはインターレース画像を段階的に表示することで知覚的性能を改善できます。これは各縮約画像を受信するごとに、これまで受信したデータに基づく完全画像の近似を表示することを意味します。受信した各ピクセルをまだ伝送されていない右下方向の位置を覆う長方形に拡大して塗りつぶすという単純で見栄えの良い効果が得られます。この処理は以下の ISO C コードで説明できます [ISO_9899]:
/*
variables declared and initialized elsewhere in the code:
height, width
functions or macros defined elsewhere in the code:
visit(), min()
*/
int starting_row[7] = { 0, 0, 4, 0, 2, 0, 1 };
int starting_col[7] = { 0, 4, 0, 2, 0, 1, 0 };
int row_increment[7] = { 8, 8, 8, 4, 4, 2, 2 };
int col_increment[7] = { 8, 8, 4, 4, 2, 2, 1 };
int block_height[7] = { 8, 8, 4, 4, 2, 2, 1 };
int block_width[7] = { 8, 4, 4, 2, 2, 1, 1 };
int pass;
long row, col;
pass = 0;
while (pass < 7)
{
row = starting_row[pass];
while (row < height)
{
col = starting_col[pass];
while (col < width)
{
visit(row, col,
min(block_height[pass], height - row),
min(block_width[pass], width - col));
col = col + col_increment[pass];
}
row = row + row_increment[pass];
}
pass = pass + 1;
}
関数 visit(row,column,height,width) は次に送られてくるピクセルを取得し、その色で指定された高さと幅の長方形(左上隅が指定の行と列)を塗ります。row と
column は左上隅を 0,0 とした測度であることに注意してください。
ビューアが受信した画像を背景画像と合成している場合、受信したピクセル位置だけを描画する方が都合がよいかもしれません(visit()
は指定の行と列のピクセルのみを設定し、長方形全体を塗るわけではありません)。これにより新しい画像が徐々に古い画像を置き換える「フェードイン」効果が得られます。この方法の利点は各ピクセルが置き換えられるたびに適切なアルファまたは透過処理が行えることです。上で説明したように長方形を塗る方法は、後に受信されるピクセルが完全または部分的に透明である場合に必要となる背景画像のピクセルを上書きしてしまい得ます。これは背景画像がオフスクリーンに保存されていない場合にのみ問題になります。
PNG のユニバーサルな交換性という目標を達成するために、デコーダはすべての種類の PNG イメージを受け入れなければなりません:indexed-color、 truecolor、および greyscale。indexed-color 表示ハードウェア上で動作するビューアは、表示のために truecolor イメージを indexed-color に縮約できる必要があります。この処理は「カラ量子化(color quantization)」と呼ばれます。
カラ量子化の簡単で高速な方法は、イメージを固定パレットへ縮約することです。均一な色間隔のパレット(いわゆる「カラキューブ」)はピクセルごとの計算を最小にするために通常用いられます。写真のような画像の場合、滑らかなグラデーションに不自然な段差が生じないようにディザリングが推奨されますが、ディザリングは雑味(graininess)を導入するため好ましくない場合もあります。
レンダリング品質は、画像固有に選ばれたパレットを使うことで大幅に改善され得ます。というのも、カラキューブには特定の画像で使われないエントリが多く含まれることが一般的だからです。この方法では、まずパレットを選ぶ作業、次に個々のピクセルを最も近い色にマップする作業が必要になり、作業量が増えます。PNG ではエンコーダが推奨パレットを提供できるようになっていますが、すべてのエンコーダがそれを行うわけではなく、提供された推奨パレットが不適切である可能性もあります(色数が多すぎる/少なすぎるなど)。したがって、高品質なビューアはパレット選択ルーチンを持っている必要があります。個々のピクセルを十分な速度でパレットエントリへマップするためには、大きなルックアップテーブルが通常もっとも実行可能な方法です。
カラ量子化の実装は多数存在します。PNG のサンプル実装である libpng (http://www.libpng.org/pub/png/libpng.html)
にはこの目的のためのコードが含まれています。
デコーダは表示のために PNG データをより低いサンプル深度(データ精度)へ縮小したい場合があります。例えば、16 ビットデータは現在のほとんどの表示ハードウェアで利用するために 8 ビット深度へ縮小する必要があります。8 ビットから 5 ビットへの縮小も一般的です。
最も正確なスケーリングは次の線形式で得られます
output = floor((input * MAXOUTSAMPLE / MAXINSAMPLE) + 0.5)
ここで
MAXINSAMPLE = (2sampledepth)-1
MAXOUTSAMPLE = (2desired_sampledepth)-1
わずかに精度が落ちる変換として、単に (sampledepth - desired_sampledepth) ビットだけ右シフトする方法があります。例えば 16 ビットサンプルを 8
ビットに縮小するには低位バイトを破棄できます。多くの状況ではシフト法は表示目的には十分な精度を持ち、速度面で有利です。(ただしもし gamma 補正が行われる場合、サンプルの再スケーリングは
gamma
補正のルックアップテーブルへ統合でき、これは 13.13
Decoder gamma handling に示されています。)
デコーダがサンプルを拡大する必要がある場合(例えば frame buffer のサンプル深度が PNG イメージより大きい場合)、12.4 Sample depth scaling に記述されたように線形スケーリングまたは左ビット複製(left-bit-replication)を使用するべきです。
sBIT チャンクが存在する場合、参照用の image data は sBIT で指定されたサンプル深度へ右シフトして復元できます。線形スケーリングは必ずしも元のデータを再現しないことに注意してください。なぜならエンコーダが上向きスケーリングに線形スケーリングを使ったと要求されているわけではないからです。しかしエンコーダは高位ビットを保つ方法を用いることが要求されているため、右シフトは常に機能します。これはシフト法が線形スケーリングより正確であると言える唯一のケースです。デコーダは sBIT を無視してもかまいません;格納された画像は IHDR チャンクで示されたサンプル深度の有効な PNG データストリームです。しかし sBIT を使って表示用にスケーリングする前の元のサンプルを回復することは、sBIT を無視するよりもより正確な表示をもたらすことが多いです。
tRNS チャンク値とピクセル値を比較して透過ピクセルを検出する場合、比較は正確に行われなければなりません。したがって、透過ピクセル検出はサンプル精度を下げる前に行わなければなりません。
ガンマに関する簡単な導入は C. Gamma and chromaticity を参照してください。
フルカラーマネジメント対応のビューアは、ここで述べるよりも高度な計算を行うでしょう。
正しいトーン再現を行うために、表示プログラムはサンプルと表示出力との関係、および表示システムの transfer function を考慮する必要があります。これは次のように計算することで行えます:
sample = integer_sample / (2sampledepth - 1.0)
display_output = sample1.0/gamma
display_input = inverse_display_transfer(display_output)
framebuf_sample = floor((display_input * MAX_FRAMEBUF_SAMPLE)+0.5)
ここで integer_sample はデータストリームからのサンプル値、framebuf_sample は frame buffer に書き込む値、MAX_FRAMEBUF_SAMPLE はフレームバッファサンプルの最大値(8 ビットなら 255、5 ビットなら 31 など)です。第一行は整数サンプルを 0.0〜1.0 範囲の正規化された浮動小数点値へ変換します。第二行は望ましい表示出力強度に比例する値へ変換し、第三行は表示システムの transfer function を考慮し、第四行は整数のフレームバッファサンプルへ変換します。0 を正のべき乗に上げると 0 になります。
第二行と第三行の間にステップを挿入して、実際の視聴条件と参照視聴条件の差を補正することもできます。しかしこの補正は veiling glare、black mapping、色の見え方モデルなどを考慮する必要があり、べき関数だけでは良く近似できません。ここではそのような計算は記述しません。視聴条件を無視しても通常誤差は小さいです。
表示の transfer function は通常、指数 display_exponent によるべき関数で近似できます。その場合、第二行と第三行は次のようにまとめられます:
display_input = sample1.0/(gamma * display_exponent) = sampledecoding_exponent
これによりべき乗計算を 1 回だけ行えばよくなります。カラー画像ではこの計算を R, G, B 各々について行います。
gAMA チャンクから gamma value を直接取得できます。あるいはアプリケーションでユーザが表示外観を調整できるようにして gamma value に影響を与えられるようにすることも可能です。例えば、ユーザはデフォルト 1.0 のパラメータ user_exponent を手動で設定し、アプリケーションは次のように設定できます:
gamma = gamma_from_file / user_exponent
decoding_exponent = 1.0 / (gamma * display_exponent)
= user_exponent / (gamma_from_file * display_exponent)
ユーザは中間階調を暗くしたいときは user_exponent を 1 より大きく、明るくしたいときは 1 より小さく設定します。
gAMA チャンクにゼロが入っていると意味を成しませんが、誤って出現することがあります。デコーダはそれを無視し、エディタはそれを破棄してユーザに警告してもよいでしょう。
すべてのピクセルごとに超越関数を計算する必要はありません。代わりに、各可能なサンプル値に対して正しい出力値を与えるルックアップテーブルを事前に作成できます。これは 8 ビット精度なら各イメージにつき 256 回の計算だけで済みます。インデックスカラー画像では、パレットの一度だけの補正で十分です(画像が透過を使っていて非一様な背景に表示する場合を除く)。
浮動小数点計算が使えない場合でも、gamma 補正テーブルは整数演算と事前計算した対数表を使って作成できます。例コードは [PNG-EXTENSIONS] にあります。
入力イメージの gamma value が不明な場合(gAMA、sRGB、および iCCP がすべてない場合)、単体の画像ビューアは妥当と思われるデフォルトの gamma value を選ぶべきですが、結果が暗すぎる/明るすぎる場合にはユーザが新しい値を選べるようにすべきです。デフォルトの gamma value は、画像がインターネット由来かローカル由来かなど他の情報に依存して決めてもよいでしょう。HTML のような文書形式や SVG のようなベクタ形式のビューアは、未タグの PNG 画像を他の未タグ画像と同様に扱うべきです。
実際には、どの表示指数を用いるべきかを決めるのはしばしば難しいです。システムに組み込みの gamma 補正がない場合、表示指数は主に CRT によって決まります。特定の CRT の詳細な較正測定がない限り、表示指数 2.2 を用いるべきです。
多くの現代の frame buffers には gamma 補正を実行するためのルックアップテーブルがあり、これらのシステムでは表示指数はそのルックアップテーブルと CRT の複合指数であるべきです。ビューア内からルックアップテーブルの内容を取得できない場合、ユーザに表示システムの指数値を入力してもらう必要があるかもしれません。残念ながら、異なるメーカーはルックアップテーブルの指定方法が異なるため、システムの gamma value の解釈はシステム依存になります。
実際の表示器の応答は単一の数値(表示指数)で表せるよりも複雑です。もしモニタの電圧入力に対する光出力の実測値が利用可能なら、上記の第三・第四行はこれらの実測値を参照することで置き換えられ、望ましい明るさに最も近い実際のフレームバッファ値を求めることができます。
色に関する参照は C. Gamma and chromaticity を参照してください。
多くの場合、PNG データストリーム内の image data はデバイス依存の RGB 値として扱われ、(適切な gamma 補正を除いて)変更せずに表示されます。これは最速の表示方法ですが、ビューアが元の画像の作成者とまったく同じ表示ハードウェアを用いない限り、特に暗色やほぼ中立の色において色は作成者が見たものと完全には一致しません。cHRM チャンクは、単なる gamma 補正よりも緻密な色合わせを可能にする情報を提供します。
cHRM データは image data を RGB から XYZ へ変換し、さらに CIE LAB のような知覚的に線形な色空間へ変換するために使えます。色を CIE LAB 空間で分割すれば最適パレットを生成できます。というのも CIE LAB における 2 色間の幾何学的距離は、人間の見た目での差異と強く相関するからです(RGB や XYZ 空間とは異なります)。得られたパレットを再び RGB へ戻して表示に用いるか、PLTE チャンクへ書き込むことができます。
画像処理アプリケーションの一部として動作するデコーダは、解析のために image data を CIE LAB 空間へ変換することもあるでしょう。
色忠実度が重要な用途(プロダクトデザイン、科学的可視化、医療、建築、広告など)では、PNG デコーダはソース RGB から表示に用いるモニタの display RGB 空間への変換を行えます。これはソース RGB → XYZ の行列と XYZ → 表示 RGB の行列を計算し、それらを合成して全体の変換を得ることを含みます。PNG デコーダはガモットマッピングを実装する責任があります。
プラットフォームにカラーマネジメントシステム(CMS)が備わっている場合、デコーダは image data、gAMA、および cHRM の値を CMS に渡して表示やさらなる処理を行わせることができます。
カラー印刷機能を提供する PNG デコーダは、Level 2 PostScript の機能を使ってキャリブレートされた RGB 空間や XYZ のようなデバイス非依存色空間で image data を指定できます。これは単純な RGB→CMYK 変換よりも良い色忠実度を提供します。PostScript Language Reference マニュアル [PostScript] に例が示されています。そのようなデコーダはソース RGB(cHRM に指定)とターゲットプリンタ間のガモットマッピングを実装する責任があり、PostScript インタプリタが所望の色を生成します。
PNG デコーダは cHRM データを使用して、カラー画像の正確なグレースケール表現を計算できます。RGB からグレイへの変換は単に XYZ の Y(輝度)成分を計算することであり、これは R, G, B の重み付き和です。重みはモニタの種類、すなわち cHRM チャンクの値に依存します。PNG デコーダは cHRM を持たないデータストリームに対してこれを行いたい場合があります。その場合の妥当なデフォルトは CCIR 709 原色です [ITU-R-BT.709]。オリジナルの NTSC 原色は、PNG 画像が本当にそのようなモニタ用に色合わせされていない限り 使用すべきではありません。
bKGD チャンクで指定された背景色は、通常画像周辺の未使用スクリーンスペースや、画像内の透過ピクセルを塗りつぶすために使用されます。(したがって、画像が透過を使用していない場合でも bKGD は有効かつ有用です。)もし bKGD チャンクが存在しない場合、ビューアは適切な背景色を決定する必要があります。他に情報がない場合、8 ビット sRGB カラースペースで 153 のような中間灰色が妥当な選択です。透明な黒や白のテキストや暗いドロップシャドウなどは、この背景に対して判読可能です。
特定の背景で画像を提示するビューア(ウェブブラウザなど)は bKGD を無視し、自身の好む背景色や背景画像で bKGD を上書きすべきです。
bKGD チャンクで示された背景色は、たとえそれが tRNS チャンクで示された色と一致していても、透明とは見なされません(または、indexed-color 画像の場合に tRNS が透過としてマークしているパレットインデックスに対応する場合でも同様です)。さもなければ背景の「背後に何か」を想定して合成しなければならなくなります。背景色は使用されるか無視されるかのどちらかであり、PNG イメージと他の背景の間の中間レイヤーではありません。
実際、多くの場合 bKGD と tRNS が同じ色を指定することが普通です。そうすれば透過処理を実装していないデコーダでも、部分的に透明なピクセルが存在しない限り意図した表示が得られます。
アルファチャネルは前景イメージを背景イメージに合成(composite)するために使用できます。PNG データストリームは前景画像と透過マスクを定義しますが、背景画像は定義しません。PNG デコーダはこの最も一般的なケースをサポートすることを要求されません。多くのデコーダは単一の背景色に対する合成をサポートすることが期待されます。
合成されたサンプル値を計算する式は次の通りです:
output = alpha * foreground + (1-alpha) * background
ここで alpha および入出力サンプル値は 0〜1 の分数で表されます。この計算は強度サンプル(gamma エンコードされていないサンプル)で行うべきです。カラー画像の場合、R, G, B の各サンプルについて個別に計算します。
以下のコードは、前景画像を背景画像に合成する一般的なケースを示します。背景画像の元のピクセルデータが利用可能であり、出力が表示用の frame buffer であると仮定します。他のバリエーションも可能です;コード下のコメントを参照してください。このコードは前景画像と背景画像のサンプル深度や gamma values が異なっていて、表示システムに最適化されていない場合でも動作するようにしています。実際には何も仮定せずまずチェックすべきです。
このコードは ISO C 構文で、コメント参照用に行番号を付しています。
01 int foreground[4]; /* image pixel: R, G, B, A */
02 int background[3]; /* background pixel: R, G, B */
03 int fbpix[3]; /* frame buffer pixel */
04 int fg_maxsample; /* foreground max sample */
05 int bg_maxsample; /* background max sample */
06 int fb_maxsample; /* frame buffer max sample */
07 int ialpha;
08 float alpha, compalpha;
09 float gamfg, linfg, gambg, linbg, comppix, gcvideo;
/* Get max sample values in data and frame buffer */
10 fg_maxsample = (1 << fg_sample_depth) - 1;
11 bg_maxsample = (1 << bg_sample_depth) - 1;
12 fb_maxsample = (1 << frame_buffer_sample_depth) - 1;
/*
* Get integer version of alpha.
* Check for opaque and transparent special cases;
* no compositing needed if so.
*
* We show the whole gamma decode/correct process in
* floating point, but it would more likely be done
* with lookup tables.
*/
13 ialpha = foreground[3];
14 if (ialpha == 0) {
/*
* Foreground image is transparent here.
* If the background image is already in the frame
* buffer, there is nothing to do.
*/
15 ;
16 } else if (ialpha == fg_maxsample) {
/*
* Copy foreground pixel to frame buffer.
*/
17 for (i = 0; i < 3; i++) {
18 gamfg = (float) foreground[i] / fg_maxsample;
19 linfg = pow(gamfg, 1.0 / fg_gamma);
20 comppix = linfg;
21 gcvideo = pow(comppix, 1.0 / display_exponent);
22 fbpix[i] = (int) (gcvideo * fb_maxsample + 0.5);
23 }
24 } else {
/*
* Compositing is necessary.
* Get floating-point alpha and its complement.
* Note: alpha is always linear; gamma does not
* affect it.
*/
25 alpha = (float) ialpha / fg_maxsample;
26 compalpha = 1.0 - alpha;
27 for (i = 0; i < 3; i++) {
/*
* Convert foreground and background to floating
* point, then undo gamma encoding.
*/
28 gamfg = (float) foreground[i] / fg_maxsample;
29 linfg = pow(gamfg, 1.0 / fg_gamma);
30 gambg = (float) background[i] / bg_maxsample;
31 linbg = pow(gambg, 1.0 / bg_gamma);
/*
* Composite.
*/
32 comppix = linfg * alpha + linbg * compalpha;
/*
* Gamma correct for display.
* Convert to integer frame buffer pixel.
*/
33 gcvideo = pow(comppix, 1.0 / display_exponent);
34 fbpix[i] = (int) (gcvideo * fb_maxsample + 0.5);
35 }
36 }
バリエーション:
/*
* Gamma encode for storage in output datastream.
* Convert to integer sample value.
*/
gamout = pow(comppix, outfile_gamma);
outpix[i] = (int) (gamout * out_maxsample + 0.5);
また、アルファがゼロのときに背景ピクセルを処理する必要があり、ただスキップするだけではなく、行 15 は背景ピクセルを処理するために行 17-23 のコピーに置き換える必要があります。
/*
* Convert frame buffer value into intensity sample.
*/
gcvideo = (float) fbpix[i] / fb_maxsample;
linbg = pow(gcvideo, display_exponent);
ただし丸め誤差が生じる可能性があるため、可能なら元の背景ピクセルを利用する方が望ましいです。
注:浮動小数点演算では入力サンプル値が 0〜1 の間に保証され、合成は常に入力値の範囲内に収まるため、オーバーフローやアンダーフローのチェックは不要です。整数演算の場合は丸め誤差解析が必要になり得て、オーバーフローやアンダーフローが発生しないことを保証する必要があります。
フルアルファチャネルを持つ PNG 画像を表示する際は、たとえ背景が単なる黒であっても画像を何かの背景に合成できることが重要です。アルファを無視すると、associated-alpha 表現から変換された PNG 画像は見た目が正しくなくなります。(もちろんアルファチャネルが別個の透明マスクである場合、アルファを無視するのは隠された部分を回復するために有用なオプションになります。)
デコーダが真の合成ロジックを実装していない場合でも、アルファ値が 0 と 1 のみを含む画像への対処は簡単です(これは greyscale や truecolor の PNG データストリームが tRNS チャンクを使う場合に暗黙的に当てはまります。indexed-color PNG データストリームの場合、tRNS が 0 と 255 以外の値を含むかどうかを簡単にチェックできます。)この単純なケースでは、透過ピクセルは背景色で置き換えられ、他のピクセルは変更されません。
もしデコーダがこれだけの透過機能しか持たない場合、フルアルファチャネルを扱うときは、すべての非ゼロアルファ値を不透明として扱うか、あるいはディザリングするべきです。いずれの方法も associated-alpha 形式から変換された画像に対してはあまり良い結果を与えませんが、何もしないよりは望ましいです。フルアルファを二値アルファへディザするのは、グレースケールを白黒へディザするのと非常に似ていますが、完全に透明なピクセルと完全に不透明なピクセルはディザによって変更されないようにするべきです。
indexed-color ハードウェア上で truecolor 画像を表示しようとするビューア、またはフレームバッファーが受け入れられるよりも大きなパレットを持つ indexed-color 画像に対しては、エンコーダが一つ以上の推奨パレットを sPLT チャンクで提供している場合があります。サイズや(場合によっては)名前に基づいてそれらの中から適切なものが見つかった場合、PNG デコーダはそのパレットを使用できます。デコーダが必要とするものとサンプル深度が異なる推奨パレットは、サンプル深度の再スケーリングで変換できます(13.12 Sample depth rescaling参照)。
背景が単色である場合、ビューアは画像と推奨パレットをその色に対して合成(composite)し、得られた画像を元に RGB パレットへ量子化するべきです。画像が透過を使用していて背景が単色でない場合、推奨パレットはほとんど役に立たないでしょう。
truecolor 画像の場合、推奨パレットは PLTE チャンクにも含められていることがあります。画像が tRNS チャンクを持ち背景が単色である場合、ビューアは望ましい背景色に合わせて推奨パレットを調整する必要があります。その方法としては、tRNS の色に最も近いパレットエントリを望ましい背景色に置き換えるか、ビューアが PLTE エントリ数より多くの色を扱えるなら背景色用のパレットエントリを追加する、などがあります。
color type 6(truecolor with alpha)の画像については、任意の PLTE チャンクは bKGD チャンクで指定された単色背景に対して画像を表示するために設計されているはずです。ビューアが異なる背景を使うつもりである場合や bKGD チャンクが存在しない場合は、そのパレットを無視するのが妥当でしょう。異なる背景で表示するために推奨パレットを使うことは可能ですが、結果はあまり良くない場合があります。
ビューアが透明な truecolor 画像を非均一な背景(単色より複雑な背景)に対して提示する場合、推奨パレットが合成(composite)された画像に最適であることはほとんど期待できません。この場合は、truecolor PNG 画像と背景画像を先に合成し、その結果画像を色量子化するのが最良です。
truecolor の PNG データストリーム内で PLTE と sPLT の両方のチャンクが現れる場合、PNG デコーダは両者が提案するパレットの中から選ぶことができますが、上述した透明性に関する違いを考慮に入れるべきです。
sPLT および hIST チャンクの周波数情報は、ビューアが PNG データストリームで使用されているパレットと同じだけの色を提供できない場合に有用です。もしビューアがほんの数色しか不足していないなら、パレットの使用頻度が最も低い色を削るだけで十分な場合が多いです。色数を大幅に減らす必要がある場合は、既存パレットのサブセットを使おうとするよりも、まったく新しい代表色を選ぶ方が良いです。これは新しい色量子化処理を行うことに相当しますが、既存のパレットとヒストグラムを入力データとして使えば、IDAT チャンク中の image data を走査する手間を省くことができます。
推奨パレットが提供されていない場合、デコーダは自前でパレットを生成できますが、そのためには IDAT チャンク内の image data を一度走査する必要があり追加のコストがかかります。代わりにデフォルトのパレット(おそらくカラキューブ)を使用することもできます。
関連項目は 12.5 Suggested palettes を参照してください。
作者は新しいチャンク型を検討する前に、本仕様や [PNG-EXTENSIONS] にある既存のチャンク型を確認することが奨励されます。PNG-EXTENSIONS にあるチャンク型は、本仕様で定義されたものよりも広くサポートされないことが予想されます。
PNG editors の例として、テキストチャンクを追加・変更するプログラムや、truecolor PNG データストリームに推奨パレットを追加するプログラムが挙げられます。一般的な画像編集ソフトは画像を読み込む際に未認識の情報を破棄するため、通常は PNG editors とは見なされません。
PNG に新しいチャンク型を追加できるようにするためには、すべてのチャンク型に対する並び順の要件について規則を確立する必要があります。さもなければ、PNG editor が未知のチャンクに遭遇したときに何をすべきか分からなくなります。
例: 仮想的な新しい補助チャンク型があって、それは PLTE が存在する場合に PLTE の後に現れることが要求されるとします。プログラムがその新チャンクを認識せずに PLTE を追加しようとすると、誤って新チャンクの後に PLTE を挿入してしまう可能性があります。このような問題は、未知チャンクをすべて破棄するように PNG editors に強制すれば防げますが、それは非常に魅力のない解決策です。代わりに、PNG は補助チャンクにこのような厳しい順序制約を持たせないことを要求します。
この種の問題を将来の拡張を許容しつつ防ぐために、PNG editors の振る舞いとチャンクの並び順に制約が課されています。safe-to-copy ビットは、修正されるデータストリーム内の未認識チャンクの取り扱いを定義します。
チャンクの並び順を決める規則は次の通りです。
これらの規則は入力データストリームから出力データストリームへチャンクをコピーする観点で表現されていますが、データストリームをその場で修正する場合にも明白な方法で適用されます。
また 5.4 Chunk naming conventions を参照してください。
PNG editors が image data を変更しない場合、tIME チャンクを変更してはなりません。tEXt、zTXt、および iTXt チャンクの Creation Time キーワードは、ユーザ提供の時刻として使用できます。
クリティカルチャンクには任意の並び順要件があり得ます。というのも PNG editors は未知のクリティカルチャンクに遭遇した場合に終了することが要求されるからです。例えば IHDR には常に最初に現れるという特定の順序規則があります。PNG エディタ、または PNG を書き出す任意のプログラムは、自身が生成できるクリティカルチャンク型の順序規則を知り、それに従わなければなりません。
補助チャンク型に対する最も厳しい順序規則は次のとおりです:
特定の補助チャンク型に対する実際の順序規則はこれより緩やかであることがあります。例えば標準的な補助チャンク型の順序規則は 5.6 Chunk ordering に示されています。
デコーダは、任意の補助チャンクが他の補助チャンクに対して特定の位置にあると仮定してはなりません。特に、ある私的な補助チャンクが常に IEND の直前に現れると仮定するのは安全ではありません。特定のアプリケーションがいつもその位置に書いている場合でも、PNG editor がその後に別の補助チャンクを挿入する可能性があるためです。ただし、そのチャンクが IDAT と IEND の間のどこかに残ることは安全に仮定できます。
非規範(non-normative)としてマークされた節に加え、本仕様のすべての作成ガイドライン、図、例、および注記は非規範的です。それ以外の本仕様の全内容は規範的です。
本文書中のキーワード MAY、MUST、SHALL、 SHOULD、および SHOULD NOT は、BCP 14 [RFC2119] [RFC8174] に従って解釈されますが、その場合に限り、すなわちここに示すようにすべて大文字で現れるときのみ適用されます。
本節は PNG データストリーム、PNG エンコーダ、PNG デコーダ、および PNG エディタ の適合性を扱います。
本節における仕様の主な目的は次のとおりです:
適合性は PNG データストリームおよび PNG エンコーダ、デコーダ、エディタについて定義されます。
本節は PNG データストリームと実装要件、ならびに PNG エンコーダ、PNG デコーダ、及び PNG エディタ に許容される差異の範囲を扱います。本節はエンコーダ、デコーダ、またはエディタの環境要件、性能要件、またはリソース要件を直接扱うものではありません。
本節の適用範囲は、PNG データストリームの公開される相互交換のための規則に限定されます。
PNG データストリームが本仕様に適合するためには、次の条件を満たしている必要があります。
PNG エンコーダが本仕様に適合するためには、次の条件を満たす必要があります。
PNG デコーダが本仕様に適合するためには、次の条件を満たす必要があります。
PNG エディタ が本仕様に適合するためには、次の条件を満たす必要があります。
これは image/png インターネット・メディアタイプの既存登録を更新するものです。トップレベル型は image です。本付録は BCP 13 および W3CRegMedia に準拠しています。
PNG 文書は明示的に型付けされた「チャンク」の集合で構成されます。PNG 仕様で定義された各チャンク型(gIFx を除く)について、それらのチャンクに関連する唯一の効果は受信者の表示またはプリンタ上で画像をレンダリングさせることです。
gIFx チャンク型はアプリケーション拡張データをカプセル化するために使われ、そのデータの利用はセキュリティリスクを呈する可能性がありますが、既知のリスクは報告されていません。同様に、将来のチャンク型(特に未登録のもの)に関連するセキュリティリスクは評価できません。ただし PNG ワーキンググループは「実行可能」データを含むチャンクが登録チャンクになることを許さない意図を持っています。
テキストチャンクである tEXt、iTXT、および zTXt は、コメント等として表示可能なデータを含みます。いくつかの OS や端末は埋め込まれた制御文字を含むテキスト表示によりキー再割当やファイル作成などの操作を許す場合があるため、その理由からテキストチャンクは直接表示する前に制御文字でフィルタすることが仕様で推奨されています。
PNG 形式はファイル伝送エラーの早期検出を容易にするよう設計されており、チャンク内のデータ整合性を保証するために巡回冗長検査(CRC)を使用します。
この登録は以前のものを更新するものです:
この付録は BCP 13 および W3CRegMedia に準拠しています。
APNG 文書は明示的に型付けされた「チャンク」の集合で構成されます。PNG 仕様で定義された各チャンク型(gIFx を除く)について、それらのチャンクに関連する唯一の効果は受信者の表示上でアニメーション画像をレンダリングさせることです。
gIFx チャンク型はアプリケーション拡張データをカプセル化するために使われ、その利用はセキュリティリスクを呈する可能性がありますが、既知のリスクはありません。同様に将来のチャンク型(特に未登録のもの)に伴うセキュリティリスクは評価できません。ただし PNG ワーキンググループは「実行可能」データを含むチャンクが登録チャンクになることを許さない意図を持っています。
テキストチャンク(tEXt、iTXt、および zTXt)はコメント等として表示可能なデータを含みます。いくつかの OS や端末は埋め込まれた制御文字を含むテキストを表示することでキー再割当やファイル作成などの操作を行わせる可能性があるため、テキストチャンクは直接表示する前に制御文字でフィルタすることが推奨されます。
PNG 形式はファイル伝送エラーの早期検出を容易にするよう設計されており、チャンク内のデータ整合性を確保するために巡回冗長検査(CRC)を用います。
もし静的画像チャンクとアニメーション画像チャンクが混在する APNG ファイルを作成した場合、APNG をサポートしないツールを使う者は静的画像しか見えず、追加コンテンツに気づかないことがあります。この状況は例えばモデレーションを回避するために悪用され得ます。
image/apng は 2015 年以来広く未登録で使用されてきました。Animated PNG は 2022 年まで公式 PNG 仕様の一部ではありませんでした。本登録と PNG 仕様(第3版)は既に広く展開されている現実と公式文書を整合させるものです。
この節は規範的ではありません。
以下は私的チャンクの定義に関するガイドラインです:
この節は規範的ではありません。
gamma value は、画像の取り込みや再現で遭遇する非線形な transfer functions の近似を記述するために用いられる数値パラメータです。gamma value はべき法則の関数における指数です。 例えば次の関数:
intensity = (voltage + constant)exponent
は CRT(Cathode Ray Tube)表示器の非線形性をモデル化するために使われます。本国際規格では、この constant が 0 であると仮定することが多いです。
本規格の目的のために、一般的な画像パイプラインにおいて非線形な transfer functions が現れ、べき法則でモデル化できる可能性のある五つの位置を考えることが便利です。それぞれに関連する特徴的な指数には特定の名前が付けられます。
| input_exponent | イメージセンサの指数。 |
| encoding_exponent | データストリームを書き込むプロセスやデバイスが実行する任意の transfer function の指数。 |
| decoding_exponent | ソフトウェアが image data ストリームを読み取る際に行う任意の transfer function の指数。 |
| LUT_exponent | frame buffer と表示デバイスの間で適用される transfer function の指数(通常はルックアップテーブルによって適用される)。 |
| output_exponent | 表示デバイスの指数。CRT の場合、通常約 2.2 に近い値になります。 |
いくつかの合成された transfer functions、すなわち段階の組合せを記述する追加の概念を定義することが便利です。
| display_exponent |
frame buffer と表示装置の表示面の間で適用される transfer function の指数。display_exponent = LUT_exponent * output_exponent
|
| gamma | PNG データストリーム内のサンプルへ表示出力強度を写像する関数の指数。gamma = 1.0 / (decoding_exponent * display_exponent)
|
| end_to_end_exponent | イメージセンサの入力強度から表示出力強度へマッピングする関数の指数。一般に 1.0 から 1.5 の範囲の値です。 |
PNG の gAMA チャンクは gamma value を記録するために使用されます。この情報は、デコーダが表示環境に関する追加情報と組み合わせて、望ましい表示出力を達成または近似するために使用され得ます。
この主題に関する追加情報は [GAMMA-FAQ] にあります。
画像エンコーディングに対するカラースペースの影響に関する追加情報は [Kasson] および [Hill] にあります。
chromaticity とカラースペースに関する背景情報は [COLOR-FAQ] にあります。
以下のサンプルコード — 参考情報 — は、PNG チャンクで用いられる CRC(Cyclic Redundancy Check)の実用的な実装を示します。(正式な仕様については ISO 3309 [ISO-3309] や ITU-T V.42 [ITU-T-V.42] を参照してください。)
サンプルコードは ISO C [ISO_9899] のプログラミング言語で書かれています。表 Table 31 のヒントは C 以外のユーザがコードを読みやすくする助けになるでしょう。
| 演算子 | 説明 |
|---|---|
&
|
ビット単位の AND 演算子。 |
^
|
ビット単位の排他的 OR 演算子。 |
>>
|
ビット単位の右シフト演算子。ここでのように符号なし量に適用されると、右シフトは左側にゼロを挿入します。 |
!
|
論理否定演算子。 |
++
|
"n++" は変数 n をインクリメントします。for ループではテストの後に適用されます。 |
0xNNN
|
0x は 16 進定数を示します。接尾辞 L は long 値(少なくとも 32 ビット)を示します。 |
/* Table of CRCs of all 8-bit messages. */
unsigned long crc_table[256];
/* Flag: has the table been computed? Initially false. */
int crc_table_computed = 0;
/* Make the table for a fast CRC. */
void make_crc_table(void)
{
unsigned long c;
int n, k;
for (n = 0; n < 256; n++) {
c = (unsigned long) n;
for (k = 0; k < 8; k++) {
if (c & 1)
c = 0xedb88320L ^ (c >> 1);
else
c = c >> 1;
}
crc_table[n] = c;
}
crc_table_computed = 1;
}
/* Update a running CRC with the bytes buf[0..len-1]--the CRC
should be initialized to all 1's, and the transmitted value
is the 1's complement of the final running CRC (see the
crc() routine below). */
unsigned long update_crc(unsigned long crc, unsigned char *buf,
int len)
{
unsigned long c = crc;
int n;
if (!crc_table_computed)
make_crc_table();
for (n = 0; n < len; n++) {
c = crc_table[(c ^ buf[n]) & 0xff] ^ (c >> 8);
}
return c;
}
/* Return the CRC of the bytes buf[0..len-1]. */
unsigned long crc(unsigned char *buf, int len)
{
return update_crc(0xffffffffL, buf, len) ^ 0xffffffffL;
}
この節は規範的ではありません。
この付録は PNG ソフトウェア開発者のためのいくつかのインターネット上のリソースの所在を示します。インターネットの性質上、このリストは不完全であり変更される可能性があります。
ICC プロファイル仕様は次で参照できます: https://www.color.org/
PNG の World Wide Web サイトは http://www.libpng.org/pub/png/ にあります。このページは
PNG と PNG 関連ツールに関する最新情報の中心的な場所です。
deflate の追加ドキュメントや移植可能な C コード、および最適化された CRC アルゴリズムの実装は zlib
のウェブサイト https://www.zlib.net/ で入手できます。
移植可能な C によるサンプル実装、libpng は http://www.libpng.org/pub/png/libpng.html
で入手できます。libpng のサンプルビューアおよびエンコーダアプリケーションは http://www.libpng.org/pub/png/book/sources.html
で入手可能で、PNG: The Definitive Guide [ROELOFS] に詳述されています。テスト画像も PNG
ウェブサイトからアクセスできます。
この節は非規範です。
Video Full Range Flag の説明を改善これまで定義されていたが非公式であった Animated PNG (APNG) 用の 3 つのチャンクが追加されました:
これにより PNG 仕様は広く展開されている業界の実践と整合します。
cICP チャンク(ビデオ信号タイプ識別のための Coding-independent code points)を追加しました。これは [ITU-T-H.273] で定義された画像形式メタデータを含めるもので、PNG が [ITU-R-BT.2100] の High Dynamic Range(HDR)および Wide Color Gamut(WCG)画像を含められるようにします。
画像のカラースペースを定義するチャンクが複数存在する場合の優先順位が明確に定義されました。
以前定義されていた eXIf チャンクは PNG-Extensions 文書から本仕様の本文へ移されました。これはその使用の増加を反映するためです。
HDR コンテンツのトーンマッピング支援のために、マスタリング時に使用された表示の色空間を記述する mDCV チャンクと、ピークおよびフレーム平均輝度レベルを記述する cLLI を追加しました。これにより異種プラットフォーム間でのより正確な色合わせが可能になります。
ICC プロファイルを含む iCCP チャンクは、ICC.1 仕様の任意のバージョンに準拠するプロファイルを含め得ることを明確にしました。PNG Second Edition は当時の v2 のみを参照していましたが、その後業界実務としてより高いバージョンも用いられるようになっています。
インデックスカラー PNG における範囲外インデックスの取り扱いを明確化
未知かつ無効な補助チャンクのエラー回復を明確化
PNG Second Edition Errata の全てを取り込みました。特に、未特定のガンマ値を持つ PNG 画像が HTML や SVG のような形式に埋め込まれた場合、それらは untagged images として扱われるべきであることを明確にしました。
コミュニティからのフィードバックに基づく様々な編集上の明確化
参照を最新版へ更新
マークアップの修正およびリンク修正
ドキュメントソースを ReSpec に合わせて再フォーマット
W3C 推奨 PNG Specification Version 1.0 と PNG Second Edition の間の変更一覧は、PNG Second Edition changelist を参照してください。
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in:
Referenced in: