PDF-bestanden maken in Java

1. Inleiding

In dit korte artikel zullen we ons concentreren op het maken van een volledig nieuw PDF-document op basis van de populaire iText- en PdfBox-bibliotheek.

2. Maven afhankelijkheden

Laten we eens kijken naar de Maven-afhankelijkheden, die in ons project moeten worden opgenomen:

 com.itextpdf itextpdf 5.5.10 org.apache.pdfbox pdfbox 2.0.4 

De laatste versie van de bibliotheken is hier te vinden: iText en PdfBox.

Een extra afhankelijkheid is nodig om toe te voegen, voor het geval ons bestand moet worden versleuteld. Het Bounty Castle Provider-pakket bevat implementaties van cryptografische algoritmen en is vereist voor beide bibliotheken:

 org.bouncycastle bcprov-jdk15on 1.56 

De nieuwste versie van de bibliotheek is hier te vinden: The Bounty Castle Provider.

3. Overzicht

Zowel de iText als de PdfBox zijn java-bibliotheken die worden gebruikt voor het maken / manipuleren van pdf-bestanden. Hoewel de uiteindelijke output van de bibliotheken hetzelfde is, werken ze op een iets andere manier. Laten we ze eens bekijken.

4. Maak een pdf in IText

4.1. Voeg tekst in pdf in

Laten we eens kijken hoe een nieuw bestand met “Hallo wereld” -tekst in pdf-bestand wordt ingevoegd

Document document = nieuw document (); PdfWriter.getInstance (document, nieuwe FileOutputStream ("iTextHelloWorld.pdf")); document.open (); Lettertype lettertype = FontFactory.getFont (FontFactory.COURIER, 16, BaseColor.BLACK); Chunk chunk = nieuwe Chunk ("Hallo wereld", lettertype); document.add (brok); document.close ();

Het maken van een pdf met behulp van de iText-bibliotheek is gebaseerd op het manipuleren van geïmplementeerde objecten Elementen interface in Document (in versie 5.5.10 zijn er 45 van die implementaties).

Het kleinste element dat aan het document kan worden toegevoegd en gebruikt, wordt genoemd Brok, wat in feite een tekenreeks is met toegepast lettertype.

Bovendien, Brok‘S kunnen worden gecombineerd met andere elementen zoals Paragrafen, Sectie etc. resulterend in mooie documenten.

4.2. Afbeelding invoegen

De iText-bibliotheek biedt een gemakkelijke manier om een ​​afbeelding aan het document toe te voegen. We hoeven alleen maar een Beeld instantie en voeg het toe aan het Document.

Padpad = Paths.get (ClassLoader.getSystemResource ("Java_logo.png"). ToURI ()); Document document = nieuw document (); PdfWriter.getInstance (document, nieuwe FileOutputStream ("iTextImageExample.pdf")); document.open (); Afbeelding img = Image.getInstance (path.toAbsolutePath (). ToString ()); document.add (img); document.close ();

4.3. Tafel invoegen

We kunnen een probleem tegenkomen wanneer we een tabel aan onze pdf willen toevoegen. Gelukkig biedt iText dergelijke functionaliteit kant-en-klaar.

Wat we eerst moeten doen, is een PdfTable object en in constructor bieden een aantal kolommen voor onze tabel. Nu kunnen we eenvoudig een nieuwe cel toevoegen door te bellen

Nu kunnen we eenvoudig een nieuwe cel toevoegen door de addCell methode op het nieuw gemaakte tabelobject. iText zal tabelrijen maken zolang alle benodigde cellen zijn gedefinieerd. Dit betekent dat als je eenmaal een tabel met 3 kolommen hebt gemaakt en er 8 cellen aan hebt toegevoegd, er slechts 2 rijen met elk 3 cellen worden weergegeven.

Laten we het voorbeeld eens bekijken:

