Erfahren Sie mehr unter pdf-lib.js.org
pdf-lib
wurde erstellt, um den Mangel an robuster Unterstützung des JavaScript-Ökosystems für die PDF-Manipulation (insbesondere für die PDF- Änderung ) zu beheben.
Zwei der Unterscheidungsmerkmale von pdf-lib
sind:
Es sind weitere gute Open-Source-JavaScript-PDF-Bibliotheken verfügbar. Die meisten von ihnen können jedoch nur Dokumente erstellen , bestehende nicht ändern . Und viele von ihnen funktionieren nur in bestimmten Umgebungen.
Dieses Beispiel erzeugt dieses PDF.
Probieren Sie die JSFiddle-Demo aus
import { PDFDocument , StandardFonts , rgb } from 'pdf-lib'
// Create a new PDFDocument
const pdfDoc = await PDFDocument . create ( )
// Embed the Times Roman font
const timesRomanFont = await pdfDoc . embedFont ( StandardFonts . TimesRoman )
// Add a blank page to the document
const page = pdfDoc . addPage ( )
// Get the width and height of the page
const { width , height } = page . getSize ( )
// Draw a string of text toward the top of the page
const fontSize = 30
page . drawText ( 'Creating PDFs in JavaScript is awesome!' , {
x : 50 ,
y : height - 4 * fontSize ,
size : fontSize ,
font : timesRomanFont ,
color : rgb ( 0 , 0.53 , 0.71 ) ,
} )
// Serialize the PDFDocument to bytes (a Uint8Array)
const pdfBytes = await pdfDoc . save ( )
// For example, `pdfBytes` can be:
// • Written to a file in Node
// • Downloaded from the browser
// • Rendered in an <iframe>
In diesem Beispiel wird diese PDF-Datei erstellt (wenn diese PDF-Datei für die Variable existingPdfBytes
verwendet wird).
Probieren Sie die JSFiddle-Demo aus
import { degrees , PDFDocument , rgb , StandardFonts } from 'pdf-lib' ;
// This should be a Uint8Array or ArrayBuffer
// This data can be obtained in a number of different ways
// If your running in a Node environment, you could use fs.readFile()
// In the browser, you could make a fetch() call and use res.arrayBuffer()
const existingPdfBytes = ...
// Load a PDFDocument from the existing PDF bytes
const pdfDoc = await PDFDocument . load ( existingPdfBytes )
// Embed the Helvetica font
const helveticaFont = await pdfDoc . embedFont ( StandardFonts . Helvetica )
// Get the first page of the document
const pages = pdfDoc . getPages ( )
const firstPage = pages [ 0 ]
// Get the width and height of the first page
const { width , height } = firstPage . getSize ( )
// Draw a string of text diagonally across the first page
firstPage . drawText ( 'This text was added with JavaScript!' , {
x : 5 ,
y : height / 2 + 300 ,
size : 50 ,
font : helveticaFont ,
color : rgb ( 0.95 , 0.1 , 0.1 ) ,
rotate : degrees ( - 45 ) ,
} )
// Serialize the PDFDocument to bytes (a Uint8Array)
const pdfBytes = await pdfDoc . save ( )
// For example, `pdfBytes` can be:
// • Written to a file in Node
// • Downloaded from the browser
// • Rendered in an <iframe>
Dieses Beispiel erzeugt dieses PDF.
Probieren Sie die JSFiddle-Demo aus
Siehe auch Formulare erstellen und ausfüllen
import { PDFDocument } from 'pdf-lib'
// Create a new PDFDocument
const pdfDoc = await PDFDocument . create ( )
// Add a blank page to the document
const page = pdfDoc . addPage ( [ 550 , 750 ] )
// Get the form so we can add fields to it
const form = pdfDoc . getForm ( )
// Add the superhero text field and description
page . drawText ( 'Enter your favorite superhero:' , { x : 50 , y : 700 , size : 20 } )
const superheroField = form . createTextField ( 'favorite.superhero' )
superheroField . setText ( 'One Punch Man' )
superheroField . addToPage ( page , { x : 55 , y : 640 } )
// Add the rocket radio group, labels, and description
page . drawText ( 'Select your favorite rocket:' , { x : 50 , y : 600 , size : 20 } )
page . drawText ( 'Falcon Heavy' , { x : 120 , y : 560 , size : 18 } )
page . drawText ( 'Saturn IV' , { x : 120 , y : 500 , size : 18 } )
page . drawText ( 'Delta IV Heavy' , { x : 340 , y : 560 , size : 18 } )
page . drawText ( 'Space Launch System' , { x : 340 , y : 500 , size : 18 } )
const rocketField = form . createRadioGroup ( 'favorite.rocket' )
rocketField . addOptionToPage ( 'Falcon Heavy' , page , { x : 55 , y : 540 } )
rocketField . addOptionToPage ( 'Saturn IV' , page , { x : 55 , y : 480 } )
rocketField . addOptionToPage ( 'Delta IV Heavy' , page , { x : 275 , y : 540 } )
rocketField . addOptionToPage ( 'Space Launch System' , page , { x : 275 , y : 480 } )
rocketField . select ( 'Saturn IV' )
// Add the gundam check boxes, labels, and description
page . drawText ( 'Select your favorite gundams:' , { x : 50 , y : 440 , size : 20 } )
page . drawText ( 'Exia' , { x : 120 , y : 400 , size : 18 } )
page . drawText ( 'Kyrios' , { x : 120 , y : 340 , size : 18 } )
page . drawText ( 'Virtue' , { x : 340 , y : 400 , size : 18 } )
page . drawText ( 'Dynames' , { x : 340 , y : 340 , size : 18 } )
const exiaField = form . createCheckBox ( 'gundam.exia' )
const kyriosField = form . createCheckBox ( 'gundam.kyrios' )
const virtueField = form . createCheckBox ( 'gundam.virtue' )
const dynamesField = form . createCheckBox ( 'gundam.dynames' )
exiaField . addToPage ( page , { x : 55 , y : 380 } )
kyriosField . addToPage ( page , { x : 55 , y : 320 } )
virtueField . addToPage ( page , { x : 275 , y : 380 } )
dynamesField . addToPage ( page , { x : 275 , y : 320 } )
exiaField . check ( )
dynamesField . check ( )
// Add the planet dropdown and description
page . drawText ( 'Select your favorite planet*:' , { x : 50 , y : 280 , size : 20 } )
const planetsField = form . createDropdown ( 'favorite.planet' )
planetsField . addOptions ( [ 'Venus' , 'Earth' , 'Mars' , 'Pluto' ] )
planetsField . select ( 'Pluto' )
planetsField . addToPage ( page , { x : 55 , y : 220 } )
// Add the person option list and description
page . drawText ( 'Select your favorite person:' , { x : 50 , y : 180 , size : 18 } )
const personField = form . createOptionList ( 'favorite.person' )
personField . addOptions ( [
'Julius Caesar' ,
'Ada Lovelace' ,
'Cleopatra' ,
'Aaron Burr' ,
'Mark Antony' ,
] )
personField . select ( 'Ada Lovelace' )
personField . addToPage ( page , { x : 55 , y : 70 } )
// Just saying...
page . drawText ( `* Pluto should be a planet too!` , { x : 15 , y : 15 , size : 15 } )
// Serialize the PDFDocument to bytes (a Uint8Array)
const pdfBytes = await pdfDoc . save ( )
// For example, `pdfBytes` can be:
// • Written to a file in Node
// • Downloaded from the browser
// • Rendered in an <iframe>
In diesem Beispiel wird diese PDF-Datei erstellt (wenn diese PDF-Datei für die Variable formPdfBytes
verwendet wird, wird dieses Bild für die Variable marioImageBytes
und dieses Bild für die Variable emblemImageBytes
verwendet).
Probieren Sie die JSFiddle-Demo aus
Siehe auch Formulare erstellen und ausfüllen
import { PDFDocument } from 'pdf-lib'
// These should be Uint8Arrays or ArrayBuffers
// This data can be obtained in a number of different ways
// If your running in a Node environment, you could use fs.readFile()
// In the browser, you could make a fetch() call and use res.arrayBuffer()
const formPdfBytes = ...
const marioImageBytes = ...
const emblemImageBytes = ...
// Load a PDF with form fields
const pdfDoc = await PDFDocument . load ( formPdfBytes )
// Embed the Mario and emblem images
const marioImage = await pdfDoc . embedPng ( marioImageBytes )
const emblemImage = await pdfDoc . embedPng ( emblemImageBytes )
// Get the form containing all the fields
const form = pdfDoc . getForm ( )
// Get all fields in the PDF by their names
const nameField = form . getTextField ( 'CharacterName 2' )
const ageField = form . getTextField ( 'Age' )
const heightField = form . getTextField ( 'Height' )
const weightField = form . getTextField ( 'Weight' )
const eyesField = form . getTextField ( 'Eyes' )
const skinField = form . getTextField ( 'Skin' )
const hairField = form . getTextField ( 'Hair' )
const alliesField = form . getTextField ( 'Allies' )
const factionField = form . getTextField ( 'FactionName' )
const backstoryField = form . getTextField ( 'Backstory' )
const traitsField = form . getTextField ( 'Feat+Traits' )
const treasureField = form . getTextField ( 'Treasure' )
const characterImageField = form . getButton ( 'CHARACTER IMAGE' )
const factionImageField = form . getTextField ( 'Faction Symbol Image' )
// Fill in the basic info fields
nameField . setText ( 'Mario' )
ageField . setText ( '24 years' )
heightField . setText ( `5' 1"` )
weightField . setText ( '196 lbs' )
eyesField . setText ( 'blue' )
skinField . setText ( 'white' )
hairField . setText ( 'brown' )
// Fill the character image field with our Mario image
characterImageField . setImage ( marioImage )
// Fill in the allies field
alliesField . setText (
[
`Allies:` ,
` • Princess Daisy` ,
` • Princess Peach` ,
` • Rosalina` ,
` • Geno` ,
` • Luigi` ,
` • Donkey Kong` ,
` • Yoshi` ,
` • Diddy Kong` ,
`` ,
`Organizations:` ,
` • Italian Plumbers Association` ,
] . join ( 'n' ) ,
)
// Fill in the faction name field
factionField . setText ( `Mario's Emblem` )
// Fill the faction image field with our emblem image
factionImageField . setImage ( emblemImage )
// Fill in the backstory field
backstoryField . setText (
`Mario is a fictional character in the Mario video game franchise, owned by Nintendo and created by Japanese video game designer Shigeru Miyamoto. Serving as the company's mascot and the eponymous protagonist of the series, Mario has appeared in over 200 video games since his creation. Depicted as a short, pudgy, Italian plumber who resides in the Mushroom Kingdom, his adventures generally center upon rescuing Princess Peach from the Koopa villain Bowser. His younger brother and sidekick is Luigi.` ,
)
// Fill in the traits field
traitsField . setText (
[
`Mario can use three basic three power-ups:` ,
` • the Super Mushroom, which causes Mario to grow larger` ,
` • the Fire Flower, which allows Mario to throw fireballs` ,
` • the Starman, which gives Mario temporary invincibility` ,
] . join ( 'n' ) ,
)
// Fill in the treasure field
treasureField . setText ( [ '• Gold coins' , '• Treasure chests' ] . join ( 'n' ) )
// Serialize the PDFDocument to bytes (a Uint8Array)
const pdfBytes = await pdfDoc . save ( )
// For example, `pdfBytes` can be:
// • Written to a file in Node
// • Downloaded from the browser
// • Rendered in an <iframe>
In diesem Beispiel wird dieses PDF erstellt (wenn dieses PDF für die Variable formPdfBytes
verwendet wird).
Probieren Sie die JSFiddle-Demo aus
import { PDFDocument } from 'pdf-lib'
// This should be a Uint8Array or ArrayBuffer
// This data can be obtained in a number of different ways
// If your running in a Node environment, you could use fs.readFile()
// In the browser, you could make a fetch() call and use res.arrayBuffer()
const formPdfBytes = ...
// Load a PDF with form fields
const pdfDoc = await PDFDocument . load ( formPdfBytes )
// Get the form containing all the fields
const form = pdfDoc . getForm ( )
// Fill the form's fields
form . getTextField ( 'Text1' ) . setText ( 'Some Text' ) ;
form . getRadioGroup ( 'Group2' ) . select ( 'Choice1' ) ;
form . getRadioGroup ( 'Group3' ) . select ( 'Choice3' ) ;
form . getRadioGroup ( 'Group4' ) . select ( 'Choice1' ) ;
form . getCheckBox ( 'Check Box3' ) . check ( ) ;
form . getCheckBox ( 'Check Box4' ) . uncheck ( ) ;
form . getDropdown ( 'Dropdown7' ) . select ( 'Infinity' ) ;
form . getOptionList ( 'List Box6' ) . select ( 'Honda' ) ;
// Flatten the form's fields
form . flatten ( ) ;
// Serialize the PDFDocument to bytes (a Uint8Array)
const pdfBytes = await pdfDoc . save ( )
// For example, `pdfBytes` can be:
// • Written to a file in Node
// • Downloaded from the browser
// • Rendered in an <iframe>
In diesem Beispiel wird diese PDF-Datei erstellt (wenn diese PDF-Datei für die Variable „ firstDonorPdfBytes
“ und diese PDF-Datei für die Variable secondDonorPdfBytes
verwendet wird).
Probieren Sie die JSFiddle-Demo aus
import { PDFDocument } from 'pdf-lib'
// Create a new PDFDocument
const pdfDoc = await PDFDocument . create ( )
// These should be Uint8Arrays or ArrayBuffers
// This data can be obtained in a number of different ways
// If your running in a Node environment, you could use fs.readFile()
// In the browser, you could make a fetch() call and use res.arrayBuffer()
const firstDonorPdfBytes = ...
const secondDonorPdfBytes = ...
// Load a PDFDocument from each of the existing PDFs
const firstDonorPdfDoc = await PDFDocument . load ( firstDonorPdfBytes )
const secondDonorPdfDoc = await PDFDocument . load ( secondDonorPdfBytes )
// Copy the 1st page from the first donor document, and
// the 743rd page from the second donor document
const [ firstDonorPage ] = await pdfDoc . copyPages ( firstDonorPdfDoc , [ 0 ] )
const [ secondDonorPage ] = await pdfDoc . copyPages ( secondDonorPdfDoc , [ 742 ] )
// Add the first copied page
pdfDoc . addPage ( firstDonorPage )
// Insert the second copied page to index 0, so it will be the
// first page in `pdfDoc`
pdfDoc . insertPage ( 0 , secondDonorPage )
// Serialize the PDFDocument to bytes (a Uint8Array)
const pdfBytes = await pdfDoc . save ( )
// For example, `pdfBytes` can be:
// • Written to a file in Node
// • Downloaded from the browser
// • Rendered in an <iframe>
In diesem Beispiel wird diese PDF-Datei erstellt (wenn dieses Bild für die Variable jpgImageBytes
und dieses Bild für die Variable pngImageBytes
verwendet wird).
Probieren Sie die JSFiddle-Demo aus
import { PDFDocument } from 'pdf-lib'
// These should be Uint8Arrays or ArrayBuffers
// This data can be obtained in a number of different ways
// If your running in a Node environment, you could use fs.readFile()
// In the browser, you could make a fetch() call and use res.arrayBuffer()
const jpgImageBytes = ...
const pngImageBytes = ...
// Create a new PDFDocument
const pdfDoc = await PDFDocument . create ( )
// Embed the JPG image bytes and PNG image bytes
const jpgImage = await pdfDoc . embedJpg ( jpgImageBytes )
const pngImage = await pdfDoc . embedPng ( pngImageBytes )
// Get the width/height of the JPG image scaled down to 25% of its original size
const jpgDims = jpgImage . scale ( 0.25 )
// Get the width/height of the PNG image scaled down to 50% of its original size
const pngDims = pngImage . scale ( 0.5 )
// Add a blank page to the document
const page = pdfDoc . addPage ( )
// Draw the JPG image in the center of the page
page . drawImage ( jpgImage , {
x : page . getWidth ( ) / 2 - jpgDims . width / 2 ,
y : page . getHeight ( ) / 2 - jpgDims . height / 2 ,
width : jpgDims . width ,
height : jpgDims . height ,
} )
// Draw the PNG image near the lower right corner of the JPG image
page . drawImage ( pngImage , {
x : page . getWidth ( ) / 2 - pngDims . width / 2 + 75 ,
y : page . getHeight ( ) / 2 - pngDims . height ,
width : pngDims . width ,
height : pngDims . height ,
} )
// Serialize the PDFDocument to bytes (a Uint8Array)
const pdfBytes = await pdfDoc . save ( )
// For example, `pdfBytes` can be:
// • Written to a file in Node
// • Downloaded from the browser
// • Rendered in an <iframe>
In diesem Beispiel wird dieses PDF erstellt (wenn dieses PDF für die Variable americanFlagPdfBytes
und dieses PDF für die Variable usConstitutionPdfBytes
verwendet wird).
Probieren Sie die JSFiddle-Demo aus
import { PDFDocument } from 'pdf-lib'
// These should be Uint8Arrays or ArrayBuffers
// This data can be obtained in a number of different ways
// If your running in a Node environment, you could use fs.readFile()
// In the browser, you could make a fetch() call and use res.arrayBuffer()
const americanFlagPdfBytes = ...
const usConstitutionPdfBytes = ...
// Create a new PDFDocument
const pdfDoc = await PDFDocument . create ( )
// Embed the American flag PDF bytes
const [ americanFlag ] = await pdfDoc . embedPdf ( americanFlagPdfBytes )
// Load the U.S. constitution PDF bytes
const usConstitutionPdf = await PDFDocument . load ( usConstitutionPdfBytes )
// Embed the second page of the constitution and clip the preamble
const preamble = await pdfDoc . embedPage ( usConstitutionPdf . getPages ( ) [ 1 ] , {
left : 55 ,
bottom : 485 ,
right : 300 ,
top : 575 ,
} )
// Get the width/height of the American flag PDF scaled down to 30% of
// its original size
const americanFlagDims = americanFlag . scale ( 0.3 )
// Get the width/height of the preamble clipping scaled up to 225% of
// its original size
const preambleDims = preamble . scale ( 2.25 )
// Add a blank page to the document
const page = pdfDoc . addPage ( )
// Draw the American flag image in the center top of the page
page . drawPage ( americanFlag , {
... americanFlagDims ,
x : page . getWidth ( ) / 2 - americanFlagDims . width / 2 ,
y : page . getHeight ( ) - americanFlagDims . height - 150 ,
} )
// Draw the preamble clipping in the center bottom of the page
page . drawPage ( preamble , {
... preambleDims ,
x : page . getWidth ( ) / 2 - preambleDims . width / 2 ,
y : page . getHeight ( ) / 2 - preambleDims . height / 2 - 50 ,
} )
// Serialize the PDFDocument to bytes (a Uint8Array)
const pdfBytes = await pdfDoc . save ( )
// For example, `pdfBytes` can be:
// • Written to a file in Node
// • Downloaded from the browser
// • Rendered in an <iframe>
pdf-lib
stützt sich auf ein Schwestermodul, um das Einbetten benutzerdefinierter Schriftarten zu unterstützen: @pdf-lib/fontkit
. Sie müssen das Modul @pdf-lib/fontkit
zu Ihrem Projekt hinzufügen und es mit pdfDoc.registerFontkit(...)
registrieren, bevor Sie benutzerdefinierte Schriftarten einbetten.
Detaillierte Installationsanweisungen zur Installation
@pdf-lib/fontkit
als UMD- oder NPM-Modul finden Sie weiter unten.
In diesem Beispiel wird diese PDF-Datei erstellt (wenn diese Schriftart für die Variable fontBytes
verwendet wird).
Probieren Sie die JSFiddle-Demo aus
import { PDFDocument , rgb } from 'pdf-lib'
import fontkit from '@pdf-lib/fontkit'
// This should be a Uint8Array or ArrayBuffer
// This data can be obtained in a number of different ways
// If you're running in a Node environment, you could use fs.readFile()
// In the browser, you could make a fetch() call and use res.arrayBuffer()
const fontBytes = ...
// Create a new PDFDocument
const pdfDoc = await PDFDocument . create ( )
// Register the `fontkit` instance
pdfDoc . registerFontkit ( fontkit )
// Embed our custom font in the document
const customFont = await pdfDoc . embedFont ( fontBytes )
// Add a blank page to the document
const page = pdfDoc . addPage ( )
// Create a string of text and measure its width and height in our custom font
const text = 'This is text in an embedded font!'
const textSize = 35
const textWidth = customFont . widthOfTextAtSize ( text , textSize )
const textHeight = customFont . heightAtSize ( textSize )
// Draw the string of text on the page
page . drawText ( text , {
x : 40 ,
y : 450 ,
size : textSize ,
font : customFont ,
color : rgb ( 0 , 0.53 , 0.71 ) ,
} )
// Draw a box around the string of text
page . drawRectangle ( {
x : 40 ,
y : 450 ,
width : textWidth ,
height : textHeight ,
borderColor : rgb ( 1 , 0 , 0 ) ,
borderWidth : 1.5 ,
} )
// Serialize the PDFDocument to bytes (a Uint8Array)
const pdfBytes = await pdfDoc . save ( )
// For example, `pdfBytes` can be:
// • Written to a file in Node
// • Downloaded from the browser
// • Rendered in an <iframe>
In diesem Beispiel wird dieses PDF erstellt (wenn dieses Bild für die Variable jpgAttachmentBytes
und dieses PDF für die Variable pdfAttachmentBytes
verwendet wird).
Probieren Sie die JSFiddle-Demo aus
import { PDFDocument } from 'pdf-lib'
// These should be Uint8Arrays or ArrayBuffers
// This data can be obtained in a number of different ways
// If your running in a Node environment, you could use fs.readFile()
// In the browser, you could make a fetch() call and use res.arrayBuffer()
const jpgAttachmentBytes = ...
const pdfAttachmentBytes = ...
// Create a new PDFDocument
const pdfDoc = await PDFDocument . create ( )
// Add the JPG attachment
await pdfDoc . attach ( jpgAttachmentBytes , 'cat_riding_unicorn.jpg' , {
mimeType : 'image/jpeg' ,
description : 'Cool cat riding a unicorn! ???️' ,
creationDate : new Date ( '2019/12/01' ) ,
modificationDate : new Date ( '2020/04/19' ) ,
} )
// Add the PDF attachment
await pdfDoc . attach ( pdfAttachmentBytes , 'us_constitution.pdf' , {
mimeType : 'application/pdf' ,
description : 'Constitution of the United States ???' ,
creationDate : new Date ( '1787/09/17' ) ,
modificationDate : new Date ( '1992/05/07' ) ,
} )
// Add a page with some text
const page = pdfDoc . addPage ( ) ;
page . drawText ( 'This PDF has two attachments' , { x : 135 , y : 415 } )
// Serialize the PDFDocument to bytes (a Uint8Array)
const pdfBytes = await pdfDoc . save ( )
// For example, `pdfBytes` can be:
// • Written to a file in Node
// • Downloaded from the browser
// • Rendered in an <iframe>
Dieses Beispiel erzeugt dieses PDF .
Probieren Sie die JSFiddle-Demo aus
import { PDFDocument , StandardFonts } from 'pdf-lib'
// Create a new PDFDocument
const pdfDoc = await PDFDocument . create ( )
// Embed the Times Roman font
const timesRomanFont = await pdfDoc . embedFont ( StandardFonts . TimesRoman )
// Add a page and draw some text on it
const page = pdfDoc . addPage ( [ 500 , 600 ] )
page . setFont ( timesRomanFont )
page . drawText ( 'The Life of an Egg' , { x : 60 , y : 500 , size : 50 } )
page . drawText ( 'An Epic Tale of Woe' , { x : 125 , y : 460 , size : 25 } )
// Set all available metadata fields on the PDFDocument. Note that these fields
// are visible in the "Document Properties" section of most PDF readers.
pdfDoc . setTitle ( '? The Life of an Egg ?' )
pdfDoc . setAuthor ( 'Humpty Dumpty' )
pdfDoc . setSubject ( ' An Epic Tale of Woe ' )
pdfDoc . setKeywords ( [ 'eggs' , 'wall' , 'fall' , 'king' , 'horses' , 'men' ] )
pdfDoc . setProducer ( 'PDF App 9000 ?' )
pdfDoc . setCreator ( 'pdf-lib (https://github.com/Hopding/pdf-lib)' )
pdfDoc . setCreationDate ( new Date ( '2018-06-24T01:58:37.228Z' ) )
pdfDoc . setModificationDate ( new Date ( '2019-12-21T07:00:11.000Z' ) )
// Serialize the PDFDocument to bytes (a Uint8Array)
const pdfBytes = await pdfDoc . save ( )
// For example, `pdfBytes` can be:
// • Written to a file in Node
// • Downloaded from the browser
// • Rendered in an <iframe>
Probieren Sie die JSFiddle-Demo aus
import { PDFDocument } from 'pdf-lib'
// This should be a Uint8Array or ArrayBuffer
// This data can be obtained in a number of different ways
// If your running in a Node environment, you could use fs.readFile()
// In the browser, you could make a fetch() call and use res.arrayBuffer()
const existingPdfBytes = ...
// Load a PDFDocument without updating its existing metadata
const pdfDoc = await PDFDocument . load ( existingPdfBytes , {
updateMetadata : false
} )
// Print all available metadata fields
console . log ( 'Title:' , pdfDoc . getTitle ( ) )
console . log ( 'Author:' , pdfDoc . getAuthor ( ) )
console . log ( 'Subject:' , pdfDoc . getSubject ( ) )
console . log ( 'Creator:' , pdfDoc . getCreator ( ) )
console . log ( 'Keywords:' , pdfDoc . getKeywords ( ) )
console . log ( 'Producer:' , pdfDoc . getProducer ( ) )
console . log ( 'Creation Date:' , pdfDoc . getCreationDate ( ) )
console . log ( 'Modification Date:' , pdfDoc . getModificationDate ( ) )
Dieses Skript gibt Folgendes aus ( wenn diese PDF-Datei für die Variable existingPdfBytes
verwendet wird ):
Title: Microsoft Word - Basic Curriculum Vitae example.doc
Author: Administrator
Subject: undefined
Creator: PScript5.dll Version 5.2
Keywords: undefined
Producer: Acrobat Distiller 8.1.0 (Windows)
Creation Date: 2010-07-29T14:26:00.000Z
Modification Date: 2010-07-29T14:26:00.000Z
import {
PDFDocument ,
StandardFonts ,
NonFullScreenPageMode ,
ReadingDirection ,
PrintScaling ,
Duplex ,
PDFName ,
} from 'pdf-lib'
// Create a new PDFDocument
const pdfDoc = await PDFDocument . create ( )
// Embed the Times Roman font
const timesRomanFont = await pdfDoc . embedFont ( StandardFonts . TimesRoman )
// Add a page and draw some text on it
const page = pdfDoc . addPage ( [ 500 , 600 ] )
page . setFont ( timesRomanFont )
page . drawText ( 'The Life of an Egg' , { x : 60 , y : 500 , size : 50 } )
page . drawText ( 'An Epic Tale of Woe' , { x : 125 , y : 460 , size : 25 } )
// Set all available viewer preferences on the PDFDocument:
const viewerPrefs = pdfDoc . catalog . getOrCreateViewerPreferences ( )
viewerPrefs . setHideToolbar ( true )
viewerPrefs . setHideMenubar ( true )
viewerPrefs . setHideWindowUI ( true )
viewerPrefs . setFitWindow ( true )
viewerPrefs . setCenterWindow ( true )
viewerPrefs . setDisplayDocTitle ( true )
// Set the PageMode (otherwise setting NonFullScreenPageMode has no meaning)
pdfDoc . catalog . set ( PDFName . of ( 'PageMode' ) , PDFName . of ( 'FullScreen' ) )
// Set what happens when fullScreen is closed
viewerPrefs . setNonFullScreenPageMode ( NonFullScreenPageMode . UseOutlines )
viewerPrefs . setReadingDirection ( ReadingDirection . L2R )
viewerPrefs . setPrintScaling ( PrintScaling . None )
viewerPrefs . setDuplex ( Duplex . DuplexFlipLongEdge )
viewerPrefs . setPickTrayByPDFSize ( true )
// We can set the default print range to only the first page
viewerPrefs . setPrintPageRange ( { start : 0 , end : 0 } )
// Or we can supply noncontiguous ranges (e.g. pages 1, 3, and 5-7)
viewerPrefs . setPrintPageRange ( [
{ start : 0 , end : 0 } ,
{ start : 2 , end : 2 } ,
{ start : 4 , end : 6 } ,
] )
viewerPrefs . setNumCopies ( 2 )
// Serialize the PDFDocument to bytes (a Uint8Array)
const pdfBytes = await pdfDoc . save ( )
// For example, `pdfBytes` can be:
// • Written to a file in Node
// • Downloaded from the browser
// • Rendered in an <iframe>
import { PDFDocument } from 'pdf-lib'
// This should be a Uint8Array or ArrayBuffer
// This data can be obtained in a number of different ways
// If your running in a Node environment, you could use fs.readFile()
// In the browser, you could make a fetch() call and use res.arrayBuffer()
const existingPdfBytes = ...
// Load a PDFDocument without updating its existing metadata
const pdfDoc = await PDFDocument . load ( existingPdfBytes )
const viewerPrefs = pdfDoc . catalog . getOrCreateViewerPreferences ( )
// Print all available viewer preference fields
console . log ( 'HideToolbar:' , viewerPrefs . getHideToolbar ( ) )
console . log ( 'HideMenubar:' , viewerPrefs . getHideMenubar ( ) )
console . log ( 'HideWindowUI:' , viewerPrefs . getHideWindowUI ( ) )
console . log ( 'FitWindow:' , viewerPrefs . getFitWindow ( ) )
console . log ( 'CenterWindow:' , viewerPrefs . getCenterWindow ( ) )
console . log ( 'DisplayDocTitle:' , viewerPrefs . getDisplayDocTitle ( ) )
console . log ( 'NonFullScreenPageMode:' , viewerPrefs . getNonFullScreenPageMode ( ) )
console . log ( 'ReadingDirection:' , viewerPrefs . getReadingDirection ( ) )
console . log ( 'PrintScaling:' , viewerPrefs . getPrintScaling ( ) )
console . log ( 'Duplex:' , viewerPrefs . getDuplex ( ) )
console . log ( 'PickTrayByPDFSize:' , viewerPrefs . getPickTrayByPDFSize ( ) )
console . log ( 'PrintPageRange:' , viewerPrefs . getPrintPageRange ( ) )
console . log ( 'NumCopies:' , viewerPrefs . getNumCopies ( ) )
Dieses Skript gibt Folgendes aus ( wenn dieses PDF für die Variable existingPdfBytes
verwendet wird ):
HideToolbar: true
HideMenubar: true
HideWindowUI: false
FitWindow: true
CenterWindow: true
DisplayDocTitle: true
NonFullScreenPageMode: UseNone
ReadingDirection: R2L
PrintScaling: None
Duplex: DuplexFlipLongEdge
PickTrayByPDFSize: true
PrintPageRange: [ { start: 1, end: 1 }, { start: 3, end: 4 } ]
NumCopies: 2
Dieses Beispiel erzeugt dieses PDF .
Probieren Sie die JSFiddle-Demo aus
import { PDFDocument , rgb } from 'pdf-lib'
// SVG path for a wavy line
const svgPath =
'M 0,20 L 100,160 Q 130,200 150,120 C 190,-40 200,200 300,150 L 400,90'
// Create a new PDFDocument
const pdfDoc = await PDFDocument . create ( )
// Add a blank page to the document
const page = pdfDoc . addPage ( )
page . moveTo ( 100 , page . getHeight ( ) - 5 )
// Draw the SVG path as a black line
page . moveDown ( 25 )
page . drawSvgPath ( svgPath )
// Draw the SVG path as a thick green line
page . moveDown ( 200 )
page . drawSvgPath ( svgPath , { borderColor : rgb ( 0 , 1 , 0 ) , borderWidth : 5 } )
// Draw the SVG path and fill it with red
page . moveDown ( 200 )
page . drawSvgPath ( svgPath , { color : rgb ( 1 , 0 , 0 ) } )
// Draw the SVG path at 50% of its original size
page . moveDown ( 200 )
page . drawSvgPath ( svgPath , { scale : 0.5 } )
// Serialize the PDFDocument to bytes (a Uint8Array)
const pdfBytes = await pdfDoc . save ( )
// For example, `pdfBytes` can be:
// • Written to a file in Node
// • Downloaded from the browser
// • Rendered in an <iframe>
pdf-lib
unterstützt die aufregende neue Deno-Laufzeit vollständig! Alle Anwendungsbeispiele funktionieren in Deno. Sie müssen lediglich die Importe für pdf-lib
und @pdf-lib/fontkit
ändern, um das Skypack-CDN zu verwenden, da Deno erfordert, dass alle Module über URLs referenziert werden.
Siehe auch So erstellen und ändern Sie PDF-Dateien in Deno mit pdf-lib
Unten finden Sie das für Deno geänderte Beispiel zum Erstellen eines Dokuments :
import {
PDFDocument ,
StandardFonts ,
rgb ,
} from 'https://cdn.skypack.dev/pdf-lib@^1.11.1?dts' ;
const pdfDoc = await PDFDocument . create ( ) ;
const timesRomanFont = await pdfDoc . embedFont ( StandardFonts . TimesRoman ) ;
const page = pdfDoc . addPage ( ) ;
const { width , height } = page . getSize ( ) ;
const fontSize = 30 ;
page . drawText ( 'Creating PDFs in JavaScript is awesome!' , {
x : 50 ,
y : height - 4 * fontSize ,
size : fontSize ,
font : timesRomanFont ,
color : rgb ( 0 , 0.53 , 0.71 ) ,
} ) ;
const pdfBytes = await pdfDoc . save ( ) ;
await Deno . writeFile ( 'out.pdf' , pdfBytes ) ;
Wenn Sie dieses Skript als create-document.ts
speichern, können Sie es mit Deno mit dem folgenden Befehl ausführen:
deno run --allow-write create-document.ts
Die resultierende out.pdf
Datei sieht wie dieses PDF aus.
Hier ist ein etwas komplizierteres Beispiel, das zeigt, wie man in Deno eine Schriftart einbettet und Text misst:
import {
degrees ,
PDFDocument ,
rgb ,
StandardFonts ,
} from 'https://cdn.skypack.dev/pdf-lib@^1.11.1?dts' ;
import fontkit from 'https://cdn.skypack.dev/@pdf-lib/fontkit@^1.0.0?dts' ;
const url = 'https://pdf-lib.js.org/assets/ubuntu/Ubuntu-R.ttf' ;
const fontBytes = await fetch ( url ) . then ( ( res ) => res . arrayBuffer ( ) ) ;
const pdfDoc = await PDFDocument . create ( ) ;
pdfDoc . registerFontkit ( fontkit ) ;
const customFont = await pdfDoc . embedFont ( fontBytes ) ;
const page = pdfDoc . addPage ( ) ;
const text = 'This is text in an embedded font!' ;
const textSize = 35 ;
const textWidth = customFont . widthOfTextAtSize ( text , textSize ) ;
const textHeight = customFont . heightAtSize ( textSize ) ;
page . drawText ( text , {
x : 40 ,
y : 450 ,
size : textSize ,
font : customFont ,
color : rgb ( 0 , 0.53 , 0.71 ) ,
} ) ;
page . drawRectangle ( {
x : 40 ,
y : 450 ,
width : textWidth ,
height : textHeight ,
borderColor : rgb ( 1 , 0 , 0 ) ,
borderWidth : 1.5 ,
} ) ;
const pdfBytes = await pdfDoc . save ( ) ;
await Deno . writeFile ( 'out.pdf' , pdfBytes ) ;
Wenn Sie dieses Skript als custom-font.ts
speichern, können Sie es mit dem folgenden Befehl ausführen:
deno run --allow-write --allow-net custom-font.ts
Die resultierende out.pdf
Datei sieht wie dieses PDF aus.
Die Anwendungsbeispiele stellen kurzen und prägnanten Code bereit, der die verschiedenen Funktionen von pdf-lib
demonstriert. Vollständige Arbeitsbeispiele finden Sie im Verzeichnis apps/
. Diese Apps werden verwendet, um vor jeder Veröffentlichung manuelle Tests von pdf-lib
durchzuführen (zusätzlich zu den automatisierten Tests).
Derzeit gibt es vier Apps:
node
– enthält Tests für pdf-lib
in Node-Umgebungen. Diese Tests sind eine praktische Referenz, wenn Sie versuchen, PDFs, Schriftarten oder Bilder mit pdf-lib
aus dem Dateisystem zu speichern/zu laden. Sie ermöglichen Ihnen außerdem, Ihre PDFs schnell in verschiedenen Viewern (Acrobat, Preview, Foxit, Chrome, Firefox usw.) zu öffnen, um die Kompatibilität sicherzustellen.web
– enthält Tests für pdf-lib
in Browserumgebungen. Diese Tests sind eine praktische Referenz, wenn Sie versuchen, PDFs, Schriftarten oder Bilder mit pdf-lib
in einer Browserumgebung zu speichern/laden.rn
– enthält Tests für pdf-lib
in React Native-Umgebungen. Diese Tests sind eine praktische Referenz, wenn Sie versuchen, PDFs, Schriftarten oder Bilder mit pdf-lib
in einer React Native-Umgebung zu speichern/laden.deno
– enthält Tests für pdf-lib
in Deno-Umgebungen. Diese Tests sind eine praktische Referenz, wenn Sie versuchen, PDFs, Schriftarten oder Bilder mit pdf-lib
aus dem Dateisystem zu speichern/zu laden. So installieren Sie die neueste stabile Version:
# With npm
npm install --save pdf-lib
# With yarn
yarn add pdf-lib
Dies setzt voraus, dass Sie npm oder Yarn als Paketmanager verwenden.
Sie können pdf-lib
auch als UMD-Modul von unpkg oder jsDelivr herunterladen. Die UMD-Builds wurden auf ES5 kompiliert, sodass sie in jedem modernen Browser funktionieren sollten. UMD-Builds sind nützlich, wenn Sie keinen Paketmanager oder Modul-Bundler verwenden. Sie können sie beispielsweise direkt im <script>
-Tag einer HTML-Seite verwenden.
Folgende Builds sind verfügbar:
HINWEIS: Wenn Sie die CDN-Skripte in der Produktion verwenden, sollten Sie eine bestimmte Versionsnummer in die URL einfügen, zum Beispiel:
- https://unpkg.com/[email protected]/dist/pdf-lib.min.js
- https://cdn.jsdelivr.net/npm/[email protected]/dist/pdf-lib.min.js
Wenn Sie einen UMD-Build verwenden, haben Sie Zugriff auf eine globale window.PDFLib
Variable. Diese Variable enthält alle von pdf-lib
exportierten Klassen und Funktionen. Zum Beispiel:
// NPM module
import { PDFDocument , rgb } from 'pdf-lib' ;
// UMD module
var PDFDocument = PDFLib . PDFDocument ;
var rgb = PDFLib . rgb ;
pdf-lib
stützt sich auf ein Schwestermodul, um das Einbetten benutzerdefinierter Schriftarten zu unterstützen: @pdf-lib/fontkit
. Sie müssen das Modul @pdf-lib/fontkit
zu Ihrem Projekt hinzufügen und es mit pdfDoc.registerFontkit(...)
registrieren, bevor Sie benutzerdefinierte Schriftarten einbetten (siehe Beispiel zum Einbetten von Schriftarten). Dieses Modul ist nicht standardmäßig enthalten, da es nicht von allen Benutzern benötigt wird, und es erhöht die Paketgröße.
Die Installation dieses Moduls ist einfach. Genau wie pdf-lib
selbst kann @pdf-lib/fontkit
mit npm
/ yarn
oder als UMD-Modul installiert werden.
# With npm
npm install --save @pdf-lib/fontkit
# With yarn
yarn add @pdf-lib/fontkit
So registrieren Sie die fontkit
Instanz:
import { PDFDocument } from 'pdf-lib'
import fontkit from '@pdf-lib/fontkit'
const pdfDoc = await PDFDocument . create ( )
pdfDoc . registerFontkit ( fontkit )
Folgende Builds sind verfügbar:
HINWEIS: Wenn Sie die CDN-Skripte in der Produktion verwenden, sollten Sie eine bestimmte Versionsnummer in die URL einfügen, zum Beispiel:
- https://unpkg.com/@pdf-lib/[email protected]/dist/fontkit.umd.min.js
- https://cdn.jsdelivr.net/npm/@pdf-lib/[email protected]/dist/fontkit.umd.min.js
Wenn Sie einen UMD-Build verwenden, haben Sie Zugriff auf eine globale window.fontkit
Variable. So registrieren Sie die fontkit
Instanz:
var pdfDoc = await PDFLib . PDFDocument . create ( )
pdfDoc . registerFontkit ( fontkit )
Die API-Dokumentation ist auf der Projektseite unter https://pdf-lib.js.org/docs/api/ verfügbar.
Das Repo für die Projektseite (und die generierten Dokumentationsdateien) befindet sich hier: https://github.com/Hopding/pdf-lib-docs.
Bei der Arbeit mit PDFs stößt man häufig auf die Begriffe „Zeichenkodierung“ und „Schriftart“. Wenn Sie Erfahrung in der Webentwicklung haben, fragen Sie sich vielleicht, warum diese so weit verbreitet sind. Sind das nicht nur lästige Details, über die Sie sich keine Sorgen machen sollten? Sollten PDF-Bibliotheken und -Reader nicht in der Lage sein, all dies für Sie zu erledigen, so wie es Webbrowser können? Leider ist dies nicht der Fall. Aufgrund der Beschaffenheit des PDF-Dateiformats ist es sehr schwierig, bei der Arbeit mit PDFs nicht auf Zeichenkodierungen und Schriftarten zu achten.
pdf-lib
tut sein Bestes, um die Dinge für Sie zu vereinfachen. Aber es kann keine Magie wirken. Das bedeutet, dass Sie Folgendes beachten sollten:
import { PDFDocument , StandardFonts } from 'pdf-lib'
const pdfDoc = await PDFDocument . create ( )
const courierFont = await pdfDoc . embedFont ( StandardFonts . Courier )
const page = pdfDoc . addPage ( )
page . drawText ( 'Some boring latin text in the Courier font' , {
font : courierFont ,
} )
embedFont
übergeben. Wenn Sie Ihre eigene Schriftart einbetten, können Sie alle von ihr unterstützten Unicode-Zeichen verwenden. Diese Funktion befreit Sie von den Einschränkungen, die Ihnen die Standardschriftarten auferlegen. Die meisten PDF-Dateien verwenden eingebettete Schriftarten. Sie können eine benutzerdefinierte Schriftart wie folgt einbetten und verwenden (siehe auch): import { PDFDocument } from 'pdf-lib'
import fontkit from '@pdf-lib/fontkit'
const url = 'https://pdf-lib.js.org/assets/ubuntu/Ubuntu-R.ttf'
const fontBytes = await fetch ( url ) . then ( ( res ) => res . arrayBuffer ( ) )
const pdfDoc = await PDFDocument . create ( )
pdfDoc . registerFontkit ( fontkit )
const ubuntuFont = await pdfDoc . embedFont ( fontBytes )
const page = pdfDoc . addPage ( )
page . drawText ( 'Some fancy Unicode text in the ŪЬȕǹƚü font' , {
font : ubuntuFont ,
} )
Beachten Sie, dass Kodierungsfehler ausgegeben werden, wenn Sie versuchen, ein Zeichen mit einer Schriftart zu verwenden, die es nicht unterstützt. Beispielsweise ist Ω
nicht im WinAnsi-Zeichensatz enthalten. Wenn Sie also versuchen, es auf einer Seite mit der Standardschrift Helvetica zu zeichnen, wird die folgende Fehlermeldung ausgegeben:
Error: WinAnsi cannot encode "Ω" (0x03a9)
at Encoding.encodeUnicodeCodePoint
Das Einbetten einer Schriftart in ein PDF-Dokument führt normalerweise zu einer Vergrößerung der Datei. Sie können die Vergrößerung einer Datei reduzieren, indem Sie die Schriftart so unterteilen, dass nur die erforderlichen Zeichen eingebettet werden. Sie können eine Schriftart unterteilen, indem Sie die Option subset
auf true
setzen. Zum Beispiel:
const font = await pdfDoc . embedFont ( fontBytes , { subset : true } ) ;
Beachten Sie, dass die Unterteilung nicht für alle Schriftarten funktioniert. Weitere Details finden Sie in #207 (Kommentar).
pdf-lib
kann PDF-Formularfelder erstellen, ausfüllen und lesen. Die folgenden Feldtypen werden unterstützt:
Codebeispiele finden Sie in den Verwendungsbeispielen für die Formularerstellung und das Ausfüllen von Formularen. Die Tests 1, 14, 15, 16 und 17 in den vollständigen Beispielen enthalten funktionierenden Beispielcode für die Formularerstellung und das Ausfüllen verschiedener JS-Umgebungen.
WICHTIG: Die Standardschriftart, die zum Anzeigen von Text in Schaltflächen, Dropdown-Listen, Optionslisten und Textfeldern verwendet wird, ist die Standardschriftart Helvetica. Diese Schriftart unterstützt nur Zeichen des lateinischen Alphabets (Einzelheiten finden Sie unter Schriftarten und Unicode). Das heißt, wenn einer dieser Feldtypen so erstellt oder geändert wird, dass er Text außerhalb des lateinischen Alphabets enthält (was häufig der Fall ist), müssen Sie eine benutzerdefinierte Schriftart einbetten und verwenden, um das Erscheinungsbild der Felder zu aktualisieren. Andernfalls wird ein Fehler ausgegeben (wahrscheinlich, wenn Sie das PDFDocument
speichern).
Sie können beim Ausfüllen von Formularfeldern eine eingebettete Schriftart wie folgt verwenden:
import { PDFDocument } from 'pdf-lib' ;
import fontkit from '@pdf-lib/fontkit' ;
// Fetch the PDF with form fields
const formUrl = 'https://pdf-lib.js.org/assets/dod_character.pdf' ;
const formBytes = await fetch ( formUrl ) . then ( ( res ) => res . arrayBuffer ( ) ) ;
// Fetch the Ubuntu font
const fontUrl = 'https://pdf-lib.js.org/assets/ubuntu/Ubuntu-R.ttf' ;
const fontBytes = await fetch ( fontUrl ) . then ( ( res ) => res . arrayBuffer ( ) ) ;
// Load the PDF with form fields
const pdfDoc = await PDFDocument . load ( formBytes ) ;
// Embed the Ubuntu font
pdfDoc . registerFontkit ( fontkit ) ;
const ubuntuFont = await pdfDoc . embedFont ( fontBytes ) ;
// Get two text fields from the form
const form = pdfDoc . getForm ( ) ;
const nameField = form . getTextField ( 'CharacterName 2' ) ;
const ageField = form . getTextField ( 'Age' ) ;
// Fill the text fields with some fancy Unicode characters (outside
// the WinAnsi latin character set)
nameField . setText ( 'Ӎӑȑїõ' ) ;
ageField . setText ( '24 ŷȇȁŗš' ) ;
// **Key Step:** Update the field appearances with the Ubuntu font
form . updateFieldAppearances ( ubuntuFont ) ;
// Save the PDF with filled form fields
const pdfBytes = await pdfDoc . save ( ) ;
Auf bestehende Formularfelder kann mit den folgenden Methoden von PDFForm
zugegriffen werden:
PDFForm.getButton
PDFForm.getCheckBox
PDFForm.getDropdown
PDFForm.getOptionList
PDFForm.getRadioGroup
PDFForm.getTextField
Neue Formularfelder können mit den folgenden Methoden von PDFForm
erstellt werden:
PDFForm.createButton
PDFForm.createCheckBox
PDFForm.createDropdown
PDFForm.createOptionList
PDFForm.createRadioGroup
PDFForm.createTextField
Nachfolgend sind einige der am häufigsten verwendeten Methoden zum Lesen und Füllen der oben genannten Unterklassen von PDFField
aufgeführt:
PDFCheckBox.check
PDFCheckBox.uncheck
PDFCheckBox.isChecked
PDFDropdown.select
PDFDropdown.clear
PDFDropdown.getSelected
PDFDropdown.getOptions
PDFDropdown.addOptions
PDFOptionList.select
PDFOptionList.clear
PDFOptionList.getSelected
PDFOptionList.getOptions
PDFOptionList.addOptions
PDFRadioGroup.select
PDFRadioGroup.clear
PDFRadioGroup.getSelected
PDFRadioGroup.getOptions
PDFRadioGroup.addOptionToPage
PDFTextField.setText
PDFTextField.getText
PDFTextField.setMaxLength
PDFTextField.getMaxLength
PDFTextField.removeMaxLength
pdf-lib
kann den Inhalt von Textfeldern extrahieren (siehe PDFTextField.getText
), aber es kann keinen einfachen Text auf einer Seite außerhalb eines Formularfelds extrahieren. Dies ist eine schwer zu implementierende Funktion, liegt jedoch im Umfang dieser Bibliothek und kann in Zukunft zu pdf-lib
hinzugefügt werden. Siehe Nr. 93, Nr. 137, Nr. 177, Nr. 329 und Nr. 380.pdf-lib
kann den Inhalt von Textfeldern entfernen und bearbeiten (siehe PDFTextField.setText
), stellt jedoch keine APIs zum Entfernen oder Bearbeiten von Text auf einer Seite außerhalb eines Formularfelds bereit. Dies ist ebenfalls eine schwer zu implementierende Funktion, liegt jedoch im Umfang von pdf-lib
und wird möglicherweise in Zukunft hinzugefügt. Siehe Nr. 93, Nr. 137, Nr. 177, Nr. 329 und Nr. 380.pdf-lib
unterstützt nicht die Verwendung von HTML oder CSS beim Hinzufügen von Inhalten zu einer PDF. Ebenso kann pdf-lib
keine HTML/CSS-Inhalte in PDFs einbetten. So praktisch eine solche Funktion auch sein mag, sie wäre äußerst schwierig zu implementieren und würde den Rahmen dieser Bibliothek bei weitem sprengen. Wenn Sie diese Funktion benötigen, sollten Sie Puppeteer in Betracht ziehen. Diskussionen sind der beste Ort, um mit uns zu chatten, Fragen zu stellen und mehr über pdf-lib zu erfahren!
Siehe auch MAINTAINERSHIP.md#communication und MAINTAINERSHIP.md#discord.
pdf-lib
unterstützt derzeit keine verschlüsselten Dokumente. Sie sollten pdf-lib
nicht mit verschlüsselten Dokumenten verwenden. Dies ist jedoch eine Funktion, die zu pdf-lib
hinzugefügt werden könnte. Bitte erstellen Sie ein Problem, wenn Sie diese Funktion hilfreich finden!
Wenn ein verschlüsseltes Dokument an PDFDocument.load(...)
übergeben wird, wird ein Fehler ausgegeben:
import { PDFDocument , EncryptedPDFError } from 'pdf-lib'
const encryptedPdfBytes = ...
// Assignment fails. Throws an `EncryptedPDFError`.
const pdfDoc = PDFDocument . load ( encryptedPdfBytes )
Dieses Standardverhalten ist normalerweise das, was Sie wollen. Damit können Sie leicht erkennen, ob ein bestimmtes Dokument verschlüsselt ist, und verhindern, dass Sie versuchen, es zu ändern. Wenn Sie das Dokument jedoch wirklich laden möchten, können Sie die Option { ignoreEncryption: true }
verwenden:
import { PDFDocument } from 'pdf-lib'
const encryptedPdfBytes = ...
// Assignment succeeds. Does not throw an error.
const pdfDoc = PDFDocument . load ( encryptedPdfBytes , { ignoreEncryption : true } )
Beachten Sie, dass die Verwendung dieser Option das Dokument nicht entschlüsselt . Dies bedeutet, dass alle Änderungen, die Sie am zurückgegebenen PDFDocument
vornehmen möchten, möglicherweise fehlschlagen oder zu unerwarteten Ergebnissen führen.
Sie sollten diese Option nicht nutzen. Es existiert nur aus Gründen der Abwärtskompatibilität.
Wir freuen uns über Beiträge aus der Open-Source-Community! Wenn Sie daran interessiert sind, zu pdf-lib
beizutragen, werfen Sie bitte einen Blick auf die Datei CONTRIBUTING.md. Es enthält Informationen, die Ihnen dabei helfen, pdf-lib
einzurichten und auf Ihrem Computer auszuführen. (Wir versuchen dies so einfach und schnell wie möglich zu machen!)
Schauen Sie sich MAINTAINERSHIP.md an, um Einzelheiten darüber zu erfahren, wie dieses Repo verwaltet wird und wie wir Probleme, PRs und Diskussionen nutzen.
pdfkit
ist eine PDF-Generierungsbibliothek für Node und den Browser. Diese Bibliothek war als Referenz und Existenznachweis bei der Erstellung von pdf-lib
äußerst hilfreich. Besonders nützlich war der Code von pdfkit
zum Einbetten von Schriftarten, PNGs und JPGs.pdf.js
ist eine PDF-Rendering-Bibliothek für den Browser. Diese Bibliothek war als Referenz beim Schreiben des Parsers von pdf-lib
hilfreich. Ein Teil des Codes für die Stream-Dekodierung wurde zur Verwendung in pdf-lib
direkt nach TypeScript portiert.pdfbox
ist eine in Java geschriebene Bibliothek zur PDF-Generierung und -Änderung. Diese Bibliothek war eine unschätzbare Referenz bei der Implementierung von Formularerstellungs- und Ausfüll-APIs für pdf-lib
.jspdf
ist eine PDF-Generierungsbibliothek für den Browser.pdfmake
ist eine PDF-Generierungsbibliothek für den Browser.hummus
ist eine PDF-Generierungs- und Änderungsbibliothek für Node-Umgebungen. hummus
ist ein Node-Wrapper um eine C++-Bibliothek und funktioniert daher nicht in vielen JavaScript-Umgebungen – wie dem Browser oder React Native.react-native-pdf-lib
ist eine PDF-Generierungs- und Änderungsbibliothek für React Native-Umgebungen. react-native-pdf-lib
ist ein Wrapper für C++- und Java-Bibliotheken.pdfassembler
ist eine PDF-Generierungs- und Änderungsbibliothek für Node und den Browser. Für die Verwendung sind einige Kenntnisse über die logische Struktur von PDF-Dokumenten erforderlich. Dieses Repo enthielt früher eine Datei namens pdf_specification.pdf
im Stammverzeichnis. Dabei handelte es sich um eine Kopie der Spezifikation PDF 1.7, die von Adobe kostenlos zur Verfügung gestellt wird. Am 30.08.2021 erhielten wir eine DMCA-Beschwerde, in der wir aufgefordert wurden, die Datei aus diesem Repo zu entfernen. Das einfache Entfernen der Datei über einen neuen Commit an master
reichte nicht aus, um der Beschwerde nachzukommen. Die Datei musste vollständig aus dem Git-Verlauf des Repos entfernt werden. Leider wurde die Datei vor über zwei Jahren hinzugefügt, was bedeutete, dass wir den Git-Verlauf des Repos neu schreiben und Push to master
erzwingen mussten?.
Wir haben die Datei entfernt und den Verlauf des Repos mit BFG Repo-Cleaner wie hier beschrieben neu geschrieben. Der vollständigen Transparenz halber finden Sie hier die genauen Befehle, die wir ausgeführt haben:
$ git clone [email protected]:Hopding/pdf-lib.git
$ cd pdf-lib
$ rm pdf_specification.pdf
$ git commit -am 'Remove pdf_specification.pdf'
$ bfg --delete-files pdf_specification.pdf
$ git reflog expire --expire=now --all && git gc --prune=now --aggressive
$ git push --force
Wenn Sie ein Benutzer von pdf-lib
sind, sollte es Ihnen egal sein! pdf-lib
einfach weiterhin wie gewohnt verwenden? !
Wenn Sie ein pdf-lib
Entwickler sind (das heißt, Sie haben pdf-lib
geforkt und/oder eine offene PR haben), hat dies Auswirkungen auf Sie. Wenn Sie das Repo vor dem 30.08.2021 geforkt oder geklont haben, ist der Git-Verlauf Ihres Forks nicht mit master
-Zweig dieses Repos synchronisiert. Leider wird Ihnen dies wahrscheinlich Kopfschmerzen bereiten. Entschuldigung! Wir wollten die Geschichte nicht neu schreiben, aber es gab wirklich keine Alternative.
Es ist wichtig zu beachten, dass sich der Quellcode von pdf-lib überhaupt nicht geändert hat. Es ist genau das Gleiche wie vor der Neufassung der Git-Geschichte. Das Repo hat immer noch genau die gleiche Anzahl an Commits (und sogar die gleichen Commit-Inhalte, mit Ausnahme des Commits, das pdf_specification.pdf
hinzugefügt hat). Was sich geändert hat, sind die SHAs dieser Commits.
Der einfachste Weg, mit dieser Tatsache umzugehen, besteht darin:
In dieser StackOverflow-Antwort finden Sie eine ausführliche Erklärung, was eine Neufassung des Git-Verlaufs mit sich bringt.
MIT