{"id":55000083,"date":"2017-04-01T00:00:00","date_gmt":"2020-03-27T19:25:57","guid":{"rendered":"http:\/\/access-im-unternehmen.aix-dev.de\/aiu\/?p=83"},"modified":"-0001-11-30T00:00:00","modified_gmt":"-0001-11-30T00:00:00","slug":"PDFs_zusammenfuehren_mit_iTextSharp","status":"publish","type":"post","link":"https:\/\/vbentwickler.de\/PDFs_zusammenfuehren_mit_iTextSharp\/","title":{"rendered":"PDFs zusammenf&uuml;hren mit iTextSharp"},"content":{"rendered":"<p><b>Im Rahmen unserer L&ouml;sung zum Erstellen von DHL-Versandetiketten ben&ouml;tigen wir eine L&ouml;sung, mit der wir mehrere PDF-Dokumente zu einem zusammenf&uuml;hren k&ouml;nnen, um dieses dann in einem Rutsch auszudrucken. Mit Bordmitteln kommen wir nicht weiter, aber es gibt ja eine Reihe von Bibliotheken, die man sich etwa als NuGet-Paket ins Projekt holen kann. In diesem Fall nutzen wir die Bibliothek iTextSharp. Diese kann noch einiges mehr, aber wir wollen erst einmal nur PDF-Dokumente zusammenf&uuml;hren.<\/b><\/p>\n<h2>iTextSharp<\/h2>\n<p><b>iTextSharp <\/b>ist eine C#-Portierung des Projekts <b>iText 5<\/b>, f&uuml;r das Sie unter dem folgenden Link eine Reihe von Beispielen in der Programmiersprache Java finden: <b>http:\/\/developers.itextpdf.com\/examples-itext5<\/b>. Mit <b>iText 5 <\/b>k&ouml;nnen Sie eine ganze Menge Aufgaben rund um die Erstellung und Bearbeitung von PDF-Dokumenten erledigen. Aktuell wollen wir jedoch nur zwei oder mehrere PDF-Dokumente zusammenf&uuml;hren.<\/p>\n<h2>Beispielanwendung<\/h2>\n<p>Um die Bibliothek <b>iTextSharp <\/b>in ein Projekt zu integrieren, nutzen Sie den NuGet-Manager. Ausgehend von einem ge&ouml;ffneten Projekt klicken Sie dann mit der rechten Maustaste auf das Projekt im Projektmappen-Explorer. Aus dem Kontextmen&uuml; w&auml;hlen Sie dann den Eintrag <b>NuGet-Pakete verwalten &#8230; <\/b>aus. Im nun erscheinenden NuGet-Paket-Manager wechseln Sie zum Bereich <b>Durchsuchen<\/b> und geben als Suchbegriff <b>iTextSharp <\/b>ein. Ganz oben in der Liste erscheint nun der Eintrag <b>iTextSharp<\/b>, den Sie ausw&auml;hlen. Klicken Sie dann auf <b>Installieren<\/b>, um das Paket zum Projekt hinzuzuf&uuml;gen (siehe Bild 1).<\/p>\n<p class=\"image\"><img decoding=\"async\" src=\"..\/fileadmin\/_temp_\/2017_02\/pic_83_001.png\" alt=\"Installieren des NuGet-Pakets iTextSharp\" width=\"599,593\" height=\"444,7408\"\/><\/p>\n<p><b><span style=\"color:darkgrey;\">Bild 1: Installieren des NuGet-Pakets iTextSharp<\/span><\/b><\/p>\n<p>Unserem WPF-Beispielprojekt f&uuml;gen wir nun auf der Seite <b>MainWindow.xaml <\/b>eine einfache Schaltfl&auml;che hinzu, mit der wir einen ersten Test starten wollen.<\/p>\n<p>Wir gehen vereinfachend davon aus, dass wir einfach zwei Dokumente namens <b>1.pdf <\/b>und <b>2.pdf <\/b>zusammenf&uuml;hren wollen.<\/p>\n<p>Dazu f&uuml;gen wir diese zum Projekt hinzu und stellen in den Eigenschaften dieser beiden Elemente den Wert <b>Immer kopieren <\/b>f&uuml;r die Eigenschaft <b>In Ausgabeverzeichnis kopieren <\/b>ein. So k&ouml;nnen wir das Verzeichnis f&uuml;r diese beiden Dokumente gleich direkt &uuml;ber die Funktion <b>AppDomain.CurrentDomain.BaseDirectory <\/b>ermitteln (dies liefert das Verzeichnis, in dem sich auch die <b>.exe<\/b>-Datei der L&ouml;sung befindet).<\/p>\n<h2>Dokumente zusammenf&uuml;hren<\/h2>\n<p>Wir wollen nun eine Methode programmieren, welche diese beiden Dokumente zusammenf&uuml;hrt und als neues PDF-Dokument abspeichert. Das geht mit der <b>iTextSharp<\/b>-Bibliothek wirklich sehr einfach. F&uuml;r die Schaltfl&auml;che hinterlegen wir die folgende Methode, die zun&auml;chst drei Pfade in den Variablen <b>document1<\/b>, <b>document2 <\/b>und <b>target <\/b>hinterlegt &#8211; jeweils mit dem aktuellen Anwendungsverzeichnis und den Namen <b>1.pdf<\/b>, <b>2.pdf <\/b>und <b>12.pdf<\/b>:<\/p>\n<pre>private void btnTestZweiDokumente_Click(object sender, RoutedEventArgs e) {\r\n     string document1 = AppDomain.CurrentDomain.BaseDirectory + \"<\/font>1.pdf\";\r\n     string document2 = AppDomain.CurrentDomain.BaseDirectory + \"<\/font>2.pdf\";\r\n     string target = AppDomain.CurrentDomain.BaseDirectory + \"<\/font>12.pdf\";<\/pre>\n<p>Dann erstellt die Methode ein neues Objekt des Typs <b>Document<\/b> und eines vom Typ <b>FileStream<\/b>. Letzteres wird auf Basis des Pfades zur Zieldatei als neue Datei angelegt:<\/p>\n<pre>     Document document = new Document();\r\n     FileStream stream = new FileStream(target, FileMode.Create);<\/pre>\n<p>Das Objekt <b>pdf <\/b>mit dem Typ <b>PdfCopy <\/b>f&uuml;hrt das <b>Document<\/b>&#8211; und das <b>FileStream<\/b>-Objekt zusammen. Ein Objekt des Typs <b>Pdf-Reader<\/b>, das sp&auml;ter die Ausgangsdokumente aufnimmt, wird mit dem Wert <b>null <\/b>initialisiert. Dann wird das <b>Document<\/b>-Objekt mit der <b>open<\/b>-Methode ge&ouml;ffnet:<\/p>\n<pre>     PdfCopy pdf = new PdfCopy(document, stream);\r\n     PdfReader reader = null;\r\n     document.Open();<\/pre>\n<p>Nun folgen die beiden Einlesevorg&auml;nge der zusammenzuf&uuml;hrenden Dokumente. Dabei wird <b>reader <\/b>jeweils mit einem neuen <b>PdfReader<\/b>-Objekt mit dem Dokumentpfad als Konstruktor-Parameter initialisiert und f&uuml;r die Anwendung innerhalb des <b>using<\/b>-Konstrukts vorbereitet. Darin wird das Dokument aus der Objektvariablen <b>reader <\/b>zum <b>pdfCopy<\/b>-Objekt hinzugef&uuml;gt:<\/p>\n<pre>     using (reader = new PdfReader(document1)) {\r\n         pdf.AddDocument(reader);\r\n     }<\/pre>\n<p>Das erledigen wir auch noch f&uuml;r das zweite Dokument, also <b>2.pdf<\/b>:<\/p>\n<pre>     using (reader = new PdfReader(document2)) {\r\n         pdf.AddDocument(reader);\r\n     }<\/pre>\n<p>Schlie&szlig;lich schlie&szlig;t die Methode das Objekt <b>document <\/b>mit der <b>Close<\/b>-Methode:<\/p>\n<pre>     document.Close();\r\n}<\/pre>\n<p>Das Ergebnis &uuml;berzeugt: Beide Dokumente erscheinen im neuen Dokument <b>12.pdf<\/b>.<\/p>\n<h2>Anwendung bauen<\/h2>\n<p>Wenn wir nun schon so eine einfache M&ouml;glichkeit haben, PDF-Dokumente zusammenzustellen, wollen wir auch gleich eine praktische Anwendung daraus bauen. Diese soll es erm&ouml;glichen, &uuml;ber einen <b>Datei ausw&auml;hlen<\/b>-Dialog verschiedene PDF-Dokumente auszuw&auml;hlen und diese so einer Liste hinzuzuf&uuml;gen. Ein Mausklick soll die Dokumente dann unter einem ebenfalls per Dateidialog auszuw&auml;hlenden Dateinamen zusammenf&uuml;hren und speichern.<\/p>\n<p>Um dies zu realisieren, ben&ouml;tigen wir ein Listenfeld, das die Dateien anzeigt, sowie eine Schaltfl&auml;che zum Hinzuf&uuml;gen der gew&uuml;nschten Dateien. Au&szlig;erdem brauchen wir noch eine Schaltfl&auml;che, die den <b>Datei speichern<\/b>-Dialog anzeigt um nach der Eingabe eines entsprechenden Dateinamens die Dateien in der Reihenfolge wie im Listenfeld zusammenzuf&uuml;hren. Interessant w&auml;re es nat&uuml;rlich noch, die Dateien im Listenfeld nach oben oder unten verschieben zu k&ouml;nnen. Dies wollen wir jedoch hintenanstellen und uns zun&auml;chst um die grundlegenden Funktionen k&uuml;mmern.<\/p>\n<p>F&uuml;r diese L&ouml;sung verlassen wir das Beispielprojekt und erstellen ein neues WPF-Projekt namens <b>PDFMerger<\/b>. Diesem f&uuml;gen Sie nun zun&auml;chst wieder das NuGet-Paket <b>iTextSharp <\/b>hinzu. Dann legen wir die ben&ouml;tigten Steuer-elemente im Fenster <b>MainWindow.xaml <\/b>an. Der dazu verwendete Code sieht wie folgt aus. Der <b><Windows.Resources><\/b>-Teil legt zwei allgemeine Eigenschaften f&uuml;r die enthaltenen <b>Button<\/b>-Elemente fest:<\/p>\n<pre>&lt;Window x:Class=\"PDFMerger.MainWindow\" ... Title=\"MainWindow\" Height=\"350\" Width=\"525\"&gt;\r\n     &lt;Window.Resources&gt;\r\n         &lt;Style TargetType=\"{x:Type Button}\"&gt;\r\n             &lt;Setter Property=\"Margin\" Value=\"5\"&gt;&lt;\/Setter&gt;\r\n             &lt;Setter Property=\"Height\" Value=\"25\"&gt;&lt;\/Setter&gt;\r\n         &lt;\/Style&gt;\r\n     &lt;\/Window.Resources&gt;<\/pre>\n<div class=\"rcp_restricted\"><p><span style=\"color: #ff0000;\">M&ouml;chten Sie weiterlesen? Dann l&ouml;sen Sie Ihr Ticket!<\/span><br \/>\n<span style=\"color: #ff0000;\">Hier geht es zur Bestellung des Jahresabonnements des Magazins <strong>Visual Basic Entwickler<\/strong>:<\/span><br \/>\n<span style=\"color: #ff0000;\"><a style=\"color: #ff0000;\" href=\"https:\/\/shop.minhorst.com\/magazine\/363\/visual-basic-entwickler-jahresabonnement?c=77\">Zur Bestellung ...<\/a><\/span><br \/>\n<span style=\"color: #ff0000;\">Danach greifen Sie sofort auf <strong>alle rund 200 Artikel<\/strong> unseres Angebots zu - auch auf diesen hier!<\/span><br \/>\n<span style=\"color: #000000;\">Oder haben Sie bereits Zugangsdaten? Dann loggen Sie sich gleich hier ein:<\/span><\/p>\n<\/div>\n\n\t\n\t<form id=\"rcp_login_form\"  class=\"rcp_form\" method=\"POST\" action=\"https:\/\/vbentwickler.de\/data\/wp\/v2\/posts\/55000083\/\">\n\n\t\t\n\t\t<fieldset class=\"rcp_login_data\">\n\t\t\t<p>\n\t\t\t\t<label for=\"rcp_user_login\">Username or Email<\/label>\n\t\t\t\t<input name=\"rcp_user_login\" id=\"rcp_user_login\" class=\"required\" type=\"text\"\/>\n\t\t\t<\/p>\n\t\t\t<p>\n\t\t\t\t<label for=\"rcp_user_pass\">Password<\/label>\n\t\t\t\t<input name=\"rcp_user_pass\" id=\"rcp_user_pass\" class=\"required\" type=\"password\"\/>\n\t\t\t<\/p>\n\t\t\t\t\t\t<p>\n\t\t\t\t<input type=\"checkbox\" name=\"rcp_user_remember\" id=\"rcp_user_remember\" value=\"1\"\/>\n\t\t\t\t<label for=\"rcp_user_remember\">Remember me<\/label>\n\t\t\t<\/p>\n\t\t\t<p class=\"rcp_lost_password\"><a href=\"\/data\/wp\/v2\/posts\/55000083?rcp_action=lostpassword\"><\/a><\/p>\n\t\t\t<p>\n\t\t\t\t<input type=\"hidden\" name=\"rcp_action\" value=\"login\"\/>\n\t\t\t\t<input type=\"hidden\" name=\"rcp_redirect\" value=\"https:\/\/vbentwickler.de\/data\/wp\/v2\/posts\/55000083\/\"\/>\n\t\t\t\t<input type=\"hidden\" name=\"rcp_login_nonce\" value=\"1b1e1c5bfe\"\/>\n\t\t\t\t<input id=\"rcp_login_submit\" class=\"rcp-button\" type=\"submit\" value=\"Login\"\/>\n\t\t\t<\/p>\n\t\t\t\t\t<\/fieldset>\n\n\t\t\n\t<\/form>\n<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Im Rahmen unserer L&ouml;sung zum Erstellen von DHL-Versandetiketten ben&ouml;tigen wir eine L&ouml;sung, mit der wir mehrere PDF-Dokumente zu einem zusammenf&uuml;hren k&ouml;nnen, um dieses dann in einem Rutsch auszudrucken. Mit Bordmitteln kommen wir nicht weiter, aber es gibt ja eine Reihe von Bibliotheken, die man sich etwa als NuGet-Paket ins Projekt holen kann. In diesem Fall nutzen wir die Bibliothek iTextSharp. Diese kann noch einiges mehr, aber wir wollen erst einmal nur PDF-Dokumente zusammenf&uuml;hren.<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"om_disable_all_campaigns":false,"_monsterinsights_skip_tracking":false,"_monsterinsights_sitenote_active":false,"_monsterinsights_sitenote_note":"","_monsterinsights_sitenote_category":0,"_uf_show_specific_survey":0,"_uf_disable_surveys":false,"footnotes":""},"categories":[66022017,662017,44000029,44000009,44000004],"tags":[],"yst_prominent_words":[],"class_list":["post-55000083","post","type-post","status-publish","format-standard","hentry","category-66022017","category-662017","category-Access_programmieren","category-CProgrammiertechnik","category-Loesungen"],"aioseo_notices":[],"_links":{"self":[{"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/posts\/55000083","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/comments?post=55000083"}],"version-history":[{"count":0,"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/posts\/55000083\/revisions"}],"wp:attachment":[{"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/media?parent=55000083"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/categories?post=55000083"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/tags?post=55000083"},{"taxonomy":"yst_prominent_words","embeddable":true,"href":"https:\/\/vbentwickler.de\/data\/wp\/v2\/yst_prominent_words?post=55000083"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}