2011-07-08 44 views
3

我的要求是要求生成包含任意文本和條形碼的pdf文檔。我有相關的question地址pdf生成的一部分,但在這裏我想知道如何在Java中的PDF中加入條形碼。如何使用生成將整合動態生成條形碼(Java)的pdf文檔?

到目前爲止,我發現在barcode4j是怎麼做的與Apache FOP明確的解釋:Instructions for the Apache FOP extension

但它看起來是XSL-FO是不是我要求的主要選擇,我寧願去與PDF表單(使用iText或PDFBox或類似)。再次,這還不是最終的。

您是否在pdf中使用圖像或字體作爲條形碼?除了pdf API以外,還有什麼依賴性(字體,庫)?

回答

1

我會使用條形碼圖像生成器,然後將其嵌入到轉換爲PDF的HTML文檔中。

檢出this library用於將XHTML呈現爲PDF。按照您最初的計劃,使用barcode4j將條形碼呈現爲圖像。

+0

然而,這不是免費的:它需要iText的,將要求在商業許可我的情況。 – topchef

+0

這是GPL3。除非你需要表揚,否則它不需要商業許可證。 –

1

如果你準備放鬆你生成PDF要求使用非Java的工具,你可能會發現以下有用的:

  1. 佈局使用HTML/CSS/JS與佔位符條形碼的頁面模板。
  2. 使用Barcode4J至output SVG,然後將其放入模板中。
  3. 使用wkhtmltopdf命令行工具呈現頁面。 wkhtmltopdf在引擎蓋下使用了WebKit,因此它使用HTML/CSS可以很好地控制PDF佈局。
2

爲了在PDF中生成條碼我強烈建議iText給你。如果你使用Maven的,您可以添加這些依賴關係,你可以開始:

<dependency> 
     <groupId>com.lowagie</groupId> 
     <artifactId>itext</artifactId> 
     <version>2.0.7</version> 
    </dependency> 
    <dependency> 
     <groupId>bouncycastle</groupId> 
     <artifactId>bcmail-jdk14</artifactId> 
     <version>136</version> 
    </dependency> 
    <dependency> 
     <groupId>bouncycastle</groupId> 
     <artifactId>bcprov-jdk14</artifactId> 
     <version>136</version> 
    </dependency> 

要生成條形碼需要的代碼只有幾行:

Barcode128 code128 = new Barcode128(); 
    code128.setCodeType(Barcode128.CODE128); 
    code128.setCode(new Long(1234559690234234); 
    Chunk chunk = new Chunk(code128.createImageWithBarcode(cb, null, null), 
      200, -30); 
    Paragraph p = new Paragraph(chunk); 

添加段落到文檔,瞧,你去了。一個好的教程可以在這裏找到:

IText Example

+0

謝謝,絕對會試試看。 – topchef

5

我成功地將條形碼使用PDFBox的和燒烤的PDF文件。燒烤提供輸出接口來自己繪製條形碼。我以這樣的方式實現了這個接口,drawBar()轉換爲對PDPageContentStream.fillRect()的調用。

添加條形碼到PDF現在歸結爲:

Barcode barcode = BarcodeFactory.createCode128(text); 
barcode.output(new PDFBoxOutput(pageContentStream, startX, startY, height)); 

的PDFBoxOutput類看起來是這樣的:

import java.awt.Color; 
import java.io.IOException; 

import net.sourceforge.barbecue.output.LabelLayout; 
import net.sourceforge.barbecue.output.Output; 
import net.sourceforge.barbecue.output.OutputException; 

import org.apache.pdfbox.pdmodel.edit.PDPageContentStream; 

public class PDFBoxOutput implements Output { 

    /** The widths and heights from Barbecue are multipplied with this scalar to get the widths and heights for PDFBox. */ 
    public final static float SCALAR = 0.5f; 

    private final PDPageContentStream stream; 
    private final float startX; 
    private final float startY; 
    private final float height; 
    private boolean toggleDrawingColor; 

    PDFBoxOutput(PDPageContentStream stream, float startX, float startY, float height) { 
     this.stream = stream; 
     this.startX = startX; 
     this.startY = startY; 
     this.height = height; 
    } 

    @Override 
    public void beginDraw() throws OutputException {} 

    @Override 
    public int drawBar(int x, int y, int width, int height, boolean paintWithForegroundColor) throws OutputException { 
     if (paintWithForegroundColor == !toggleDrawingColor) { 
      try { 
       stream.setLineWidth(0.0f); 
       stream.setStrokingColor(Color.BLACK); 
       stream.fillRect(startX + SCALAR * x, startY - SCALAR * y, SCALAR * width, this.height); 
       stream.stroke(); 
      } catch (IOException e) { 
       throw new OutputException(e); 
      } 
     } 
     return width; 
    } 

    @Override 
    public int drawText(String text, LabelLayout layout) throws OutputException { 
     return 0; 
    } 

    @Override 
    public void endDraw(int width, int height) throws OutputException {} 

    @Override 
    public void paintBackground(int x, int y, int width, int height) {} 

    @Override 
    public void toggleDrawingColor() { 
     toggleDrawingColor = !toggleDrawingColor; 
    } 

} 
+0

它的工作原理。起初,條碼已生成,但不會掃描。有兩種可能的修復方法:1)將SCALAR更改爲1,但條形碼很大(並且很難看),或者2)在Adobe設置(或等效)中更改DPI:編輯 - >首選項 - >頁面顯示 - >分辨率 - 自定義分辨率爲300像素/英寸)。我在96. –

+0

我知道這不是評論的目的,但非常感謝你,這對我來說非常完美。 – UpAllNight