【実務・中級編】【プロフェッショナル】Application.HWNDを利用し、PowerPointがスライドショー(SlideShowWindows)を実行している最中に、Windows APIでタスクバーを完全に非表示にし、キオスク端末のような完全フルスクリーン表示を強制するシステム制御 – PowerPoint VBA解析バイブル

スポンサーリンク

展示会や店頭サイネージ、あるいは企業の受付。PowerPointを「ただのスライド」ではなく、「専用のキオスク端末」として機能させなければならない局面がある。

しかし、現場のエンジニアを悩ませるのはWindowsというOSの「お節介」だ。スライドショーを実行していても、何かの拍子にタスクバーが最前面に浮上したり、通知ポップアップが画面を汚したりする。標準の「キオスクモード(ppShowTypeKiosk)」設定だけでは、プロの要求する「完全な静寂」は手に入らない。

今回は、PowerPoint VBAからWindows APIの深淵に触れ、OSのUI要素を物理的に制御して「完全なるフルスクリーン」を強制する、プロダクションレベルの実装技法を伝授する。

—

1. なぜ標準機能では不十分なのか

PowerPointの`SlideShowSettings.ShowType = ppShowTypeKiosk`は、エスケープキーによる終了を無効化するが、Windowsのシェル(Explorer.exe)そのものを制御するわけではない。

  • タスクバーの侵入: 他のプロセスが通知を発行した瞬間、タスクバーがスライドの背後から這い上がってくる。
  • 誤操作の脆弱性: WindowsキーやCtrl+Escといったシステムショートカットを完全に封じ込めるには、ウィンドウハンドル(HWND)レベルでの制御が不可欠だ。

プロフェッショナルの仕事とは、ユーザーに「背後でWindowsが動いている」ことを一瞬たりとも悟らせないことにある。

—

2. アーキテクチャ:Win32 APIによるシェル制御

我々がターゲットにするのは、Windowsのタスクバーを司るウィンドウクラス `Shell_TrayWnd` だ。これを`FindWindow`で捕捉し、`ShowWindow`で描画状態を操作する。

ここで重要なのは、「オブジェクトのライフサイクル管理」だ。タスクバーを消したままVBAが異常終了すれば、その端末の操作性は著しく損なわれる。エラーハンドリングと、プログラム終了時の「確実な復元(Restore)」をペアで設計するのが鉄則だ。

64bit/32bit両対応の宣言部

現代のビジネス環境ではOfficeの64bit化が進んでいる。`PtrSafe`属性と`LongPtr`型を使い分け、環境に依存しない堅牢なコードを書く必要がある。

—

3. 実装:プロダクションコード例

以下のコードは、標準モジュールに配置して使用する。単なるコピペ用ではなく、保守性を高めるためにカプセル化を意識した設計にしている。

Option Explicit

‘ — Win32 API Declarations —
If VBA7 Then
‘ 64bit環境用
Private Declare PtrSafe Function FindWindow Lib “user32” Alias “FindWindowA” ( _
ByVal lpClassName As String, ByVal lpWindowName As String) As LongPtr
Private Declare PtrSafe Function ShowWindow Lib “user32” ( _
ByVal hwnd As LongPtr, ByVal nCmdShow As Long) As Long
Else
‘ 32bit環境用
Private Declare Function FindWindow Lib “user32” Alias “FindWindowA” ( _
ByVal lpClassName As String, ByVal lpWindowName As String) As Long
Private Declare Function ShowWindow Lib “user32″ ( _
ByVal hwnd As Long, ByVal nCmdShow As Long) As Long
End If

‘ ShowWindow Constants
Private Const SW_HIDE As Long = 0
Private Const SW_SHOW As Long = 5

‘ — Taskbar Control Logic —

”’

”’ Windowsタスクバーの表示・非表示を切り替える
”’

”’ Trueで見表示、Falseで非表示 Public Sub SetTaskbarVisibility(ByVal isVisible As Boolean)
Dim taskbarHwnd As LongPtr

‘ タスクバーのウィンドウハンドルを取得
taskbarHwnd = FindWindow(“Shell_TrayWnd”, vbNullString)

If taskbarHwnd <> 0 Then
If isVisible Then
ShowWindow taskbarHwnd, SW_SHOW
Else
ShowWindow taskbarHwnd, SW_HIDE
End If
Else
Debug.Print “Error: タスクバーのハンドル取得に失敗しました。”
End If
End Sub

‘ — SlideShow Control Logic —

”’

”’ キオスクモードでのスライドショー開始
”’

Public Sub StartProfessionalKiosk()
On Error GoTo ErrorHandler

‘ 1. タスクバーを完全に隠蔽
SetTaskbarVisibility False

‘ 2. スライドショーの設定(キオスクモード)
With ActivePresentation.SlideShowSettings
.ShowType = ppShowTypeKiosk
.LoopUntilStopped = msoTrue
.Run
End With

Exit Sub

ErrorHandler:
‘ 異常終了時も必ずタスクバーを復元する
SetTaskbarVisibility True
MsgBox “スライドショー開始時にエラーが発生しました: ” & Err.Description, vbCritical
End Sub

”’

”’ スライドショー終了と環境復元
”’

Public Sub TerminateProfessionalKiosk()
‘ スライドショーを停止
On Error Resume Next
ActivePresentation.SlideShowWindow.View.Exit
On Error GoTo 0

‘ タスクバーを復元
SetTaskbarVisibility True
End Sub

—

4. チーフアーキテクトによる設計の要点

① ライフサイクルのフック

上記のコードをボタンから呼び出すだけでは不十分だ。ユーザーが強引にスライドを閉じた場合や、予期せぬクラッシュに備え、クラスモジュールを用いたイベント監視を推奨する。
`Application.OnSlideShowTerminate` イベントを捕捉し、そこで `SetTaskbarVisibility True` を呼び出すのが、プロの設計だ。

② ファイル/DB連携時の注意点

キオスク端末で外部データ(ExcelやSQL Server)と連携する場合、非同期処理によるフォーカス遷移に注意せよ。外部通信中にOSが「応答なし」と判断してタスクバーを強制表示させることがある。通信処理は最小限のタイムアウトを設定し、DoEventsを適切に配置してUIスレッドを死守すること。

③ HWNDの重要性

`Application.HWND` を利用すれば、PowerPoint自体のウィンドウを最前面に固定(TopMost)することも可能だ。今回のタスクバー隠蔽と組み合わせれば、もはやその端末は「Windowsマシン」ではなく「専用サイネージ機」へと昇華する。

—

5. 運用上の警告

この手法は「極めて強力」である。開発中に誤ってタスクバーを非表示にしたままコードを止めてしまった場合は、以下の手順で復旧することを覚えておくように。

1. `Ctrl + Shift + Esc` でタスクマネージャーを起動
2. 「新しいタスクの実行」から `explorer.exe` を入力して実行(または再起動)
3. あるいは、VBAのイミディエイトウィンドウで `SetTaskbarVisibility True` を手動実行

結論:OSを支配してこそプロの自動化

標準機能の範疇で苦労するのは、一般のオペレーターの仕事だ。我々エンジニアの仕事は、APIという裏口からシステムを掌握し、クライアントに「魔法」を見せることにある。

今回紹介したタスクバー制御は、その第一歩に過ぎない。オブジェクトモデルの制約を超え、WindowsというプラットフォームそのものをPowerPointの一部として扱う視点を持て。それが、真の業務自動化エンジニアへの道である。

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