画像データの実際のバイトサイズを変更せずに、ImageMagickでDPIを変更したい

画像データの実際のバイトサイズを変更せずに、ImageMagickでDPIを変更したい

GIMP では、私がやりたいことを非常に簡単に実行できます。ドイツ語のダイアログしかインストールしていませんが、翻訳してみます。 に移動して、Picture -> PrintingSize値とを調整する方法X-Resolutionについて説明していますY-Resolution。これは、いわゆる DPI 値として知られています。デフォルトでは である形式を選択することもできますPixel/Inch。(ドイツ語では、ダイアログはBild -> Druckgrößeであり、X-Auflösungと ですY-Auflösung)

わかりました。そこにある値は多くの72場合デフォルトです。たとえば、これを変更すると、300画像はコンピューター上では同じままですが、印刷すると、見たときに小さくなりますが、すべての詳細はそのままで、小さくなるだけです -> 印刷された用紙の解像度が高くなります (ただし、サイズは小さくなります...私にとっては問題ありません)。

私は LaTeX で作業しているとき、または正確にはpdflatex最近の Ubuntu マシンのコマンドで作業しているときによくこれを行います。GIMP で上記のプロセスを手動で実行すると、すべて正常に動作します。結果として得られる PDF では画像は小さく表示されますが、印刷品質は高くなります。

私がやろうとしているのは、GIMP に入って DPI 値を調整するプロセスを自動化することです。ImageMagick は優れたツールとして知られており、私は他の多くのタスクに使用していたので、このツールで目的を達成しようとしました。しかし、このツールでは私の望みどおりに機能しません。

いろいろ試してみた結果、これが実際に私の友達になるべきコマンドだと思いました。

convert input.png -density 300 output.png

これにより、Web のどこでも読み取ることができるので、DPI が 300 に設定されるはずです。 動作するようです。 ファイルをチェックすると、同じままです (編集: 上で説明したように、これは期待どおりです)。

file input.png output.png
     input.png: PNG image data, 611 x 453, 8-bit grayscale, non-interlaced
    output.png: PNG image data, 611 x 453, 8-bit grayscale, non-interlaced

このコマンドを使用すると、希望どおりの結果が得られたようです。

identify -verbose output.png | grep 300
    Resolution: 300x300
    PNG:pHYs                 : x_res=300, y_res=300, units=0

(面白いことに、同じ出力が返されるのでinput.png混乱します...これは監視すべき間違ったパラメータなのかもしれません)

しかし今、TeX を でレンダリングすると、pdflatex画像はまだ大きくてぼやけています。また、GIMP で画像を再度開くと、DPI 値は72ではなく に設定されています300。つまり、実際にはまったく効果はありませんでした。

さて、ここで何が問題なのでしょうか。私は何かを完全に間違えているのでしょうか。GIMP ではすべて正常に動作しているので、私が間違っているはずはありません。

これに関してご助力いただければ幸いです。Linux システムで簡単に実行できる他の自動化ソリューションも検討します。

答え1

単位を指定します - このオプションを省略すると問題が発生したように思います (DPI がデフォルトのはずですが)。例:

convert -units PixelsPerInch input.png -density 300 output.png

GIMP が解像度を読み取るためにどの埋め込みデータ フィールドを使用するかご存知ですか。ImageMagick が使用する標準のフィールドを上書きする独自のフィールドがあるのでしょうか。たとえば、Photoshop は と を使用するため、Photoshop:XResolution密度Photoshop:YResolution設定を認識できるように Photoshop にこれらを設定する必要があります (ImageMagick ではこれができません。ExifTool を使用します)。

答え2

どう説得すればいいのかわからなかった変換するメタデータのみを追加し、[モノクロ] ビットマップを再エンコードしないようにしました。これにより、ファイルが 50% 以上拡大しました。

私は発見したpngクラッシュ(ImageMagick ツールではありません) は密度メタデータを追加することもできます。このコマンド ラインは 600dpi としてマークし、その他の最適化を許可して、ファイル サイズを約 10% 削減します。

pngcrush -res 600 in.png out.png

答え3

Exiftoolを使用して解像度を読み出すことができます。たとえば、Exiftool '-*resolution*' c.jpg次のように表示されます。

解像度単位: インチ X解像度: 300 Y解像度: 300

Exiftool でもパラメータを設定できますが、マニュアル ページに記載されているようにImage::ExifTool::TagNames、Extra Tags XResolution と YResolution は Exiftool では書き込みできません。

ImageMagick に解像度変更オプションがあるかどうかはわかりませんが、ないとしたら驚きです。また、このようなタスクを自動化する GIMP スクリプトを書くのは簡単ですし、小さなプログラムで解像度を変更することも可能です。たとえば、次の C プログラム ( でコンパイル可能gcc setRes.c -O3 -Wall -o setRes) は、jpeg ファイルの最初の数バイトを読み取り、解像度を 300 に変更して書き換えます。示されているプログラムは、x86 などのリトルエンディアン マシン用の定数を使用しています。ビッグエンディアンのマシンで実行すると、Error: xyz may be not a .jpg filexyz が 0 であっても、のようなメッセージで終了します。JPEGファイルです。注意:私は で結果の画像をテストしていませんpdflatex。おそらく、 に質問を投稿する価値があると思います。テックス SE

