既存のpdf
(サイズ)を圧縮する方法について、Googleで多くの検索を行っています。私の問題は
C#プログラムで実行する必要があるため、どのアプリケーションも使用できません。
私のクライアントは予算を使いたくないので、私は有料ライブラリを使用できません。したがって、有料ライブラリは確かに[〜#〜] no [〜#〜]
私は過去2日間家事をしていて、iTextSharp、BitMiracleを使用した解決策に出会いましたが、前者はファイルの1%しか減らなかったので、それは有料です。
私はPDFcompressNETとpdftkにも出会いましたが、それらの.dllを見つけることができませんでした。
実際には、pdfは2〜3枚の画像(白黒)と約70ページのサイズで5 MBの保険証券です。
PDFのみの出力が必要です(他の形式にすることはできません)
これを行う方法を次に示します(これは、使用するツールキットに関係なく機能するはずです)。
24ビットRGBまたは32ビットcmykイメージがある場合は、次の手順を実行します。
そうは言っても、監視なしでこれをすべてうまくやることができれば、それ自体で商品ができあがります。
これのほとんどは Atalasoft dotImage (免責事項:無料ではありません。私はそこで作業します。ほぼすべてのPDFツールを作成しました。以前は作業していたと言えます)アクロバット)。
DotImageを使用する特定の方法の1つは、画像のみのページをすべて取り出し、それらを再圧縮して新しいPDFに保存してから、元のページからすべてのページを取得して新しいPDFを作成することです。文書化し、それらを再圧縮されたページに置き換えて、再度保存します。それほど難しいことではありません。
List<int> pagesToReplace = new List<int>();
PdfImageCollection pagesToEncode = new PdfImageCollection();
using (Document doc = new Document(sourceStream, password)) {
for (int i=0; i < doc.Pages.Count; i++) {
Page page = doc.Pages[i];
if (page.SingleImageOnly) {
pagesToReplace.Add(i);
// a PDF image encapsulates an image an compression parameters
PdfImage image = ProcessImage(sourceStream, doc, page, i);
pagesToEncode.Add(i);
}
}
PdfEncoder encoder = new PdfEncoder();
encoder.Save(tempOutStream, pagesToEncode, null); // re-encoded pages
tempOutStream.Seek(0, SeekOrigin.Begin);
sourceStream.Seek(0, SeekOrigin.Begin);
PdfDocument finalDoc = new PdfDocument(sourceStream, password);
PdfDocument replacementPages = new PdfDocument(tempOutStream);
for (int i=0; i < pagesToReplace.Count; i++) {
finalDoc.Pages[pagesToReplace[i]] = replacementPages.Pages[i];
}
finalDoc.Save(finalOutputStream);
ここで欠けているのはProcessImage()です。 ProcessImageはページをラスタライズし(画像がPDFに合わせて拡大縮小されている可能性があることを理解する必要はありません)、画像を抽出し(そして画像の変換行列を追跡し)、上記の手順を実行します。これは簡単なことではありませんが、実行可能です。
私はあなたが言及したライブラリのいずれかが完全に無料ではないことをクライアントに知らせたいと思うかもしれません:
上記のすべてを考えると、freeware要件をドロップできると思います。
Docotic.Pdfは、破壊的な変更を導入することなく 圧縮されたPDFと圧縮されていないPDFのサイズを小さくする をさまざまな程度に変更できます。
ゲインはPDFのサイズと構造に依存します。小さなファイルまたはほとんどがスキャンされた画像であるファイルの場合、削減はそれほど大きくない可能性があるため、ファイルを使用してライブラリを試し、自分で確認する必要があります。
サイズとが最も気になる場合、ファイルには多くの画像とこれらの画像の品質をいくらか失うことに問題がない場合は、Docotic.Pdfを使用して既存の画像を簡単に再圧縮できます。
以下は、すべての画像をバイレベルにし、ファックス圧縮で圧縮するコードです。
static void RecompressExistingImages(string fileName, string outputName)
{
using (PdfDocument doc = new PdfDocument(fileName))
{
foreach (PdfImage image in doc.Images)
image.RecompressWithGroup4Fax();
doc.Save(outputName);
}
}
RecompressWithFlate
、RecompressWithGroup3Fax
、RecompressWithJpeg
メソッドもあります。
ライブラリは、必要に応じてカラー画像を2値画像に変換します。 deflate圧縮レベル、JPEG品質などを指定できます。
Docotic.Pdfは、PDFの大きな画像のサイズを変更することもできます(同時に再圧縮することもできます)。これは、ドキュメント内の画像が実際に必要な画像よりも大きい場合や、画像の品質がそれほど重要でない場合に役立ちます。
以下は、幅または高さが256以上のすべての画像を拡大縮小するコードです。拡大縮小された画像は、JPEG圧縮を使用してエンコードされます。
public static void RecompressToJpeg(string path, string outputPath)
{
using (PdfDocument doc = new PdfDocument(path))
{
foreach (PdfImage image in doc.Images)
{
// image that is used as mask or image with attached mask are
// not good candidates for recompression
if (!image.IsMask && image.Mask == null && (image.Width >= 256 || image.Height >= 256))
image.Scale(0.5, PdfImageCompression.Jpeg, 65);
}
doc.Save(outputPath);
}
}
画像は、ResizeTo
メソッドの1つを使用して、指定された幅と高さにサイズ変更できます。 ResizeTo
メソッドは画像のアスペクト比を保持しようとしないことに注意してください。適切な幅と高さを自分で計算する必要があります。
免責事項:私はビットミラクルで働いています。
PdfSharp の使用
public static void CompressPdf(string targetPath)
{
using (var stream = new MemoryStream(File.ReadAllBytes(targetPath)) {Position = 0})
using (var source = PdfReader.Open(stream, PdfDocumentOpenMode.Import))
using (var document = new PdfDocument())
{
var options = document.Options;
options.FlateEncodeMode = PdfFlateEncodeMode.BestCompression;
options.UseFlateDecoderForJpegImages = PdfUseFlateDecoderForJpegImages.Automatic;
options.CompressContentStreams = true;
options.NoCompression = false;
foreach (var page in source.Pages)
{
document.AddPage(page);
}
document.Save(targetPath);
}
}
GhostScript は、PDFを圧縮できるAGPLライセンスソフトウェアです。 AGPLライセンスのC#ラッパーもgithubにあります こちら 。
そのラッパーからGhostscriptProcessor
クラスを使用して、カスタムコマンドをGhostScriptに渡すことができます。たとえば、PDF圧縮について説明している このAskUbuntu回答 にあるようなコマンドです。