DocumentBuilder フルエント API
DocumentBuilder は、テキストの配置、フォント、注釈、フォームフィールド、コンテンツ要素を完全に制御しながら、PDF ドキュメントをページ単位で構築するためのフルエント API です。
バインディング対応状況(v0.3.38)。
DocumentBuilder+FluentPageBuilder+EmbeddedFontは Rust、Python、Node/TypeScript、C#、Go、WASM で提供されています。すべてのバインディングが同一の機能を公開しています。複数ページ構築、埋め込みフォントによる CJK/キリル文字/ギリシャ文字テキスト、15 種類の注釈メソッド、5 種類の AcroForm ウィジェット、グラフィックスプリミティブ(rect、filled_rect、line)、AES-256 暗号化、そして HTML+CSS パイプラインです。
クイック例
Rust
use pdf_oxide::writer::{DocumentBuilder, PageSize, DocumentMetadata};
let mut builder = DocumentBuilder::new()
.metadata(DocumentMetadata::new().title("My Document"));
builder
.page(PageSize::Letter)
.at(72.0, 720.0)
.heading(1, "Hello, World!")
.paragraph("This is a PDF document created with DocumentBuilder.")
.done();
let bytes = builder.build()?;
std::fs::write("output.pdf", bytes)?;
Python
from pdf_oxide import DocumentBuilder, EmbeddedFont
font = EmbeddedFont.from_file("DejaVuSans.ttf")
pdf = (DocumentBuilder()
.register_embedded_font("DejaVu", font)
.a4_page()
.font("DejaVu", 12).at(72, 720).text("Hello, World!")
.highlight((1.0, 1.0, 0.0))
.done()
.build())
open("output.pdf", "wb").write(pdf)
Node / TypeScript
import { DocumentBuilder, EmbeddedFont } from "pdf-oxide";
const font = await EmbeddedFont.fromFile("DejaVuSans.ttf");
const bytes = new DocumentBuilder()
.registerEmbeddedFont("DejaVu", font)
.a4Page()
.font("DejaVu", 12).at(72, 720).text("Hello, World!")
.highlight([1.0, 1.0, 0.0])
.done()
.build();
C#
using PdfOxide;
using var font = EmbeddedFont.FromFile("DejaVuSans.ttf");
var bytes = DocumentBuilder.Create()
.RegisterEmbeddedFont("DejaVu", font)
.A4Page()
.Font("DejaVu", 12).At(72, 720).Text("Hello, World!")
.Highlight(1.0, 1.0, 0.0)
.Done()
.Build();
File.WriteAllBytes("output.pdf", bytes);
Go(CGo 経由。CGO_ENABLED=1 が必要)
import pdfoxide "github.com/yfedoseev/pdf_oxide/go"
font, _ := pdfoxide.EmbeddedFontFromFile("DejaVuSans.ttf")
defer font.Close()
builder := pdfoxide.NewDocumentBuilder()
builder.RegisterEmbeddedFont("DejaVu", font)
builder.A4Page().
Font("DejaVu", 12).At(72, 720).Text("Hello, World!").
Highlight(1.0, 1.0, 0.0).
Done()
bytes, _ := builder.Build()
WASM(ブラウザ/Node/バンドラー — API は共通)
import init, { DocumentBuilder, EmbeddedFont } from "pdf-oxide-wasm/web";
await init();
const font = await fetch("/DejaVuSans.ttf").then(r => r.arrayBuffer());
const bytes = new DocumentBuilder()
.registerEmbeddedFont("DejaVu", EmbeddedFont.fromBytes(new Uint8Array(font), "DejaVu"))
.a4Page()
.font("DejaVu", 12).at(72, 720).text("Hello, World!")
.done()
.build();
C++
#include <pdf_oxide/pdf_oxide.hpp>
auto font = pdf_oxide::EmbeddedFont::from_file("DejaVuSans.ttf");
auto builder = pdf_oxide::DocumentBuilder::create();
builder.register_embedded_font("DejaVu", font);
builder.a4_page()
.font("DejaVu", 12).at(72, 720).text("Hello, World!")
.highlight(1.0, 1.0, 0.0)
.done();
std::vector<std::uint8_t> bytes = builder.build();
Swift
import PdfOxide
let font = try EmbeddedFont.fromFile("DejaVuSans.ttf")
let builder = try DocumentBuilder.create()
try builder.registerEmbeddedFont("DejaVu", font)
let page = try builder.a4Page()
try page.font("DejaVu", 12).at(72, 720).text("Hello, World!")
.highlight(1.0, 1.0, 0.0)
.done()
let bytes = try builder.build()
Dart
import 'package:pdf_oxide/pdf_oxide.dart';
final font = EmbeddedFont.fromFile('DejaVuSans.ttf');
final builder = DocumentBuilder.create();
builder.registerEmbeddedFont('DejaVu', font);
builder.a4Page()
.font('DejaVu', 12.0).at(72.0, 720.0).text('Hello, World!')
.highlight(1.0, 1.0, 0.0)
.done();
final bytes = builder.build();
R
library(pdfoxide)
font <- pdf_embedded_font_from_file("DejaVuSans.ttf")
b <- pdf_builder_create()
pdf_builder_register_embedded_font(b, "DejaVu", font)
pg <- pdf_builder_a4_page(b)
pdf_page_font(pg, "DejaVu", 12)
pdf_page_at(pg, 72, 720)
pdf_page_builder_text(pg, "Hello, World!")
pdf_page_highlight(pg, 1.0, 1.0, 0.0)
pdf_page_done(pg)
bytes <- pdf_builder_build(b)
Julia
using PdfOxide
emb = embedded_font_from_file("DejaVuSans.ttf")
b = DocumentBuilder()
register_embedded_font(b, "DejaVu", emb)
pg = a4_page(b)
font(pg, "DejaVu", 12)
at(pg, 72, 720)
text(pg, "Hello, World!")
highlight(pg, 1.0, 1.0, 0.0)
done(pg)
bytes = build(b)
Zig
const pdf_oxide = @import("pdf_oxide");
const a = std.heap.page_allocator;
var font = try pdf_oxide.EmbeddedFont.fromFile("DejaVuSans.ttf");
var builder = try pdf_oxide.DocumentBuilder.create();
try builder.registerEmbeddedFont("DejaVu", &font);
var page = try builder.a4Page();
try page.font("DejaVu", 12);
try page.at(72, 720);
try page.text("Hello, World!");
try page.highlight(1.0, 1.0, 0.0);
try page.done();
const bytes = try builder.build(a);
Objective-C
#import "POXPdfOxide.h"
NSError *err = nil;
POXEmbeddedFont *font = [POXEmbeddedFont fromPath:@"DejaVuSans.ttf" error:&err];
POXDocumentBuilder *builder = [POXDocumentBuilder createWithError:&err];
[builder registerEmbeddedFont:@"DejaVu" font:font error:&err];
POXPageBuilder *page = [builder a4PageWithError:&err];
[page font:@"DejaVu" size:12 error:&err];
[page at:72 y:720 error:&err];
[page text:@"Hello, World!" error:&err];
[page highlightR:1.0 g:1.0 b:0.0 error:&err];
[page done:&err];
NSData *bytes = [builder buildWithError:&err];
Elixir
{:ok, font} = PdfOxide.font_from_file("DejaVuSans.ttf")
{:ok, db} = PdfOxide.builder()
:ok = PdfOxide.builder_register_embedded_font(db, "DejaVu", font)
{:ok, page} = PdfOxide.builder_a4_page(db)
:ok = PdfOxide.page_font(page, "DejaVu", 12)
:ok = PdfOxide.page_at(page, 72, 720)
:ok = PdfOxide.page_text(page, "Hello, World!")
:ok = PdfOxide.page_highlight(page, 1.0, 1.0, 0.0)
:ok = PdfOxide.page_done(page)
{:ok, bytes} = PdfOxide.builder_build(db)
完全な API リファレンス
DocumentBuilder
DocumentBuilder::new() – ビルダーの作成
let mut builder = DocumentBuilder::new();
.metadata(metadata) – ドキュメントメタデータの設定
use pdf_oxide::writer::DocumentMetadata;
let mut builder = DocumentBuilder::new()
.metadata(
DocumentMetadata::new()
.title("Report")
.author("Jane Smith")
.subject("Q4 Analysis")
.keywords("finance, quarterly")
.creator("MyApp")
);
.page(size) – ページの追加
ページにコンテンツを追加するための FluentPageBuilder を返します。完了したら .done() を呼び出します。
use pdf_oxide::writer::PageSize;
builder.page(PageSize::A4)
.at(72.0, 770.0)
.text("Hello")
.done();
.letter_page() / .a4_page() – 便利なページメソッド
builder.letter_page().text("US Letter page").done();
builder.a4_page().text("A4 page").done();
.build() – PDF バイト列の生成
let bytes: Vec<u8> = builder.build()?;
.save(path) – ビルドしてファイルに保存
builder.save("output.pdf")?;
.save_encrypted(path, user_pw, owner_pw) – AES-256 暗号化
v0.3.38 で追加。すべてのバインディングで利用可能です。
DocumentBuilder::new()
.a4_page().text("secret").done()
.save_encrypted("out.pdf", "user-pw", "owner-pw")?;
(DocumentBuilder()
.a4_page().text("secret").done()
.save_encrypted("out.pdf", "user-pw", "owner-pw"))
DocumentBuilder.Create()
.A4Page().Text("secret").Done()
.SaveEncrypted("out.pdf", "user-pw", "owner-pw");
その他に次も利用できます。メモリ内出力用の .to_bytes_encrypted(user_pw, owner_pw)、カスタムアルゴリズムと権限ごとのフラグを指定する .save_with_encryption(path, algorithm, permissions, user_pw, owner_pw)(Rust)。
DocumentMetadata
ドキュメントレベルのメタデータ用ビルダーです。
| メソッド | 説明 |
|---|---|
.title(s) |
ドキュメントのタイトルを設定 |
.author(s) |
ドキュメントの作成者を設定 |
.subject(s) |
ドキュメントの件名を設定 |
.keywords(s) |
ドキュメントのキーワードを設定 |
.creator(s) |
作成アプリケーションを設定 |
FluentPageBuilder
builder.page(size) から返されます。すべてのメソッドはチェーン用に self を返します(.done() を除く)。
テキストと配置
| メソッド | 説明 |
|---|---|
.at(x, y) |
カーソル位置を設定(左下からのポイント数) |
.text(s) |
現在のカーソル位置にテキストを追加 |
.heading(level, s) |
見出しを追加(1〜6、適切なフォントで) |
.paragraph(s) |
自動ワードラップ付きの段落を追加 |
.font(name, size) |
後続のテキストのフォントを設定 |
.text_config(config) |
テキスト設定全体を指定 |
.space(points) |
垂直方向の余白を追加 |
.horizontal_rule() |
水平方向の区切り線を追加 |
.element(elem) |
生の ContentElement を追加 |
.elements(vec) |
複数の生コンテンツ要素を追加 |
注釈
| メソッド | 説明 |
|---|---|
.link_url(url) |
直前のテキスト要素を URL にリンク |
.link_page(page_index) |
直前のテキストを内部ページにリンク |
.link_named(destination) |
名前付き送り先にリンク |
.highlight(color) |
直前のテキストをハイライト(RGB タプル) |
.underline(color) |
直前のテキストに下線 |
.strikeout(color) |
直前のテキストに取り消し線 |
.squiggly(color) |
直前のテキストに波線下線 |
.sticky_note(text) |
カーソル位置に付箋を追加 |
.sticky_note_with_icon(text, icon) |
特定のアイコン付きで付箋を追加 |
.sticky_note_at(x, y, text) |
特定の位置に付箋を追加 |
.stamp(stamp_type) |
カーソル位置にスタンプを追加 |
.stamp_at(rect, stamp_type) |
特定の矩形にスタンプを追加 |
.freetext(rect, text) |
フリーテキスト注釈を追加 |
.freetext_styled(rect, text, font, size) |
スタイル付きフリーテキスト注釈を追加 |
.watermark(text) |
ページ全体に斜めの透かしを追加 |
.watermark_confidential() |
プリセットの「CONFIDENTIAL」透かしを追加 |
.watermark_draft() |
プリセットの「DRAFT」透かしを追加 |
.watermark_custom(watermark) |
カスタム透かし注釈を追加 |
.add_annotation(annotation) |
任意の注釈タイプを追加 |
AcroForm ウィジェット
v0.3.38 ですべてのバインディングに追加されました。すべての位置はページの左下原点からの PDF ポイント単位です。
| メソッド | 説明 |
|---|---|
.text_field(name, x, y, w, h, default_value=None) |
単一行テキスト入力 |
.checkbox(name, x, y, w, h, checked) |
チェックボックスウィジェット |
.combo_box(name, x, y, w, h, options, selected=None) |
ドロップダウンセレクター |
.radio_group(name, buttons, selected=None) |
ラジオグループ。buttons は (export_value, x, y, w, h) のリスト |
.push_button(name, x, y, w, h, caption) |
ラベル付きのクリック可能なボタン |
(DocumentBuilder()
.a4_page()
.text_field("name", 150, 680, 200, 20, "Jane Doe")
.checkbox("subscribe", 72, 650, 15, 15, True)
.combo_box("country", 150, 620, 200, 20, ["US", "UK", "DE"], "US")
.radio_group("tier", [("free", 72, 590, 15, 15), ("pro", 120, 590, 15, 15)], "pro")
.push_button("submit", 72, 540, 80, 25, "Submit")
.done()
.save("form.pdf"))
グラフィックスプリミティブ
v0.3.38 ですべてのバインディングに追加されました。rect(x, y, w, h)(線のみ)、filled_rect(x, y, w, h, color)(RGB タプルで塗りつぶし)、line(x1, y1, x2, y2) です。これらは同じ FluentPageBuilder チェーンを経由し、フォームの背景、区切り線、シンプルな表の罫線には十分です。
パス/パターン/グラデーション/ExtGState を完全に制御するには、ContentStreamBuilder(Rust のみ — グラフィックス、パターン、シェーディング を参照)を使用してください。
.done() – ページの完了
制御を DocumentBuilder に戻します。
builder.page(PageSize::Letter)
.at(72.0, 720.0)
.text("Content")
.done(); // Back to builder
TextConfig
テキストレンダリングの設定です。
use pdf_oxide::writer::TextConfig;
let config = TextConfig {
font: "Times-Roman".to_string(),
size: 14.0,
align: TextAlign::Center,
line_height: 1.5,
};
| フィールド | 型 | デフォルト |
|---|---|---|
font |
String |
"Helvetica" |
size |
f32 |
12.0 |
align |
TextAlign |
Left |
line_height |
f32 |
1.2 |
PageSize
| バリアント | 幅 x 高さ(ポイント) |
|---|---|
Letter |
612 x 792 |
A4 |
595 x 842 |
Legal |
612 x 1008 |
A3 |
842 x 1190 |
Custom(w, h) |
カスタム寸法 |
応用例
注釈付きの複数ページドキュメント
use pdf_oxide::writer::{
DocumentBuilder, DocumentMetadata, PageSize, StampType
};
let mut builder = DocumentBuilder::new()
.metadata(
DocumentMetadata::new()
.title("Annotated Report")
.author("Review Team")
);
// Cover page
builder.page(PageSize::Letter)
.at(72.0, 600.0)
.font("Helvetica-Bold", 28.0)
.text("Annual Review 2025")
.font("Helvetica", 14.0)
.space(20.0)
.text("Prepared by the Review Team")
.watermark_draft()
.done();
// Content page with annotations
builder.page(PageSize::Letter)
.at(72.0, 720.0)
.heading(1, "Executive Summary")
.paragraph(
"Revenue increased 18% year-over-year, driven by expansion \
into new markets and strong retention rates."
)
.text("See full financial details")
.link_page(2) // Link to page 3 (0-indexed)
.space(12.0)
.heading(2, "Key Findings")
.text("Customer satisfaction reached an all-time high.")
.highlight((1.0, 1.0, 0.0)) // Yellow highlight
.sticky_note("Verify this claim with latest survey data")
.paragraph(
"Operating costs were reduced through automation initiatives, \
achieving a 15% improvement in operational efficiency."
)
.stamp(StampType::ForComment)
.done();
// Data page
builder.page(PageSize::Letter)
.at(72.0, 720.0)
.heading(1, "Financial Details")
.paragraph("Detailed breakdown of revenue by segment...")
.horizontal_rule()
.paragraph("North America: $82M (+12%)")
.paragraph("Europe: $41M (+28%)")
.paragraph("Asia-Pacific: $19M (+35%)")
.done();
builder.save("annotated_report.pdf")?;
精密なテキスト配置
use pdf_oxide::writer::{DocumentBuilder, PageSize};
let mut builder = DocumentBuilder::new();
builder.page(PageSize::Letter)
// Title at top center area
.at(200.0, 740.0)
.font("Helvetica-Bold", 20.0)
.text("Certificate of Completion")
// Recipient name
.at(200.0, 620.0)
.font("Times-Roman", 16.0)
.text("Awarded to: Jane Smith")
// Details at specific positions
.at(72.0, 500.0)
.font("Helvetica", 12.0)
.text("For successfully completing the Advanced Rust Programming course.")
.at(72.0, 450.0)
.text("Date: November 15, 2025")
.at(350.0, 450.0)
.text("Instructor: Dr. Alan Turing")
.horizontal_rule()
.at(72.0, 380.0)
.font("Helvetica", 9.0)
.text("Certificate ID: CERT-2025-00042")
.done();
builder.save("certificate.pdf")?;
関連ページ
- PdfBuilder フルエント API – PdfBuilder による高レベルな作成
- 注釈の作成 – すべての注釈タイプの詳細
- フォームフィールドの作成 – インタラクティブなフォームフィールドの追加
- 表のレンダリング – 表の作成