【実務・中級編】【初心者】開いているすべてのプレゼンテーションを対象に、未保存の変更を確認しながら一括で別名保存する「一斉退避」マクロ – PowerPoint VBA解析バイブル

スポンサーリンク

PowerPoint VBAを掌握せよ:業務を止める「保存の迷宮」を脱出する一斉退避スクリプト

業務が佳境に入ると、デスクトップには数え切れないほどのプレゼンテーションが散らばる。一つひとつ開き、名前を付け、保存先を選び、閉じる……。この「お片付け」に時間を溶かすのは、プロフェッショナルの仕事ではない。

今回は、開いているすべてのプレゼンテーションを安全かつ高速にアーカイブする「一斉退避マクロ」を伝授する。単なるコードの羅列ではない。「なぜVBAで事故が起きるのか」という本質的な設計思想から解説しよう。

—

1. なぜ「単純なループ」で事故が起きるのか

VBAで開いている全プレゼンを操作する際、多くの初心者は `For Each` ループを使い、その中で `SaveAs` を実行する。だが、これには大きな落とし穴がある。

1. コレクションの動的変更: 保存処理でファイルがアクティブ化される際、意図せずコレクションの順序が揺らぐリスクがある。
2. パスの未定義: 新規作成しただけのプレゼン(「プレゼンテーション1」など)には `Path` が存在しない。これを考慮せず保存しようとすると、例外が発生して処理が止まる。
3. ユーザーの確認ダイアログ: `SaveAs` のたびに「上書きしますか?」と聞かれては、自動化の意味がない。

これらを解決するのが、「例外を握りつぶすのではなく、状態を先回りして検証する」というエンジニアリングの基本だ。

—

2. 実装:堅牢な一斉退避スクリプト

以下のコードは、単に保存するだけではない。「フォルダが存在しなければ生成する」「ファイル名を一意に保つ」といった、実務で必須の要件を組み込んでいる。

Option Explicit

‘ ———————————————————
‘ プレゼンテーション一斉退避メイン処理
‘ ———————————————————
Public Sub ArchiveAllPresentations()
Dim ppt As Presentation
Dim saveDir As String
Dim fileName As String
Dim fso As Object

‘ アーカイブ先の定義(環境に合わせて変更してください)
saveDir = Environ(“USERPROFILE”) & “\Desktop\Archive_” & Format(Now, “yyyyMMdd_HHmm”)

‘ ファイルシステムオブジェクトの生成
Set fso = CreateObject(“Scripting.FileSystemObject”)

‘ 保存先ディレクトリの作成
If Not fso.FolderExists(saveDir) Then
fso.CreateFolder (saveDir)
End If

‘ 全ての開いているプレゼンテーションをループ
‘ ※逆順ループ(Count To 1)は、コレクション変更時の安全性を高める定石
Dim i As Long
For i = Application.Presentations.Count To 1 Step -1
Set ppt = Application.Presentations(i)

‘ パスが空(未保存)の場合はファイル名に現在時刻を付与して衝突を防ぐ
If ppt.Path = “” Then
fileName = saveDir & “\Untitled_” & i & “_” & Format(Now, “HHmmss”) & “.pptx”
Else
fileName = saveDir & “\” & fso.GetFileName(ppt.FullName)
End If

‘ 警告なしで保存(ppSaveAsOpenXMLPresentation = 24)
‘ ※必要に応じて拡張子やフォーマットを調整すること
On Error Resume Next ‘ 予期せぬエラーで停止しないための防壁
ppt.SaveCopyAs fileName

If Err.Number <> 0 Then
Debug.Print “Failed to save: ” & ppt.Name & ” Error: ” & Err.Description
Err.Clear
Else
Debug.Print “Saved: ” & fileName
End If
On Error GoTo 0
Next i

MsgBox “全プレゼンテーションの退避が完了しました。”, vbInformation
End Sub

—

3. このコードを「現場の武器」にするための知見

1. `SaveCopyAs` を選択する理由

今回のスクリプトで `SaveAs` ではなく `SaveCopyAs` を採用したのには意図がある。`SaveAs` は対象のドキュメント自体のパスを書き換えてしまう。作業中に「元のファイルを書き換えたくない」というケースが多いため、「別名でコピーを保存し、作業中の状態はそのまま維持する」挙動こそが、現場での安全性を担保する。

2. 逆順ループの哲学

`For i = Application.Presentations.Count To 1 Step -1` としているのは、万が一ループ内でファイルを閉じる処理を追加したくなった際、インデックスのズレによる `Runtime Error` を防ぐためだ。これはVBAに限らず、コレクションを操作する際の鉄則である。

3. エラーハンドリングの境界線

`On Error Resume Next` を乱用するのは悪手だが、今回のように「どれか一つが失敗しても他を止めない」という一括処理では、適切に使用する必要がある。その代わり、`Debug.Print` を用いて、どのファイルでエラーが起きたのかをイミディエイトウィンドウに記録する。「動かないこと」より「どこで止まったか分からないこと」の方が、業務自動化においては遥かに罪深い。

—

最後に:ツールは作って終わりではない

このスクリプトは、あなたのデスクトップという「カオス」を解消する第一歩に過ぎない。もしあなたが、このコードをベースに「特定の命名規則で自動保存させたい」「PDF化を同時に行いたい」という欲求を持ったなら、それはエンジニアとして成長している証拠だ。

PowerPoint VBAは古い言語だが、その分、仕様は極めて安定している。この「お片付け」スクリプトをマスターし、次はプレゼン生成そのものを自動化する領域へ踏み込んでほしい。

準備はいいか。コードをコピーし、即座に実行せよ。あなたの貴重な時間は、クリック作業ではなく、価値あるアウトプットのために使うべきだ。

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