Document document = nieuw document (); PdfWriter.getInstance (document, nieuwe FileOutputStream ("iTextTable.pdf")); document.open (); PdfPTable table = nieuwe PdfPTable (3); addTableHeader (tabel); addRows (tabel); addCustomRows (tabel); document.add (tabel); document.close ();

We maken een nieuwe tabel met 3 kolommen en 3 rijen. De eerste rij behandelen we als een tabelkop met een gewijzigde achtergrondkleur en randbreedte:

private void addTableHeader (PdfPTable-tabel) {Stream.of ("column header 1", "column header 2", "column header 3") .forEach (columnTitle -> {PdfPCell header = new PdfPCell (); header.setBackgroundColor (BaseColor .LIGHT_GRAY); header.setBorderWidth (2); header.setPhrase (nieuwe Phrase (columnTitle)); table.addCell (header);}); }

De tweede rij bestaat uit drie cellen met alleen tekst, geen extra opmaak.

private void addRows (PdfPTable-tabel) {table.addCell ("rij 1, kolom 1"); table.addCell ("rij 1, kolom 2"); table.addCell ("rij 1, kolom 3"); }

We kunnen niet alleen tekst in cellen opnemen, maar ook afbeeldingen. Bovendien kan elke cel afzonderlijk worden opgemaakt, in het onderstaande voorbeeld passen we horizontale en verticale uitlijningsaanpassingen toe:

private void addCustomRows (PdfPTable-tabel) gooit URISyntaxException, BadElementException, IOException {Path path = Paths.get (ClassLoader.getSystemResource ("Java_logo.png"). toURI ()); Afbeelding img = Image.getInstance (path.toAbsolutePath (). ToString ()); img.scalePercent (10); PdfPCell imageCell = nieuwe PdfPCell (img); table.addCell (imageCell); PdfPCell horizontalAlignCell = nieuwe PdfPCell (nieuwe zin ("rij 2, kolom 2")); horizontalAlignCell.setHorizontalAlignment (Element.ALIGN_CENTER); table.addCell (horizontalAlignCell); PdfPCell verticalAlignCell = nieuwe PdfPCell (nieuwe zin ("rij 2, kolom 3")); verticalAlignCell.setVerticalAlignment (Element.ALIGN_BOTTOM); table.addCell (verticalAlignCell); }

4.4. Bestandsversleuteling

Om toestemming toe te passen met de iText-bibliotheek, moeten we al een pdf-document hebben gemaakt. In ons voorbeeld gebruiken we onze iTextHelloWorld.pdf eerder gegenereerd bestand.

Zodra we het bestand hebben geladen met PDF lezer, we moeten een PdfStamper die wordt gebruikt om extra inhoud op bestanden toe te passen, zoals metadata, codering enz:

