【VBA】ExcelファイルをPDFに一括変換する方法|フォルダ指定でまとめて保存(コピペOK)

VBA
スポンサーリンク
スポンサーリンク

この記事でできること

以前の自分は、毎月の月次報告を20ファイルくらい手作業でPDFにしていた。Excelを開いて、名前を付けて保存して、PDF選んで…を20回。金曜の午後がこれだけで消えていて、正直しんどかった。

この記事のVBAを使えば、指定フォルダ内のExcelファイルを一括でPDFに変換できる。1つずつ開いて保存する必要はない。マクロを実行するだけで、フォルダ内の全Excelファイルが自動でPDFになる。これを知ったとき、もっと早くやればよかったと本気で思った。

  • 対象:毎月の報告書や請求書を手作業でPDF化している人、VBAが初めての人
  • 所要時間:コピペ → 実行まで約5分(目安)

Dir関数を使ったファイル一覧の取得が初めての場合は、先に 【VBA】フォルダ内のファイル一覧を自動取得する方法 を読んでおくと理解しやすい。


完成イメージ(Before / After)

Before(実行前)

フォルダ内にExcelファイルが複数ある状態。PDFはまだない。


C:\報告書\
  ├── 2026年01月_売上報告.xlsx
  ├── 2026年02月_売上報告.xlsx
  └── 2026年03月_売上報告.xlsx

After(実行後)

同じフォルダにPDFファイルが自動生成される。


C:\報告書\
  ├── 2026年01月_売上報告.xlsx
  ├── 2026年01月_売上報告.pdf  ← 自動生成
  ├── 2026年02月_売上報告.xlsx
  ├── 2026年02月_売上報告.pdf  ← 自動生成
  ├── 2026年03月_売上報告.xlsx
  └── 2026年03月_売上報告.pdf  ← 自動生成

実行前の準備

バックアップを取る

対象フォルダ内のExcelファイルをフォルダごとコピーしてバックアップを取ること。VBAからファイルを開いて処理するため、万が一に備える。

Excelをマクロ有効ブック(.xlsm)で保存する

  1. 新しいExcelブックを開く(VBAを書く用のファイル)
  2. 「ファイル」→「名前を付けて保存」
  3. ファイルの種類を 「Excel マクロ有効ブック (*.xlsm)」 に変更して保存

.xlsx のままだとマクロが保存されない。必ず .xlsm にすること。

注意: VBAを書くExcelファイルと、PDF化したいExcelファイルは別。PDF化したいファイルは .xlsx のままでOK。

対象フォルダのパスを確認する

PDF化したいExcelファイルが入っているフォルダのパスを確認しておく。パスの調べ方:エクスプローラーでフォルダを開き、アドレスバーをクリックするとパスが表示される。


手順(コピペ → 実行まで約5分)

VBE(コードを書く画面)を開く

Alt + F11 キーを押すとVBE(Visual Basic Editor)が開く。

一般的にはAlt + F11で開けるが、企業のセキュリティ設定でVBAが無効化されている場合は、IT部門に確認すること。

標準モジュールを挿入する

  1. VBEのメニュー「挿入」→「標準モジュール」をクリック
  2. 右側に白い画面(コードウィンドウ)が表示される

