PDFlib

高度なPDFアプリケーションの開発を支援する定番プログラムライブラリー Supported by インフォテック株式会社

PDFlib サンプル集(クックブック)

本サンプルプログラムは、PDF 文書生成ライブラリーの実装である PDFlib の基本的な機能を実際のプログラムで紹介したものです。

本サイトでダウンロードした PDFlib は、一部機能の制限を除き、評価版として無償でお使いいただけます。

バーコードフィールド

Acrobat がサポートする3種類のバーコード(PDF417バーコード、データマトリックスバーコード、QR バーコード)を生成するサンプルプログラムです。

左のテキストフィールドに入力したテキストデータを、右側のバーコードに反映します。

バーコードフィールドの表示と印刷は、Acrobat 9 かそれ以降のバージョンで動作します。

必要な製品:PDFlib/PDFlib+PDI/PDFlib PPS


package com.pdflib.cookbook.pdflib.form_fields;

import com.pdflib.pdflib;
import com.pdflib.PDFlibException;

/**
 * バーコードフィールド : Acrobat がサポートする3種類のバーコードを生成します。
 * 
 * このバーコードフォームは次のように動作します。
 * - 左のテキストフィールドは、ユーザーが入力できるデータソースとして機能します。
 * - 右のバーコードフィールドは、PDF417、データマトリックス、QR のバーコードとし
 *   て表され、テキストの値を反映します。
 * - 各バーコードフィールドには "calculate" アクションとして JavaScript が割り当
 *   てられます。
 *   "calculate" イベントが発生するたび、バーコードは再計算されます。
 * - 追加の"page open"アクションは、ページを開いた時にバーコードをレンダリングさせ
 *   るため"this.calculateNow()" を実行します。
 * - "Reset"ボタンは、全てのテキストフィールドを(それに伴いバーコードフィールドも)
 *   初期化して元の状態に戻すために使用することができます。
 * 重要:バーコードフィールドの表示と印刷は、Acrobat 9 かそれ以降のバージョンで動作
 *       します。(Adobe Readerでは動作しない)
 * 
 * 必要な製品: PDFlib/PDFlib+PDI/PPS 9
 * 必要なデータ: 無し
 * 
 */
public class barcode_field {
    /**
     * バーコードフィールドのデフォルトのデータを提供するサンプルテキスト
     */
    final static int MARGIN = 30;
    
    /**
     * バーコードフィールドのデフォルトのデータを提供するサンプルテキスト
     */
    final static String SAMPLE_TEXT =
        "To change the barcode field to the right, type in this box. "
        + "The barcode field to the right will reflect the contents of the "
        + "text field as barcode after the text field lost the focus. To "
        + "reset the contents of all barcode fields, click the 'Reset' button.";
    
    /**
     * テキスト入力フィールドのツールヒントテキスト
     */
    final static String TOOLTIP_TEXT = "Enter data for barcode field here";
    
    /**
     * ページの高さ
     */
    final static int PAGE_HEIGHT = 842;
    
    /**
     * ページの幅
     */
    final static int PAGE_WIDTH = 595;
    
    /**
     * リセットボタンの高さ
     */
    final static int RESET_BUTTON_HEIGHT = 50;
    
    /**
     * リセットボタンの幅
     */
    final static int RESET_BUTTON_WIDTH = 120;
    
