今回はVBAを利用してHTMLを生成するテクニックを紹介
題材は先日紹介した、参照設定とCreateObjectの対応リスト - You.Activate
thom.hateblo.jp
このページはご覧いただくとわかるように、項目名は同じで内容だけ異なるものが複数回出てくる。
ひとつのオブジェクトの紹介は以下のHTMLで構成されている。
<h3>ファイルシステムオブジェクト</h3> <dl class="ProgIDList"> <dt>説明</dt><dd>ファイル・フォルダの生成・移動・削除やテキストファイルの生成、読み込みなどに使用</dd> <dt class="fl">ProgID</dt><dd>Scripting.FileSystemObject</dd> <dt class="fl">参照設定名</dt><dd>Microsoft Scripting Runtime</dd> <dt class="fl">ライブラリ名</dt><dd>Scripting</dd> <dt class="fl">オブジェクト名</dt><dd>FileSystemObject</dd> <dt>アーリーバインディング書式</dt> <dd class="code"><pre class="brush:vb toolbar:false"> Dim fso As Scripting.FileSystemObject Set fso = New Scripting.FileSystemObject </pre></dd> <dt>レイトバインディング書式</dt> <dd class="code"><pre class="brush:vb toolbar:false"> Dim fso As Object Set fso = CreateObject("Scripting.FileSystemObject") </pre></dd>
これをバカ正直にコピー&ペーストで編集しても良いのだけれど、いかんせん効率が悪い。
ということで、これもテンプレートを作ってVBAでやってしまおう。
※本来はDBにデータを格納してPHPで動的にページを生成するのがセオリーだが、たかだか1ページのために仕組みを作るのも面倒だしこれくらいなら得意のVBAで良いかなと。
まず、シートはこんな感じ。
薄い黄色で塗ってあるのがテンプレートで可変項目は$$$としている。
その右がデータ部で、1列がひとつのオブジェクト紹介。右へ右へとどんどんデータが続くイメージ。
ふつうはデータ方向は下なんだけど、HTMLのテンプレートは縦に書きたかったのでやむなく。
※もっとデータが多ければ、可変項目を「$$1$$」などとナンバリングしたテンプレートを別シートに作り、データは1行1レコードとする方法もある。
コードは以下の通り。シートモジュールに直接貼り付けて実行する。
Option Explicit Sub HTMLOutput() Const MAX_ROW = 19 Const START_COLUMN = 3 Const END_COLUMN = 5 Dim template: template = Range("B1:B" & MAX_ROW).Value Dim j, i For j = START_COLUMN To END_COLUMN Dim data: data = Range(Cells(1, j), Cells(MAX_ROW, j)).Value For i = 1 To MAX_ROW Debug.Print Replace(template(i, 1), "$$$", data(i, 1)) Next Next End Sub
実行するとイミディエイトウインドウにHTMLコードが生成されるので、あとは切り取ってエディタに貼り付ければ完成。
最大行、開始列、終了列はハードコーディングしてるので使用時は定数を変更する必要あり。自動取得も簡単だけれど、今回は使い捨てマクロなのでそこは適当に。。
やってることは単純で、テンプレート部とデータ部をそれぞれ別の二次元配列に入れ、あとは1行ずつ$$$をリプレースしながらイミディエイトウインドウに出力している。
ちなみにイミディエイトウインドウは最大200行までしか出力できないので、一気に大量のデータをさばきたいときは変数に入れて最後にクリップボードに送るか、テキストファイルとして出力するなどの工夫が必要。まあ本格的にデータ扱うなら、PHP等で仕組み化した方が良いと思うが。
上記マクロで使っているセル範囲を配列に転記するテクニックはこちらに詳しく書いた。
thom.hateblo.jp