コードを貼り付けて実行する

  1. 下の「コード(最小版)」をコピーして、コードウィンドウに貼り付ける
  2. コード内の folderPath を自分のフォルダパスに書き換える
  3. Alt + F8 を押す(または VBE上で F5
  4. 「ExcelToPDF」を選択して「実行」
  5. 処理が完了すると、件数がメッセージボックスに表示される

コード(最小版)– 同じフォルダにPDFを保存

まずはこれだけで動く。指定フォルダ内の .xlsx ファイルを、同じフォルダに .pdf として保存する。


Sub ExcelToPDF()

    Dim folderPath As String
    Dim fileName As String
    Dim pdfName As String
    Dim wb As Workbook
    Dim fileCount As Long

    ' --- ★ ここを自分のフォルダパスに書き換える ---
    folderPath = "C:\報告書\"

    ' フォルダパスの末尾に \ がなければ追加
    If Right(folderPath, 1) <> "\" Then folderPath = folderPath & "\"

    ' 画面更新を停止(高速化)
    Application.ScreenUpdating = False
    Application.DisplayAlerts = False

    fileCount = 0

    ' フォルダ内の .xlsx ファイルを順番に処理
    fileName = Dir(folderPath & "*.xlsx")

    Do While fileName <> ""

        ' Excelファイルを読み取り専用で開く
        Set wb = Workbooks.Open(folderPath & fileName, ReadOnly:=True, UpdateLinks:=0)

        ' PDFファイル名を生成(拡張子を .pdf に変換)
        pdfName = Left(fileName, InStrRev(fileName, ".") - 1) & ".pdf"

        ' PDF として保存
        wb.ExportAsFixedFormat _
            Type:=xlTypePDF, _
            Filename:=folderPath & pdfName, _
            Quality:=xlQualityStandard, _
            IncludeDocProperties:=False, _
            IgnorePrintAreas:=False, _
            OpenAfterPublish:=False

        ' ファイルを閉じる(保存しない)
        wb.Close SaveChanges:=False

        fileCount = fileCount + 1

        ' 次のファイルへ
        fileName = Dir()

    Loop

    ' 画面更新を再開
    Application.ScreenUpdating = True
    Application.DisplayAlerts = True

    MsgBox fileCount & " 件のExcelファイルをPDFに変換しました。", vbInformation

End Sub

コードの動作:

  1. 指定フォルダ内の .xlsx ファイルを Dir で順番に取得
  2. 各ファイルを読み取り専用で開く(元ファイルは変更されない)
  3. ExportAsFixedFormat でPDFとして保存(同じフォルダに同名 .pdf)
  4. ファイルを閉じて次のファイルへ
  5. 全ファイルの処理が終わったら件数を表示

フォルダパスについて: folderPath = "C:\報告書\" の部分を自分のフォルダパスに書き換える。パスの末尾には \ を付ける。

自分はこの最小版で十分だった。月次報告20ファイルが1分もかからず全部PDFになったときは感動した。

ネットワークドライブ(\\server\share\ のようなパス)で使う場合は、Dirの動作が不安定になることがある。その場合は下の実務版コードを使うこと。


コード(実務版)– 出力先フォルダ指定+ログ+エラースキップ

業務で使うなら、出力先フォルダを分けたい、.xlsm にも対応したい、エラーで止まらないようにしたい、という要望がある。処理ログをシートに記録する機能付き。

ファイル名を先に配列に格納してからループする方式は、フォルダ内のファイル一覧を自動取得する方法 で紹介した Dir関数の応用。Dirの内部状態がリセットされるリスクを回避できる。

ログシートのレイアウト:

A B C
1 ファイル名 結果 詳細
2 2026年01月_売上報告.xlsx OK 2026年01月_売上報告.pdf
3 破損ファイル.xlsx エラー ファイルを開けませんでした

Sub ExcelToPDFEx()

    Dim folderPath As String
    Dim outputPath As String
    Dim fileName As String
    Dim pdfName As String
    Dim wb As Workbook
    Dim ws As Worksheet
    Dim fso As Object
    Dim fileCount As Long
    Dim errCount As Long
    Dim logRow As Long
    Dim fileList() As String
    Dim i As Long
    Dim n As Long

    ' --- ★ ここを自分のフォルダパスに書き換える ---
    folderPath = "C:\報告書\"
    outputPath = "C:\報告書\PDF出力\"  ' 出力先フォルダ(なければ自動作成)

    ' フォルダパスの末尾に \ がなければ追加
    If Right(folderPath, 1) <> "\" Then folderPath = folderPath & "\"
    If Right(outputPath, 1) <> "\" Then outputPath = outputPath & "\"

    ' 出力先フォルダがなければ作成(FSO で安全にチェック)
    Set fso = CreateObject("Scripting.FileSystemObject")
    If Not fso.FolderExists(outputPath) Then
        fso.CreateFolder outputPath
    End If
    Set fso = Nothing

    ' --- ファイル名を先に配列に格納(Dir の安全対策) ---
    n = 0
    fileName = Dir(folderPath & "*.xls*")  ' .xlsx と .xlsm の両方に対応
    Do While fileName <> ""
        n = n + 1
        ReDim Preserve fileList(1 To n)
        fileList(n) = fileName
        fileName = Dir()
    Loop

    If n = 0 Then
        MsgBox "対象フォルダにExcelファイルが見つかりませんでした。" & vbCrLf & _
               folderPath, vbExclamation
        Exit Sub
    End If

    ' --- ログ用シートを準備 ---
    Set ws = ThisWorkbook.Worksheets(1)
    ws.Cells.Clear
    ws.Cells(1, 1).Value = "ファイル名"
    ws.Cells(1, 2).Value = "結果"
    ws.Cells(1, 3).Value = "詳細"
    logRow = 2

    ' 画面更新を停止(高速化)
    Application.ScreenUpdating = False
    Application.DisplayAlerts = False

    fileCount = 0
    errCount = 0

    ' --- ファイルを順番に処理 ---
    For i = 1 To n

        fileName = fileList(i)

        ' ログにファイル名を記録
        ws.Cells(logRow, 1).Value = fileName

        On Error GoTo ErrHandler

        ' Excelファイルを読み取り専用で開く
        Set wb = Workbooks.Open(folderPath & fileName, ReadOnly:=True, UpdateLinks:=0)

        ' PDFファイル名を生成(拡張子を .pdf に変換)
        pdfName = Left(fileName, InStrRev(fileName, ".") - 1) & ".pdf"

        ' PDF として保存
        wb.ExportAsFixedFormat _
            Type:=xlTypePDF, _
            Filename:=outputPath & pdfName, _
            Quality:=xlQualityStandard, _
            IncludeDocProperties:=False, _
            IgnorePrintAreas:=False, _
            OpenAfterPublish:=False

        ' ファイルを閉じる(保存しない)
        wb.Close SaveChanges:=False
        Set wb = Nothing

        ' ログに成功を記録
        ws.Cells(logRow, 2).Value = "OK"
        ws.Cells(logRow, 3).Value = pdfName

        fileCount = fileCount + 1
        On Error GoTo 0

NextFile:
        logRow = logRow + 1

    Next i

    ' 画面更新を再開
    Application.ScreenUpdating = True
    Application.DisplayAlerts = True

    MsgBox "完了" & vbCrLf & _
           "成功:" & fileCount & " 件" & vbCrLf & _
           "エラー:" & errCount & " 件" & vbCrLf & _
           "ログはシートに記録しました。", vbInformation

    Exit Sub

ErrHandler:
    ' エラーが出たファイルはスキップしてログに記録
    ws.Cells(logRow, 2).Value = "エラー"
    ws.Cells(logRow, 3).Value = Err.Description
    errCount = errCount + 1

    ' 開いたブックがあれば閉じる
    If Not wb Is Nothing Then
        wb.Close SaveChanges:=False
        Set wb = Nothing
    End If

    ' Application 設定を確実に復帰
    Application.ScreenUpdating = True
    Application.DisplayAlerts = True

    On Error GoTo 0
    Resume NextFile

End Sub

追加ポイント:

  • 出力先フォルダを別途指定(FileSystemObject.FolderExists で安全にチェック、なければ自動作成)
  • .xls* パターンで .xlsx と .xlsm の両方に対応
  • ファイル名を先に配列に格納してからループ(Dir の内部状態リセット問題を回避)
  • エラーが出たファイルはスキップして次のファイルへ進む
  • シートの A〜C 列に処理ログ(ファイル名・結果・詳細)を記録
  • エラーハンドラで Application.ScreenUpdating / DisplayAlerts を確実に復帰

よくある落とし穴5選

自分が初めてPDF一括変換を試したとき、印刷範囲を設定し忘れていた。上司に提出したら「全部白紙なんだけど?」と言われて血の気が引いた。原因はExcel側の印刷範囲が未設定で、空白ページだけがPDFに出力されていたこと。以来、PDF化の前に印刷プレビューを確認するのが習慣になった。

# 症状 原因 対策
1 PDFに空白ページが大量に含まれる Excelファイルに印刷範囲が設定されていない。または印刷範囲外のセルにデータが残っている PDF化する前に、各Excelファイルの印刷範囲を確認する。不要なセルのデータを削除しておく
2 「実行時エラー ‘1004’」でファイルが開けない ファイルが他のユーザーに開かれている、またはパスワードで保護されている 実務版コードを使えばエラーをスキップできる。共有フォルダのファイルは他の人が閉じてから実行する
3 一部のファイルがPDF化されない フォルダに .xlsm ファイルが混在しているが、最小版コードは .xlsx しか対象にしていない 実務版コードを使う(.xls* で .xlsx と .xlsm の両方に対応)
4 同名のPDFが上書きされる 同じフォルダに既にPDFがある状態で再実行した DisplayAlerts = False のため確認なしで上書きされる。上書きしたくない場合は、出力先フォルダを変えるか、ファイル名に日時を追加する
5 PDFのレイアウトがおかしい(列が切れる、文字が小さい) Excelの印刷設定(用紙サイズ、余白、倍率)が適切でない PDF化する前に、各Excelファイルで「印刷プレビュー」を確認して印刷設定を調整しておく

FAQ

Q1: 特定のシートだけPDF化したい

wb.ExportAsFixedFormatwb.Worksheets("Sheet1").ExportAsFixedFormat に変えれば、指定シートだけPDF化できる。シート名を自分の環境に合わせて書き換えること。

Q2: 複数シートを1つのPDFにまとめたい

ブック全体を ExportAsFixedFormat すれば、全シートが1つのPDFになる(最小版・実務版ともにこの動作)。自分も最初「シートごとに別PDFになるのでは?」と心配したが、デフォルトでブック全体が1PDFにまとまる。

Q3: PDF化した後にメールで送りたい

【VBA】ExcelからOutlookメールを自動作成する方法 を参照。.Attachments.Add でPDFファイルのパスを指定すれば添付できる。宛先リストと組み合わせれば、PDF添付メールの一括送信も可能。

Q4: PDF化と同時にファイル名を変えたい

pdfName の生成部分を変更すればよい。例:日付を先頭に付ける場合は pdfName = Format(Now, "yyyymmdd_HHmmss") & "_" & 元のファイル名 & ".pdf" とする。ファイル名の一括変更については 【VBA】ファイル名を一括変更(リネーム)する方法 も参考になる。

Q5: サブフォルダ内のファイルも対象にしたい

Dir関数はサブフォルダの再帰検索には対応していない。FileSystemObject を使った再帰処理が必要になるが、コードが複雑になるため記事の範囲外。ココナラで相談を推奨。


まとめ

この記事で、フォルダ内のExcelファイルを一括でPDFに変換できるようになった。

  • 最小版:指定フォルダ内の .xlsx → 同じフォルダに .pdf を保存
  • 実務版:出力先フォルダ指定+.xlsm対応+エラースキップ+処理ログ

重要なのは、PDF化する前に各Excelファイルの印刷設定を確認しておくこと。印刷範囲・用紙サイズ・余白がPDFのレイアウトにそのまま反映される。まず1ファイルだけテスト変換してから本番実行するのがおすすめ。

関連記事

次にやりたくなること


もっとカスタマイズしたい場合

「サブフォルダも含めて再帰的にPDF化したい」「特定のシートだけを個別PDFにしたい」「PDF化と同時にメール送信もしたい」など、業務に合わせたカスタマイズが必要な場合は、ココナラで相談できます。

相談時に以下の情報があるとスムーズです:

  • Excel のバージョン / OS
  • 対象フォルダの構成(サブフォルダの有無)
  • PDFの出力先と命名規則
  • 1回あたりの処理ファイル数(目安)

あわせて読みたい

コメント

タイトルとURLをコピーしました