Die Frage ist falsch in dem Sinne, dass es darauf hindeutet, dass das HTML-Parsing alles verlangsamt. Das ist nicht wahr. Der Engpass tritt auf, noch bevor das erste HTML-Snippet analysiert wird.
Sie sind die grundlegendsten Handvoll Zeilen Code mit Ihrem PDF von HTML zu erstellen, wie im ParseHtml Beispiel demonstriert:
public void createPdf(String file) throws IOException, DocumentException {
// step 1
Document document = new Document();
// step 2
PdfWriter writer = PdfWriter.getInstance(document, new FileOutputStream(file));
// step 3
document.open();
// step 4
XMLWorkerHelper.getInstance().parseXHtml(writer, document,
new FileInputStream(HTML));
// step 5
document.close();
}
Dieser Code ist einfach, aber es führt intern eine Menge von Operationen, wie erklärt in den Kommentaren dieser anderen Frage: XMLWorkerHelper performance slow.
Die Registrierung von Schriftartenverzeichnissen erfordert viel Zeit. Sie können dies vermeiden, indem Sie Ihren eigenen FontProvider
verwenden, wie im Beispiel ParseHtmlFonts getan.
public void createPdf(String file) throws IOException, DocumentException {
// step 1
Document document = new Document();
// step 2
PdfWriter writer = PdfWriter.getInstance(document, new FileOutputStream(file));
writer.setInitialLeading(12.5f);
// step 3
document.open();
// step 4
// CSS
CSSResolver cssResolver = new StyleAttrCSSResolver();
CssFile cssFile = XMLWorkerHelper.getCSS(new FileInputStream(CSS));
cssResolver.addCss(cssFile);
// HTML
XMLWorkerFontProvider fontProvider = new XMLWorkerFontProvider(XMLWorkerFontProvider.DONTLOOKFORFONTS);
fontProvider.register("resources/fonts/Cardo-Regular.ttf");
fontProvider.register("resources/fonts/Cardo-Bold.ttf");
fontProvider.register("resources/fonts/Cardo-Italic.ttf");
fontProvider.addFontSubstitute("lowagie", "cardo");
CssAppliers cssAppliers = new CssAppliersImpl(fontProvider);
HtmlPipelineContext htmlContext = new HtmlPipelineContext(cssAppliers);
htmlContext.setTagFactory(Tags.getHtmlTagProcessorFactory());
// Pipelines
PdfWriterPipeline pdf = new PdfWriterPipeline(document, writer);
HtmlPipeline html = new HtmlPipeline(htmlContext, pdf);
CssResolverPipeline css = new CssResolverPipeline(cssResolver, html);
// XML Worker
XMLWorker worker = new XMLWorker(css, true);
XMLParser p = new XMLParser(worker);
p.parse(new FileInputStream(HTML));
// step 5
document.close();
}
In diesem Fall anweisen wir iText DONTLOOKFORFONTS, also eine enorme Menge an Zeit zu sparen. Anstatt iText nach Schriften zu suchen, teilen wir iText mit, welche Schriften wir im HTML verwenden werden.
Ist Ihr HTML tief verschachtelt? Zum Beispiel, ist alles in einem riesigen DIV verpackt? In diesen Fällen muss der Parser (und sogar normale Desktop-Browser) den ganzen Weg bis zum Ende des Dokuments gehen, bevor es das erste Ding rendern kann. Benutzt du Tische? PDFs haben kein Konzept von Tabellen, also muss iText sie simulieren, die rechenintensiv sein können, wenn sie lang sind. Benutzt du Bilder? Wenn dies der Fall ist, muss iText die Bilder laden/herunterladen (abhängig davon, wie sie referenziert werden), was ebenfalls Zeit benötigt. –
Ich habe noch keine Antwort, aber ich sehe, wie unglaublich langsam diese Bibliothek auch ist. Die meiste Zeit ist in der folgenden Methode in ParseXHtml gegessen: iTextSharp.text.FontFactoryImp.RegisterDirectories –
Ich finde die XMLWorkerHelper-Instanz super langsam nur beim Ausführen meiner Anwendung im Debug-Modus. –