두 개 이상의 PDF 결합
배경 : 영업 직원을위한 주간 보고서 패키지를 제공해야합니다. 이 패키지에는 여러 (5-10) 개의 수정 보고서가 포함되어 있습니다.
문제점 : 사용자가 모든 보고서를 실행하고 단일 보고서 만 실행하도록 허용하고 싶습니다. 보고서를 만들고 다음을 수행하여이를 수행 할 수 있다고 생각했습니다.
List<ReportClass> reports = new List<ReportClass>();
reports.Add(new WeeklyReport1());
reports.Add(new WeeklyReport2());
reports.Add(new WeeklyReport3());
<snip>
foreach (ReportClass report in reports)
{
report.ExportToDisk(ExportFormatType.PortableDocFormat, @"c:\reports\" + report.ResourceName + ".pdf");
}
이렇게하면 보고서로 가득 찬 폴더가 제공되지만 모든 주간 보고서가 포함 된 단일 PDF를 모든 사람에게 이메일로 보내고 싶습니다. 그래서 그것들을 합쳐야합니다.
타사 컨트롤을 더 이상 설치하지 않고 쉽게 수행 할 수있는 방법이 있습니까? 이미 DevExpress 및 CrystalReports가 있으며 너무 많이 추가하고 싶지 않습니다.
foreach 루프 또는 개별 루프에서 결합하는 것이 가장 좋을까요? (또는 다른 방법)
비슷한 문제를 해결해야했고 결국 MIT 라이센스가 부여 된 PDFSharp 프로젝트를 사용하는 작은 pdfmerge 유틸리티를 만들었습니다 .
코드는 매우 간단합니다. cmdline 유틸리티가 필요했기 때문에 PDF 병합보다 인수를 구문 분석하는 데 더 많은 코드가 있습니다.
using (PdfDocument one = PdfReader.Open("file1.pdf", PdfDocumentOpenMode.Import))
using (PdfDocument two = PdfReader.Open("file2.pdf", PdfDocumentOpenMode.Import))
using (PdfDocument outPdf = new PdfDocument())
{
CopyPages(one, outPdf);
CopyPages(two, outPdf);
outPdf.Save("file1and2.pdf");
}
void CopyPages(PdfDocument from, PdfDocument to)
{
for (int i = 0; i < from.PageCount; i++)
{
to.AddPage(from.Pages[i]);
}
}
다음은 PDFSharp를 사용하여 X 양의 PDF를 병합하는 단일 함수입니다.
using PdfSharp;
using PdfSharp.Pdf;
using PdfSharp.Pdf.IO;
public static void MergePDFs(string targetPath, params string[] pdfs) {
using(PdfDocument targetDoc = new PdfDocument()){
foreach (string pdf in pdfs) {
using (PdfDocument pdfDoc = PdfReader.Open(pdf, PdfDocumentOpenMode.Import)) {
for (int i = 0; i < pdfDoc.PageCount; i++) {
targetDoc.AddPage(pdfDoc.Pages[i]);
}
}
}
targetDoc.Save(targetPath);
}
}
PDFsharp 는 여러 PDF 문서를 하나로 병합 할 수있는 것 같습니다.
ITextSharp 에서도 마찬가지입니다 .
이것은 제가 알아 낸 것이고 여러분과 나누고 싶었던 것입니다.
여기에서 여러 PDF를 하나로 결합 할 수 있습니다 (입력 목록 순서에 따라).
public static byte[] MergePdf(List<byte[]> pdfs)
{
List<PdfSharp.Pdf.PdfDocument> lstDocuments = new List<PdfSharp.Pdf.PdfDocument>();
foreach (var pdf in pdfs)
{
lstDocuments.Add(PdfReader.Open(new MemoryStream(pdf), PdfDocumentOpenMode.Import));
}
using (PdfSharp.Pdf.PdfDocument outPdf = new PdfSharp.Pdf.PdfDocument())
{
for(int i = 1; i<= lstDocuments.Count; i++)
{
foreach(PdfSharp.Pdf.PdfPage page in lstDocuments[i-1].Pages)
{
outPdf.AddPage(page);
}
}
MemoryStream stream = new MemoryStream();
outPdf.Save(stream, false);
byte[] bytes = stream.ToArray();
return bytes;
}
}
iTextsharp와 c #을 사용하여 pdf 파일을 결합했습니다. 이것이 제가 사용한 코드입니다.
string[] lstFiles=new string[3];
lstFiles[0]=@"C:/pdf/1.pdf";
lstFiles[1]=@"C:/pdf/2.pdf";
lstFiles[2]=@"C:/pdf/3.pdf";
PdfReader reader = null;
Document sourceDocument = null;
PdfCopy pdfCopyProvider = null;
PdfImportedPage importedPage;
string outputPdfPath=@"C:/pdf/new.pdf";
sourceDocument = new Document();
pdfCopyProvider = new PdfCopy(sourceDocument, new System.IO.FileStream(outputPdfPath, System.IO.FileMode.Create));
//Open the output file
sourceDocument.Open();
try
{
//Loop through the files list
for (int f = 0; f < lstFiles.Length-1; f++)
{
int pages =get_pageCcount(lstFiles[f]);
reader = new PdfReader(lstFiles[f]);
//Add pages of current file
for (int i = 1; i <= pages; i++)
{
importedPage = pdfCopyProvider.GetImportedPage(reader, i);
pdfCopyProvider.AddPage(importedPage);
}
reader.Close();
}
//At the end save the output file
sourceDocument.Close();
}
catch (Exception ex)
{
throw ex;
}
private int get_pageCcount(string file)
{
using (StreamReader sr = new StreamReader(File.OpenRead(file)))
{
Regex regex = new Regex(@"/Type\s*/Page[^s]");
MatchCollection matches = regex.Matches(sr.ReadToEnd());
return matches.Count;
}
}
이미 여기에 좋은 답변이 있지만 pdftk 가이 작업에 유용 할 수 있다고 언급 할 수 있다고 생각했습니다 . 하나의 PDF를 직접 생성하는 대신 필요한 각 PDF를 생성 한 다음 pdftk를 사용하여 포스트 프로세스로 함께 결합 할 수 있습니다. 이것은 system () 또는 ShellExecute () 호출을 사용하여 프로그램 내에서 수행 할 수도 있습니다.
다음은 PDFSharp 및 ConcatenateDocuments 를 사용하는 예제에 대한 링크입니다.
byte[]
iTextSharp를 사용하여 버전 5.x까지 두 가지 결합 :
internal static MemoryStream mergePdfs(byte[] pdf1, byte[] pdf2)
{
MemoryStream outStream = new MemoryStream();
using (Document document = new Document())
using (PdfCopy copy = new PdfCopy(document, outStream))
{
document.Open();
copy.AddDocument(new PdfReader(pdf1));
copy.AddDocument(new PdfReader(pdf2));
}
return outStream;
}
대신의 byte[]
'그것은 또한 통과하는 것이 가능이야 Stream
의'
나는 3 pdfbytes를 병합하고 1 바이트를 반환해야했기 때문에 위의 두 가지를 결합했습니다.
internal static byte[] mergePdfs(byte[] pdf1, byte[] pdf2,byte[] pdf3)
{
MemoryStream outStream = new MemoryStream();
using (Document document = new Document())
using (PdfCopy copy = new PdfCopy(document, outStream))
{
document.Open();
copy.AddDocument(new PdfReader(pdf1));
copy.AddDocument(new PdfReader(pdf2));
copy.AddDocument(new PdfReader(pdf3));
}
return outStream.ToArray();
}
다음은 iTextSharp를 사용하는 예입니다.
public static void MergePdf(Stream outputPdfStream, IEnumerable<string> pdfFilePaths)
{
using (var document = new Document())
using (var pdfCopy = new PdfCopy(document, outputPdfStream))
{
pdfCopy.CloseStream = false;
try
{
document.Open();
foreach (var pdfFilePath in pdfFilePaths)
{
using (var pdfReader = new PdfReader(pdfFilePath))
{
pdfCopy.AddDocument(pdfReader);
pdfReader.Close();
}
}
}
finally
{
document?.Close();
}
}
}
PdfReader 생성자에는 많은 오버로드가 있습니다. 이 매개 변수 유형을 대체하는 것이 가능 IEnumerable<string>
으로 IEnumerable<Stream>
그것은 잘 작동합니다. 이 메서드는 OutputStream을 닫지 않고 해당 작업을 Stream 생성자에게 위임합니다.
여기 솔루션 http://www.wacdesigns.com/2008/10/03/merge-pdf-files-using-c 무료 오픈 소스 iTextSharp 라이브러리를 사용합니다. http://sourceforge.net/projects/itextsharp
PDFBox로이 작업을 수행했습니다. iTextSharp와 유사하게 작동한다고 가정합니다.
pdf-shuffler gtk-apps.org를 사용해 볼 수 있습니다.
많은 사람들이 PDF Sharp를 추천 한 것을 알고 있지만 그 프로젝트가 2008 년 6 월 이후로 업데이트 된 것 같지 않습니다. 또한 소스를 사용할 수 없습니다.
개인적으로 저는 작업하기가 매우 쉬운 iTextSharp를 가지고 놀았습니다.
다음 메서드 는 PDF 배열 List
인 byte
배열을 가져 와서 byte
배열을 반환합니다 byte
.
using ...;
using PdfSharp.Pdf;
using PdfSharp.Pdf.IO;
public static class PdfHelper
{
public static byte[] PdfConcat(List<byte[]> lstPdfBytes)
{
byte[] res;
using (var outPdf = new PdfDocument())
{
foreach (var pdf in lstPdfBytes)
{
using (var pdfStream = new MemoryStream(pdf))
using (var pdfDoc = PdfReader.Open(pdfStream, PdfDocumentOpenMode.Import))
for (var i = 0; i < pdfDoc.PageCount; i++)
outPdf.AddPage(pdfDoc.Pages[i]);
}
using (var memoryStreamOut = new MemoryStream())
{
outPdf.Save(memoryStreamOut, false);
res = Stream2Bytes(memoryStreamOut);
}
}
return res;
}
public static void DownloadAsPdfFile(string fileName, byte[] content)
{
var ms = new MemoryStream(content);
HttpContext.Current.Response.Clear();
HttpContext.Current.Response.ContentType = "application/pdf";
HttpContext.Current.Response.AddHeader("content-disposition", $"attachment;filename={fileName}.pdf");
HttpContext.Current.Response.Buffer = true;
ms.WriteTo(HttpContext.Current.Response.OutputStream);
HttpContext.Current.Response.End();
}
private static byte[] Stream2Bytes(Stream input)
{
var buffer = new byte[input.Length];
using (var ms = new MemoryStream())
{
int read;
while ((read = input.Read(buffer, 0, buffer.Length)) > 0)
ms.Write(buffer, 0, read);
return ms.ToArray();
}
}
}
따라서 PdfHelper.PdfConcat
method 의 결과는 method에 전달됩니다 PdfHelper.DownloadAsPdfFile
.
추신 : NuGet
이름이 지정된 패키지 [PdfSharp][1]
를 설치해야합니다. 따라서 Package Manage Console
창 유형에서 :
설치 패키지 PdfSharp
다음 방법은 iTextSharp를 사용하여 두 개의 pdf (f1 및 f2)를 병합합니다. 두 번째 pdf는 f1의 특정 색인 뒤에 추가됩니다.
string f1 = "D:\\a.pdf";
string f2 = "D:\\Iso.pdf";
string outfile = "D:\\c.pdf";
appendPagesFromPdf(f1, f2, outfile, 3);
public static void appendPagesFromPdf(String f1,string f2, String destinationFile, int startingindex)
{
PdfReader p1 = new PdfReader(f1);
PdfReader p2 = new PdfReader(f2);
int l1 = p1.NumberOfPages, l2 = p2.NumberOfPages;
//Create our destination file
using (FileStream fs = new FileStream(destinationFile, FileMode.Create, FileAccess.Write, FileShare.None))
{
Document doc = new Document();
PdfWriter w = PdfWriter.GetInstance(doc, fs);
doc.Open();
for (int page = 1; page <= startingindex; page++)
{
doc.NewPage();
w.DirectContent.AddTemplate(w.GetImportedPage(p1, page), 0, 0);
//Used to pull individual pages from our source
}// copied pages from first pdf till startingIndex
for (int i = 1; i <= l2;i++)
{
doc.NewPage();
w.DirectContent.AddTemplate(w.GetImportedPage(p2, i), 0, 0);
}// merges second pdf after startingIndex
for (int i = startingindex+1; i <= l1;i++)
{
doc.NewPage();
w.DirectContent.AddTemplate(w.GetImportedPage(p1, i), 0, 0);
}// continuing from where we left in pdf1
doc.Close();
p1.Close();
p2.Close();
}
}
비슷한 문제를 해결하기 위해 다음과 같이 iTextSharp를 사용했습니다.
//Create the document which will contain the combined PDF's
Document document = new Document();
//Create a writer for de document
PdfCopy writer = new PdfCopy(document, new FileStream(OutPutFilePath, FileMode.Create));
if (writer == null)
{
return;
}
//Open the document
document.Open();
//Get the files you want to combine
string[] filePaths = Directory.GetFiles(DirectoryPathWhereYouHaveYourFiles);
foreach (string filePath in filePaths)
{
//Read the PDF file
using (PdfReader reader = new PdfReader(vls_FilePath))
{
//Add the file to the combined one
writer.AddDocument(reader);
}
}
//Finally close the document and writer
writer.Close();
document.Close();
참조 URL : https://stackoverflow.com/questions/808670/combine-two-or-more-pdfs
'programing' 카테고리의 다른 글
iOS 11에서 증가 된 탐색 표시 줄 제목 사용 (0) | 2021.01.17 |
---|---|
사용할 항목 : var 또는 개체 이름 유형? (0) | 2021.01.17 |
트랜잭션 내에서 "GO"사용 (0) | 2021.01.17 |
NSError는 어떻게 볼 수 있습니까? (0) | 2021.01.17 |
Android-표시된 모든 토스트 메시지 숨기기 (0) | 2021.01.17 |