PdfReader pdfReader = nieuwe PdfReader ("HelloWorld.pdf"); PdfStamper pdfStamper = nieuwe PdfStamper (pdfReader, nieuwe FileOutputStream ("encryptedPdf.pdf")); pdfStamper.setEncryption ("userpass" .getBytes (), ".getBytes (), 0, PdfWriter.ENCRYPTION_AES_256); pdfStamper.close ();

In ons voorbeeld hebben we het bestand versleuteld met twee wachtwoorden. Het gebruikerswachtwoord (“userpass”) waarbij een gebruiker alleen het alleen-lezen recht heeft zonder de mogelijkheid om het af te drukken, en het eigenaarswachtwoord (“ownerpass”) dat wordt gebruikt als hoofdsleutel waardoor een persoon volledige toegang heeft tot pdf.

Als we de gebruiker toestemming willen geven om pdf af te drukken, in plaats van 0 (derde parameter van setEncryption) kunnen we slagen voor:

PdfWriter.ALLOW_PRINTING

Natuurlijk kunnen we verschillende toestemmingen combineren, zoals:

PdfWriter.ALLOW_PRINTING | PdfWriter.ALLOW_COPY

Houd er rekening mee dat als we iText gebruiken om toegangsrechten in te stellen, we ook een tijdelijke pdf maken die moet worden verwijderd en zo niet, dan zou deze volledig toegankelijk kunnen zijn voor iedereen.

5. Maak een pdf in PdfBox

5.1. Voeg tekst in pdf in

In tegenstelling tot de iText, de PdfBox bibliotheek biedt API die is gebaseerd op streammanipulatie. Er zijn geen klassen zoals Brok/Paragraaf enz. De PDDocument class is een Pdf-weergave in het geheugen waarbij de gebruiker gegevens schrijft door te manipuleren PDPageContentStream klasse.

Laten we het codevoorbeeld eens bekijken:

PDDocument-document = nieuw PDDocument (); PDPage-pagina = nieuwe PDPage (); document.addPage (pagina); PDPageContentStream contentStream = nieuwe PDPageContentStream (document, pagina); contentStream.setFont (PDType1Font.COURIER, 12); contentStream.beginText (); contentStream.showText ("Hallo wereld"); contentStream.endText (); contentStream.close (); document.save ("pdfBoxHelloWorld.pdf"); document.close ();

5.2. Afbeelding invoegen

Afbeeldingen invoegen is eenvoudig.

Eerst moeten we een bestand laden en een PDImageXObject, teken het vervolgens op het document (u moet de exacte x-, y-coördinaten opgeven).

Dat is alles:

PDDocument-document = nieuw PDDocument (); PDPage-pagina = nieuwe PDPage (); document.addPage (pagina); Padpad = Paths.get (ClassLoader.getSystemResource ("Java_logo.png"). ToURI ()); PDPageContentStream contentStream = nieuwe PDPageContentStream (document, pagina); PDImageXObject afbeelding = PDImageXObject.createFromFile (path.toAbsolutePath (). ToString (), document); contentStream.drawImage (afbeelding, 0, 0); contentStream.close (); document.save ("pdfBoxImage.pdf"); document.close (); 

5.3. Een tafel invoegen

Helaas, PdfBox biedt geen kant-en-klare methoden om tabellen aan te maken. Wat we in zo'n situatie kunnen doen, is het met de hand tekenen - teken letterlijk elke lijn totdat onze tekening lijkt op onze gedroomde tafel.

5.4. Bestandsversleuteling

PdfBox bibliotheek biedt de mogelijkheid om de bestandsrechten voor de gebruiker te coderen en aan te passen. Vergelijken met iText, het vereist niet om een ​​reeds bestaand bestand te gebruiken, zoals we gewoon gebruiken PDDocument. Pdf-bestandsrechten worden afgehandeld door Toegangsmachtiging class, waar we kunnen instellen of een gebruiker in staat zal zijn om inhoud te wijzigen, uit te pakken of een bestand af te drukken.

Vervolgens maken we een StandardProtectionPolicy object dat op een wachtwoord gebaseerde beveiliging aan het document toevoegt. We kunnen twee soorten wachtwoorden specificeren. Het gebruikerswachtwoord, waarna de persoon een bestand kan openen met toegepaste toegangsrechten en het eigenaarswachtwoord (geen beperkingen voor het bestand):

PDDocument-document = nieuw PDDocument (); PDPage-pagina = nieuwe PDPage (); document.addPage (pagina); AccessPermission accessPermission = nieuwe AccessPermission (); accessPermission.setCanPrint (false); accessPermission.setCanModify (false); StandardProtectionPolicy standardProtectionPolicy = nieuwe StandardProtectionPolicy ("ownerpass", "userpass", accessPermission); document.protect (standardProtectionPolicy); document.save ("pdfBoxEncryption.pdf"); document.close (); 

Ons voorbeeld presenteert een situatie dat als een gebruiker een gebruikerswachtwoord opgeeft, het bestand niet kan worden gewijzigd en afgedrukt.

6. Conclusies

In deze zelfstudie hebben we manieren besproken om een ​​pdf-bestand te maken in twee populaire Java-bibliotheken.

Volledige voorbeelden zijn te vinden in het op Maven gebaseerde project op GitHub.