/* jiw -- 24 Sep 2012 -- Re: set resolution in a jpg -- Offered without
warranty under GPL v3 terms as at http://www.gnu.org/licenses/gpl.html
*/
#include <stdlib.h>
#include <stdio.h>
void errorExit(char *msg, char *par, int fe) {
  fprintf (stderr, "\n%3d Error: %s %s\n", fe, msg, par);
  exit (1);
}
// Note, hex constants are byte-reversed on little vs big endian machines
enum { JF=0x464a, IF=0x4649, L300=0x2c01, B300=0x012c, NEWRES=L300};
int main(int argc, char *argv[]) {
  FILE *fi;
  short int buf[9];
  int r, L=sizeof buf;
  if (argc<2) errorExit(argv[0], "requires a .jpg file name", 0);
  fi = fopen(argv[1], "r+b");
  if(!fi) errorExit("open failed for", argv[1], ferror(fi));
  r = fread(buf, 1, L, fi);
  if (r != L) errorExit("read failed for", argv[1], ferror(fi));
  if (buf[3] != JF || buf[4] != IF) // Check JFIF signature
    errorExit(argv[1], "may be not a .jpg file", 0);
  buf[7] = buf[8] = NEWRES;
  fseek(fi, 0, SEEK_SET);
  r = fwrite(buf, 1, L, fi);
  if (r != L) errorExit("write failed for", argv[1], ferror(fi));
  return 0;
}

答え4

「画像データの実際のバイトサイズを変更せずに、Imagemagick を使用して DPI を変更したい。」

これは完全に不可能です!

なぜなら:

     more "Dots per Inch" 
<==> more pixels per area 
<==> more total pixels per image 
<==> more total bytes per image

また、DPI が実際に何であるかを理解していないようです。

  1. これは完全に抽象的な値であり、印刷物や画面またはモニター上のレンダリングの絶対サイズも把握している場合にのみ実用的な価値を持ちます。
    • まったく同じ 72 x 72 ピクセルの画像を 1 インチ幅の正方形に「印刷」できます。印刷物の解像度は になります72dpi
    • 1/4 インチ幅の正方形に「印刷」することもできます。その場合、印刷物の解像度は になります288dpi
    • 注: 1 インチ四方に「印刷」すると288dpi、同じ画像ではなくなります。プリンタ ドライバまたはその他のフィルタリング メカニズムによって何らかの外挿が行われ、72 x 72 ピクセルの画像ではなく 288 x 288 ピクセルの画像になります...
  2. どちらの印刷物にもまったく同じ画像情報が含まれます。288dpi の画像に突然多くの情報が含まれることはありません。

