勉強したことのメモ

Webエンジニア / プログラマが勉強したことのメモ。

JavaScriptにて領収書等のテンプレートHTMLページをPDFファイル化させる方法(html2pdf)

JavaScriptにてhtml2pdfというライブラリを使用することでHTML / CSSで作成したページをPDFファイルとしてダウンロードできるらしい。実際にありそうなのは領収書等のテンプレートファイルをPDFダウンロードさせるような形になると思うのでその方法をメモ。

 

html2pdf

公式サイト

https://ekoopmans.github.io/html2pdf.js/

CDN

CDNで使う場合は以下を記述する。

<script src="https://cdnjs.cloudflare.com/ajax/libs/html2pdf.js/0.8.0/html2pdf.bundle.min.js"></script>

異なるバージョンを利用したい場合は以下から探す。

https://cdnjs.com/libraries/html2pdf.js

 

テンプレートファイル

公開は以下サイトの領収書テンプレートを利用させていただいた。

https://www.review-rank.net/?p=15883

 

サンプル

https://taitan916.info/sample/html2pdf/

 

ソースコード

<!doctype html>
<html lang="ja">
<head>
<meta charset="utf-8">
<title>html2pdf サンプル</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<style type="text/css">
<!--
* {
    margin:0;
    padding:0;
    word-wrap: break-word;
    overflow-wrap: break-word;
    box-sizing: border-box;
    font-family: "游明朝", YuMincho, "Hiragino Mincho ProN W3", "ヒラギノ明朝 ProN W3", "Hiragino Mincho ProN", "HG明朝E", "MS P明朝", "MS 明朝", serif;
}
#container {
    margin:0px auto 0 auto;
    border:3px solid #000;
    text-align:center;
    margin:1em 1em;
    padding:2em 0;
    max-width:820px;
}
.inner {
    padding-left:2em;
    padding-right:2em;
}
#flexbox {
    display: -webkit-flex;
    display: flex;
    -webkit-justify-content: space-between;
    justify-content: space-between;
}
/* 領収書 */
#flexbox div:nth-of-type(1) {
    font-size:1.4em;
    letter-spacing:1em;
}
/* 〇〇様 */
#flexbox div:nth-of-type(2) {
    font-size:1.4em;
    margin:auto 0 0 auto;
    padding-right:1em;
}
/* No. */
#flexbox div:nth-of-type(3) {
    font-size:0.7em;
    flex-basis:10em;
    margin:auto 0 0 0;
    border-bottom:1px solid #000;
    text-align:left;
}
/* 料金欄 */
#price {
    margin:0.5em 0 0;
    background:#eee;
    text-align:center;
    font-size:1.4em;
    letter-spacing:1em;
    line-height:2em;
}
#centerbox {
    width:60%;
    margin:0 auto;
}
/* 但し書き */
#proviso {
    margin-top:0.5em;
    font-size:0.8em;
    text-align:left;
}
/* 日付 */
#date {
    font-size:0.8em;
    text-align:right;
}

#flexlist {
    display: -webkit-flex;
    display: flex;
    margin-top:1em;
}
/* 収入印紙 */
#stamp {
    display: -webkit-flex;
    display: flex;
    -webkit-justify-content: center;
    justify-content: center;
    -webkit-align-items: center;
    align-items: center;
    -webkit-flex-wrap: wrap;
    flex-wrap: wrap;
    width:5em;
    height:6em;
    border:1px solid #000;
    list-style-type:none;
    font-size:0.8em;
}
#stamp li {
    width:50%;
}
/* 内訳・税抜金額・消費税 */
#items {
    display: -webkit-flex;
    display: flex;
    -webkit-justify-content: space-between;
    justify-content: space-between;
    -webkit-align-items: flex-start;
    align-items: flex-start;
    -webkit-flex-direction: column;
    flex-direction: column;
    font-size:0.8em;
    text-align:left;
    margin:0 0 0 2em;
    list-style-type:none;
    height:6em;
}
#items li {
    width:20em;
    border-bottom:1px solid #000;
}
-->
</style>
</head>
<body>
    <div id="container">
        <div id="flexbox" class="inner">
            <div>領収書</div>
            <div>hogehoge様</div>
            <div>No.123456789</div>
        </div>
        <div id="price">\110,000</div>
        <div id="centerbox">
            <div id="proviso">但</div>
            <div id="date">2024年1月31日 上記正に領収いたしました。</div>
        </div>
        <div id="flexlist" class="inner">
            <ul id="stamp">
                <li>収</li>
                <li>入</li>
                <li>印</li>
                <li>紙</li>
            </ul>
            <ul id="items">
                <li>内訳</li>
                <li>税抜金額 \100,000</li>
                <li>消費税等 \10,000</li>
            </ul>
        </div>
    </div>
    <div>
        <button id="pdf_dl">PDFダウンロード</button>
    </div>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/html2pdf.js/0.8.0/html2pdf.bundle.min.js"></script>
    <script>
    document.querySelector("#pdf_dl").addEventListener("click", () => {
        const container = document.querySelector("#container");
        const filename = "sample.pdf";
        html2pdf(container).save(filename);
    });
    </script>
</body>
</html>

 

所感

メリットとしてはPHPが利用できない環境(ASP内のページ等)でも使えるという点と、HTMLのページが割と綺麗に反映されるという点。デメリットとしては画像扱いになるようでPDF内で文字列のコピーや検索ができない点。

「PHPが利用できない環境(ASP内のページ等)でも使える」というのが個人的には大きいメリットなので引き出しとして覚えておきたい。

 

参考サイト

https://zenn.dev/collabostyle/articles/e3e1d693e4a19d

 - JavaScript

  関連記事

バニラJavaScriptでリッチなセレクトメニュー(プルダウン)を実装できる「Choices.js」の利用方法

サジェストや複数選択等、機能付きのセレクトメニュー(プルダウン)を実装する際、今 ...

JavaScriptでオブジェクトをzlib圧縮してCookieに保存できる「zcookies」ライブラリの利用方法

あるシステムでCookieを保存している部分があった。ただ、日本語を保存している ...

表示範囲を自由に変更可能な折れ線グラフが表示できるJSライブラリ amCharts の使用方法

どこかのサイトを閲覧していた際に、恐らくはJavaScriptのライブラリで描写 ...

JavaScriptで画像読み込み完了のタイミングを検知する「imagesLoaded」ライブラリの利用方法

大き目のサイズの画像をページに設置すると読み込み完了まで時間がかかる。その画像が ...

ブラウザ開発者ツールの起動を検出しソースコード変更やリダイレクト設定できる「console-ban」ライブラリの利用方法

他サイトのソースコードを拝見するため開発者ツールを開こうとすると、偶に「デバッガ ...