    public static void main(String argv[]) {
        String outfile = "barcode_field.pdf";
        String title = "Barcode Fields";

        pdflib p = null;
	int exitcode = 0;

        try {
            p = new pdflib();

            /* load_font() 等でエラーが起きた場合、-1を返す */
            p.set_option("errorpolicy=return");

            if (p.begin_document(outfile,
                    "compatibility=1.7ext3 pagelayout=singlepage") == -1)
                throw new Exception("Error: " + p.get_errmsg());

            p.set_info("Creator", "PDFlib Cookbook");
            p.set_info("Title", title);

            int font = p.load_font("Helvetica", "winansi", "");
            if (font == -1)
                throw new Exception("Error: " + p.get_errmsg());

            /*
             * ページ上の全てのフィールドの内容を再計算するJavaScriptを定義する
             */
            final int calculate_now_action =
                p.create_action("JavaScript", "script { this.calculateNow(); }");
            
            /* ページを始める */
            p.begin_page_ext(0, 0, 
                "width=a4.width height=a4.height "
                    + "action={open "+ calculate_now_action + "}");

            /*
             * リセットボタンのオプションリストを生成する。デフォルト値にリセットする
             * には全てのフィールド名を含む必要がある。
             */
            String reset_optlist = "namelist={";
            
            /*
             * 使用可能な領域と、テキストとバーコードフィールドのサイズを計算する。
             * バーコードフィールドはテキストフィールドの幅の2倍に設定する。
             */
            final int num_fields = 3;
            final double field_area_height =
                PAGE_HEIGHT - 3 * MARGIN - RESET_BUTTON_HEIGHT;
            final double field_area_width =
                PAGE_WIDTH - 2 * MARGIN;
            final double field_height =
                (field_area_height - (num_fields - 1) * MARGIN) / num_fields;
            final double text_field_width = (field_area_width - MARGIN) / 3;
            final double barcode_field_width =
                                (field_area_width - MARGIN) * 2 / 3;
            
            int field_number = 0;
            
            String text_field_name = "text_" + field_number;
            String barcode_field_name = "barcode_" + field_number;
            
            /*
             * リセットするため、テキストフィールド名をリストフィールドに追加する。
             */
            reset_optlist += " {" + text_field_name + "}";
            
            /*
             * テキストフィールドを生成
             * 
             * Acrobat は少なくともバージョン10.1までは、ページ上の最初のフィールドにバー
             * コードフィールドがある場合、クラッシュするバグが含まれていることに注意する。
             * そのため、別の種類のフィールドが最初に作成されていることを確認してください。
             */
            String optlist = "tooltip={PDF417 barcode:\n" + TOOLTIP_TEXT + "} "
                + "multiline=true bordercolor={gray 0} linewidth=1 "
                + "font=" + font + " "
                + "currentvalue={PDF417 barcode:\n" + SAMPLE_TEXT + "} "
                + "defaultvalue={PDF417 barcode:\n" + SAMPLE_TEXT + "}";
            double x = MARGIN;
            double y = PAGE_HEIGHT - (MARGIN + RESET_BUTTON_HEIGHT )
                        - (field_number + 1) * (MARGIN + field_height);
            p.create_field(x, y, x + text_field_width, y + field_height,
                text_field_name, "textfield", optlist);
            
            /*
             * テキストフィールドの内容からバーコードフィールドの値を計算するアクションを
             * 生成する。
             */
            int calculate_action = create_calc_action(p, text_field_name);
            
            /*
             * PDF417 バーコードを生成:
             * 
             * - 圧縮無し (dataprep=0)
             * - エラー訂正係数 レベル 7 (ecc=7)
             * - 横間隔: 3, 縦間隔: 6 (xsymheight=6 xsymwidth=3)
             */
            optlist = "barcode={symbology=PDF417 dataprep=0 "
                + "ecc=7 xsymheight=6 xsymwidth=3} "
                + "action={calculate=" + calculate_action + "} font=" + font;
            x = 2 * MARGIN + text_field_width;
            p.create_field(x, y, x + barcode_field_width, y + field_height,
                barcode_field_name, "textfield", optlist);
            
            /*
             * データマトリックスバーコードを生成するため、いくつかの手順を繰り返す
             */
            field_number += 1;
            text_field_name = "text_" + field_number;
            barcode_field_name = "barcode_" + field_number;
            
            reset_optlist += " {" + text_field_name + "}";
            
            optlist = "tooltip={Data Matrix barcode:\n" + TOOLTIP_TEXT + "} "
                + "multiline=true bordercolor={gray 0} linewidth=1 "
                + "font=" + font + " "
                + "currentvalue={Data Matrix barcode:\n" + SAMPLE_TEXT + "} "
                + "defaultvalue={Data Matrix barcode:\n" + SAMPLE_TEXT + "}";
            x = MARGIN;
            y = PAGE_HEIGHT - (MARGIN + RESET_BUTTON_HEIGHT )
                    - (field_number + 1) * (MARGIN + field_height);
            p.create_field(x, y, x + text_field_width, y + field_height,
                text_field_name, "textfield", optlist);
            calculate_action = create_calc_action(p, text_field_name);
            
            /*
             * データマトリックスバーコードを生成
             */
            optlist = "barcode={symbology=DataMatrix dataprep=0 "
                + "ecc=0 xsymwidth=10} "
                + "action={calculate=" + calculate_action + "} font=" + font;
            x = 2 * MARGIN + text_field_width;
            p.create_field(x, y, x + barcode_field_width, y + field_height,
                barcode_field_name, "textfield", optlist);
            
            /*
             * QRコードバーコードを生成するため、いくつかの手順を繰り返す
             */
            field_number += 1;
            text_field_name = "text_" + field_number;
            barcode_field_name = "barcode_" + field_number;
            
            reset_optlist += " {" + text_field_name + "}";
            
            optlist = "tooltip={QR Code barcode:\n" + TOOLTIP_TEXT + "} "
                + "multiline=true bordercolor={gray 0} linewidth=1 "
                + "font=" + font + " "
                + "currentvalue={QR Code barcode:\n" + SAMPLE_TEXT + "} "
                + "defaultvalue={QR Code barcode:\n" + SAMPLE_TEXT + "}";
            x = MARGIN;
            y = PAGE_HEIGHT - (MARGIN + RESET_BUTTON_HEIGHT )
                    - (field_number + 1) * (MARGIN + field_height);
            p.create_field(x, y, x + text_field_width, y + field_height,
                text_field_name, "textfield", optlist);
            calculate_action = create_calc_action(p, text_field_name);
            
            /*
             * QR コード バーコードを生成 :
             * 
             * - エラー訂正係数 :レベル 2 (ecc=2)
             * - 横間隔: 10
             * - エンコードする前に圧縮 (dataprep=1)
             */
            optlist = "barcode={symbology=QRCode ecc=2 xsymwidth=10 dataprep=1} "
                + "action={calculate=" + calculate_action + "} font=" + font;
            x = 2 * MARGIN + text_field_width;
            p.create_field(x, y, x + barcode_field_width, y + field_height,
                barcode_field_name, "textfield", optlist);
            
            /*
             * リセットボタンのためのオプションリストを終了し、テキスト入力フィールドを
             * デフォルト値にリセットするリセットボタンを作成する。
             */
            reset_optlist += "}";
            final int reset_action = p.create_action("ResetForm", reset_optlist);

            optlist = "action={activate=" + reset_action + "} font={" + font 
                    + "} caption={Reset} bordercolor=black "
                    + "tooltip={Reset all fields to default values}";
            x = MARGIN;
            y = PAGE_HEIGHT - MARGIN - RESET_BUTTON_HEIGHT;
            p.create_field(x, y, x + RESET_BUTTON_WIDTH, y + RESET_BUTTON_HEIGHT,
                "Reset", "PushButton", optlist);
            
            /*
             * Adobe Reader の場合、バーコードフィールドを表示できないため、テキスト
             * ボックスで警告を表示する
             */
            optlist = "font=" + font + " fontsize=14 fillcolor=red";
            int tf = -1;
            tf = p.add_textflow(tf,
                "Note that the barcode fields only work with full Acrobat "
                    + "version 9 or newer, but not with Adobe Reader!",
                    optlist);
            x = 2 * MARGIN + RESET_BUTTON_WIDTH;
            p.fit_textflow(tf, x, y,
                PAGE_WIDTH + 3 * MARGIN - RESET_BUTTON_WIDTH,
                y + RESET_BUTTON_HEIGHT, "fitmethod=auto");
            
            p.end_page_ext("");
            p.end_document("");
        }
        catch (PDFlibException e) {
            System.err.println("PDFlib exception occurred:");
            System.err.println("[" + e.get_errnum() + "] " + e.get_apiname()
                + ": " + e.get_errmsg());
            exitcode = 1;
        }
        catch (Exception e) {
            System.err.println(e);
            exitcode = 1;
        }
        finally {
            if (p != null) {
                p.delete();
            }
            System.exit(exitcode);
        }
    }

    /**
     * バーコードフィールドの値を計算するためのアクションを作成する
     * 
     * @param p
     *            pdflib オブジェクト
     * @param text_field_name
     *            バーコードフィールドの値を決定している、テキストフィールドの名前
     * 
     * @return calculate アクションのハンドル
     * 
     * @throws PDFlibException
     */
    private static int create_calc_action(pdflib p, String text_field_name)
            throws PDFlibException {
        final String script =
            "script { "
                + "try { "
                    + "var fieldname = \"" + text_field_name + "\"; "
                    + "event.value = fieldname + \":\" + this.getField(fieldname).value;"
                + "} "
                + "catch(e) {"
                    + "event.value = \"EXCEPTION\";"
                + "}"
            + "}";
        return p.create_action("JavaScript", script);
    }
}
(Nov 16, 2015 - May 23, 2019)