top
Loading...
JAVAPDF解決方案

概述 Java Servlet 編程可以很方便地將 HTML 文件發送到客戶端的 Web 瀏覽器。然而許多站點還允許訪問非 HTML 格式的文檔,包括 Adobe PDF、Microsoft Word 和 Micorsoft Excel 等。事實上這些非 HTML 格式只要能用 MIME 類型表示,就可以利用 servlet 來發送。本文將以 PDF為例,向你介紹如何使用 servlet 傳送非 HTML 格式文件及該文件是如何在服務器端用Java生成的。

你只要將文件寫到servlet 的輸出流中,就可以利用 servlet 在瀏覽器中打開一個文件。首先從獲得 servlet 的輸出流開始:

ServletOutputStream out = res.getOutputStream();

互聯網上使用 MIME (multipurpos Internet mail extension 多目的互聯網郵件擴展協議)來傳送混合格式、多媒體和二進制數據文件。如果要在 servlet 的 response 對象中打開某個文檔,就必須設置該文檔的 MIME 類型。

向Web客戶端發送PDF文檔

(一)MIME類型

Web 瀏覽器使用 MIME 類型來識別非 HTML 文檔,并決定如何顯示該文檔內的數據。將插件 (plug-in) 與 MIME 類型結合使用,則當 Web 瀏覽器下載 MIME 類型指示的文檔時,就能夠啟動相應插件處理此文檔。某些 MIME 類型還可以與外部程序結合使用,瀏覽器下載文檔后會啟動相應的外部程序。

MIME 類型非常有用。它們允許 Web 瀏覽器處理不同格式的文檔,卻不需要事先嵌入相關知識。Java Servlets 可以使用 MIME 類型來向瀏覽器傳送非 HTML 文件,比如 Adobe PDF 和 Micorsoft Word。使用正確的 MIME 類型能夠保證這些非 HTML 文件被正確的插件或外部程序顯示。

PDF 文件的 MIME 類型是 "application/pdf"。要用servlet 來打開一個 PDF 文檔,需要將 response 對象中 header 的 content 類型設置成 "application/pdf":

// PDF 文件的 MIME 類型
    res.setContentType( "application/pdf" );

(二)Content disposition

HTTP response header中的content-disposition 允許 servlet 指定文檔表示的信息。使用這種header ,你就可以將文檔指定成單獨打開(而不是在瀏覽器中打開),還可以根據用戶的操作來顯示。如果用戶要保存文檔,你還可以為該文檔建議一個文件名。這個建議名稱會出現在 Save As 對話框的“文件名”欄中。如果沒有指定,則對話框中就會出現 servlet 的名字。在 servlet 中,你需要將 header 設置成下面這樣:

res.setHeader("Content-disposition",
                  "attachment; filename=" +
                  "Example.pdf" );
    // attachment -因為不希望在瀏覽器中直接打開它,而是利用Adobe Acrobat。
    // 可以通過設置default file name來確定保存文當時的建議名稱。

(三)封裝非 HTML 文檔

完成上述工作后,剩下的就非常簡單了。你需要根據待傳送文件的名字,創建一個 java.net.URL 對象。交給 URL 構造器的字符串必須是指向該文件的一個有效 URL 地址。在這里,我要打開本地的PDF文檔:

String fileURL = "http://localhost/aboutadobe/careeropp/pdfs/tables.pdf;

URL 字符串也可以類似于 http://www.gr.com/pub/somefile.doc 或 http://www.gr.com/pub/somefile.xls。但必須確保待傳送文件類型與先前在 HTTP response 對象中設置的 MIME 類型一致。

(四)其他

開始閱讀傳送的文檔之前,首先要從 URL 對象中獲得輸入流 InputStream,用 BufferedInputStream 將 InputStream 封裝起來。

BufferedInputStreambis = newBufferedInputStream(url.openStream());

一旦你完成上述操作,就只要簡單地將 InputStream 中的字節,寫入到 servlet 的輸出流 OutputStream 中:

BufferedOutputStreambos = new BufferedOutputStream(out);

    byte[] buff = new byte[2048];
    intbytesRead;

    // 一個簡單的讀寫循環

    while(-1 != (bytesRead = bis.read(buff, 0, buff.length))) {
        bos.write(buff, 0, bytesRead);
    }

在最后的代碼塊中,關閉這些流 ,如:bos.close();

PDF文檔在服務器端的生成

利用iText040工具包可以很方便的輸出一個十分漂亮的PDF文檔。

1.Document的創建

Document document=new Document(p0, p1, p2, p3, p4)

其中,p0為頁面的大小,如 PageSize.A4; p1—p4分別描述上下左右頁邊空白。

2. 構造復寫器

PdfWriter.getInstance(document, new  FileOutputStream("tables.pdf"))

執行程序后,將在當前目錄下生成一個名為tables.pdf的文件。

接著打開Document:document.open()

3. 根據需要定義一個Table

//一個擁有十列的Table
Table datatable = new Table(10);
//定義Cell與Cell之間的距離為零
datatable.setCellpadding(0);
//定義Cell的間隔
      datatable.setCellspacing(3);
//使Table沒有邊框
datatable.setBorder(Rectangle.NO_BORDER);
//定義每一列的寬度
      intheaderwidths[] = {10, 30, 15, 15, 5, 5, 5, 5, 5, 5};
      datatable.setWidths(headerwidths);
datatable.setWidth(100);

4.字體的定義:

BaseFont bf = BaseFont.createFont(String name, String encoding, boolean embedded)

“name”為字體名,“encoding”為編碼名稱。

5. Cell的定義

Cell cell = new Cell(new Phrase("String string",f));

String為Cell中要顯示的內容。另外有很多方法來控制Cell,其中比較常用的幾個方法如下:

cell.setBorder(int value)

根據經驗,value值對應的邊框形狀見下圖:

圖例Value整數值
Rectangle.ALIGN_BOTTOM6
Rectangle.ALIGN_BASELINE7
Rectangle.ALIGN_CENTER1
Rectangle.ALIGN_JUSTIFIED3
Rectangle.ALIGN_MIDDLE5
Rectangle.ALIGN_RIGHT2
Rectangle.ALIGN_TOP4

cell.setColspan(int value)和 cell.setRowspan(int value)分別定義了cell所占的列和行。

值得注意的是:一行中各cell所占列的總和一定要嚴格符合構造table時定義的列數。

cell.setHorizontalAlignment(int value)和cell.setVerticalAlignment(int value)分別確定該cell將處在水平及豎直方向上的位置。

最后,將cell加入到table中去:table.addCell(Cell cell)

6.table加到document中去,并關閉document:

document.add(table);
document.close();

小結

正如你所讀到的,利用iText040編寫一個可以輸出PDF文檔的JavaBean。接著,再通過sevlet將它輸出到客戶端,相當簡單。只要你使用適當的方法,設置正確的MIME類型就可以做到。

北斗有巢氏 有巢氏北斗