72x72ピクセルの元の画像を1インチ幅の正方形で印刷したい場合288dpi再スケール画像を拡大します (この場合は拡大します)。元の画像の 1 ピクセルごとに、拡大された新しい画像の 4 ピクセルが必要になります。これらの 4 ピクセル (そのうち 3 つは新しいピクセル) の色の値を計算するために使用できるさまざまなアルゴリズムがあります。

  • 元のピクセルと同じ値を与えることもできます(これは非常に「生の」アルゴリズムですが、
  • または、元のピクセルのカラー値と隣接するピクセルのカラー値を平均化することもできます。

いずれにしても、それぞれ 288 ピクセルの高さ (288 x 288 ピクセル) の 288 行のピクセルで構成される、より大きな画像を作成します。

Gimp が「画像 -> 印刷サイズ」を実行すると、絶対ピクセル サイズで必要な変更を再計算するプロセスが簡素化され、より使いやすくなります。この目的のために...

  • ...最初に DPI について尋ねられるのは、特定のプリンターが印刷解像度を任意に変更できないためです (プリンターによっては、1 つだけでなく、2 つまたは 3 つの異なる解像度を提供できるものもあります)。そのため、どの解像度で印刷するかを尋ねられます。これが最初の情報です。
  • ...次に、2 番目の情報として、印刷物を用紙にどのサイズ ( cmmmまたは) で表示するかが尋ねられます。inch

Gimp は、これら 2 つの情報に基づいて、要求された解像度で要求されたスペースを埋めるために使用する必要があるピクセルの合計数 (元のピクセル数から推定) を計算します。

しかし、ラスター画像を拡大してピクセル数を増やしても、実際の情報が追加されるわけではなく、架空の「品質」が追加されるだけです。見てスケールアップ アルゴリズムが「優れた」ものであれば、人間の目には見栄えが良くなります。一方、単純なアルゴリズムのように、既存のピクセルを 2 倍、3 倍、または 4 倍にすると、見栄えが悪くなります。

ラスター画像の場合、
DPI設定は、印刷または表示中プリンターやモニターは固定の解像度を提供しているため、これは... という情報のみです。

  • ...プリンタドライバまたは
  • ...印刷をサポートする画像処理アプリケーション

知っておく必要があります。

そしてImageMagickのドキュメント私に完全に同意します:

-density width
-density widthxheight
画像の水平解像度と垂直解像度を設定する デバイスへのレンダリング。

ベクター画像またはファイル形式の場合
(PDFやPostScriptなど)DPI設定は、ラスタライズそれらを使用します。DPI が高いほど、より多くの画像情報がラスター形式に転送されるため、実際の元の品質からより多くの詳細が保持されます。、mmまたはcmの指定されたサイズのベクター画像inchをより高い DPI でラスターに変換すると、画像の合計ピクセル数が増加します。

また、ImageMagick は「印刷」そのものをサポートしていません。代わりに、ImageMagick は...

  • ...特定のラスター形式から他のラスター形式にファイルを変換します。
  • ...またはラスター画像を縮小または拡大します。
  • ...または、特定のアルゴリズムに従って色の値を変更します。
  • ...または、画像を切り取ったり、重ね合わせたり、反転したり、ミラーリングしたりします。
  • ...などなど....

...ただし、操作した画像を印刷するには、別のプログラムを使用する必要があります。

一部の画像形式 (TIFF、PNG など) では、メタデータ内に DPI 設定を内部的に保存することがサポートされています。

しかし、これは単なる「ヒント」属性であり、基礎となるラスター イメージを変更しません。これが、この発見をした理由です。

「ファイルを確認すると、同じままです。」

この「ヒント」は、プリンタ ドライバや LaTeX などのページ作成プログラムによって自動的に評価される可能性があります。このような DPI「ヒント」がない場合 (または何らかの理由で LaTeX が期待する方法で表示されない場合) でも、LaTeX は、ページ上の任意の画像を期待どおりにレンダリングするように指示できます。必要なのは、画像の周囲にもう少し明示的な LaTeX コードを追加することだけです。

他の画像形式 (JPEG(?)、BMP、...) では、内部メタデータに DPI ヒントを保存することすらサポートされていません。

つまり、Gimp は画像を印刷したいので、「画像 -> 印刷サイズ」で実行しているものだけをサポートしています。ImageMagick では印刷できません。

印刷するときに、Gimp でやりたいことをやり続けてください。ImageMagick では意味がありません。

参照この追加のIMドキュメントスニペット、これはまったく同じトピックを別の言葉で説明しています。


それで残るのは次のようになります:

  • Gimp で画像を「操作」し、その結果を LaTeX に埋め込むと、ページは期待どおりに表示されます。
  • ImageMagickで画像を「操作」し、その結果をLaTeXに埋め込むと、ページは次のようになります。ない期待通りです。

上記の問題を解決するには、以下を提供してください。

  • ImageMagick インストールの正確なバージョン (convert -versionおよびの完全な出力convert -list configure)。
  • オリジナルのサンプル画像へのリンク
  • Gimp で操作した同じ画像 (へのリンク)
  • ImageMagick で操作された同じ画像 (へのリンク)。

こうすることで、問題解決に貢献できます。

ただし、これは現在の件名/見出しが尋ねている問題とは異なることに注意してください。「画像データの実際のバイトサイズを変更せずに、Imagemagick で DPI を変更したい」


アップデート

それはまだ上記で述べた内容が一部の読者には明確でないと思われるので、もう一度試してみます...

記載されているものは何でも'解決'または'密度'画像ファイルの中には、メタデータ属性ファイルに記述される実際のピクセル数には影響せず、この点ではまったく無関係です。ヒント印刷やレンダリングデバイス、またはアプリケーションがあるいはそうではないかもしれない画像を印刷、レンダリング、または表示するときに従ってください。

この目的のために、これは画像ファイル内に保存されるいくつかの数字です。これらの数字は、プリンタやディスプレイなどの出力デバイスに、画像が 1 インチあたり何ドット (またはピクセル) で表示されるかを伝えます。PostScript、PDF、MWF、SVG などのベクター形式の場合、画像で使用される実際の座標を描画するためのピクセル スケールを伝えます。

一例として、ImageMagickが画像メタデータ内に記録した解像度の値は、ないアプリケーションによって尊重されるのはAdobe Photoshopです。Photoshopは、希望する印刷解像度や表示解像度に関するヒントを、独自のプロファイルに保存します。8ビムImageMagickは、画像ファイルのメタデータに解像度の変更を書き込むように求められても、このプロファイルには触れません。一方、Photoshopは、この目的のために定義された標準のメタデータフィールドに格納されたImageMagickのすべての解像度のヒントを、独自のものを見つけるとすぐに無視します。8ビムプロフィール。

OP は次の見出しを選択すべきでした:

  • 「画像の実際のピクセル数を変えずに、ImageMagick で DPI (メタデータ解像度のヒント) を変更したい」

あらゆる誤解を避けるために...

関連情報