教えて!ExcelVBA!

ExcelVBAの基礎知識・書き方について紹介します。

【ExcelVBA API操作】アプリケーションの重複起動を回避(FindWindow)する方法を教えて!

f:id:m_kbou:20210516121936p:plain

アプリケーションが起動しているかを確認するWindowsAPI関数(FindWindow)について紹介します。FindWindowを使用する事でアプリケーションの重複起動を回避する事も可能です。

 

 

構文

記述方法は以下の通りとなります。

(API定義)

Declare Function FindWindow Lib "user32" Alias "FindWindowA" (ByVal lpClassName As String, ByVal lpWindowName As String) As Long

----------------------------------------

(VBA記述)

FindWindow(lpClassName, lpWindowName)

[説明]:

アプリケーションの重複起動を回避するAPI関数はFindWindow関数となります。VBAから呼び出して使用する場合には、

---------------------------------

Declare Function FindWindow Lib "user32" Alias "FindWindowA" (ByVal lpClassName As String, ByVal lpWindowName As String) As Long

---------------------------------

をプロシージャ外で宣言します。

引数であるlpClassNameにはアプリケーションのウィンドウクラス名を指定し、lpWindowNameにはウィンドウ名を指定します。lpClassNameで指定するウィンドウクラス名については、以下にプリケーションとウィンドウクラス名の対比形式で幾つか紹介しておきます。また、lpWindowNameについては固定値で「vbNullString」をセットします。FindWindow関数を実行すると戻り値として「0」又は「0以外」が返ります。「0」の場合は指定したウィンドウクラス名のアプリケーションが起動していない状態となり、「0以外」の場合は起動している状態(ウィンドウハンドル値の取得に成功)となります。

【アプリケーション(ウィンドウクラス名)】
・Access(OMain)
・Excel(XLMAIN)
・Word(OpusApp)
・PowerPoint(PP10FrameClass)
・Internet Explorer(IEFrame)
・Visual Basic Editor(wndclass_desked_gsk)
・エクスプローラ(ExploreWClass)
・メモ帳(Notepad)
・ワードパッド(WordPadClass)
・電卓(SciCalc)
・ペイント(MSPaintApp)

 

使い方

使用方法について説明します。 

[プログラミング例]:

Declare Function FindWindow Lib "user32" Alias "FindWindowA" (ByVal lpClassName As String, ByVal lpWindowName As String) As Long

Sub アプリケーションの重複起動を回避する()

  '↓処理①
  Dim ウィンドウ As Long

  '↓処理②
  ウィンドウ = FindWindow("Notepad", vbNullString)
  If (ウィンドウ = 0) Then
    Shell "C:\Windows\System32\notepad.exe", vbNormalFocus
  Else
    MsgBox "メモ帳は既に起動されています。"
  End If

End Sub

処理の流れは以下の通りとなります。

[処理①]:変数定義
ウィンドウを格納する変数定義となります。

[処理②]:FindWindowによるアプリケーション重複起動回避
WindowsAPI関数であるFindWindowを使用したアプリケーション重複起動の回避判定となります。各引数には以下の内容をセットして処理を実行します。
・lpClassName・・・ウィンドウクラス名をセットします。
        ※今回はメモ帳を判定するため「"Notepad"」をセットしました。
・lpWindowName・・・ウィンドウ名をウィンドウ名をセットします。
        ※「vbNullString」(固定値)をセットします。
実行すると戻り値として「0」又は「0以外」が返されます。「0」の場合は未だメモ帳が起動していない状態となるため、メモ帳を起動(Shell関数を使用した起動)します。「0以外」の場合はメモ帳が既に起動している状態となるため、MsgBoxで”メモ帳は既に起動されています。”が表示されます。

f:id:m_kbou:20210523001450p:plain

※上記のプログラミング例は、VBE(VBA記述画面)に記述しないと実行ができません。VBEの開き方についてはこちらを参考にして下さい。

[実行例]:

(例1)既にアプリケーション(メモ帳)が起動している場合

(事前準備)

事前にメモ帳を開きます。(※タスクバーを確認するとメモ帳が起動している事がわかります。)

f:id:m_kbou:20210516170748p:plain

①<実行>ボタンをクリックします。<実行>ボタンには上記のプログラミング例のプログラムが登録されています。(※ボタンの作り方やボタンにプログラムを割り当てるにはこちらを参考にして下さい。)

f:id:m_kbou:20210516165906p:plain

②既にメモ帳が開いているため、MsgBoxで「メモ帳は既に起動されています。」が表示されます。

f:id:m_kbou:20210516165920p:plain

(例2)アプリケーション(メモ帳)が起動していない場合

(事前確認)

メモ帳が開いていない事を確認します。(※タスクバーを確認するとメモ帳が起動していない事がわかります。)

f:id:m_kbou:20210516170856p:plain

①<実行>ボタンをクリックします。<実行>ボタンには上記のプログラミング例のプログラムが登録されています。(※ボタンの作り方やボタンにプログラムを割り当てるにはこちらを参考にして下さい。)

f:id:m_kbou:20210516165937p:plain

②未だメモ帳が開いていないため、メモ帳が起動します。 

f:id:m_kbou:20210516165951p:plain

[サンプル]:

上記で説明したファイルをダウンロードできます。ご自由にお使い下さい。

drive.google.com

アプリケーションの重複起動を回避する方法についての説明は以上です。

 

おわりに

今回はWindowsAPI関数によるアプリケーションの重複起動を回避する方法について説明しました。是非参考にして下さい。