2017-01-24 12 views
1

Excelファイルにマスターマクロがあり、別のExcelファイル 'file B'を開く 'file A'があります。開いていると、アドインはデータを「ファイルB」にインポートします。アドインのインポートが完了したら、「ファイルB」を閉じたいと思っています。そのための最良の方法を探しています。プログラムでMsgBoxを閉じる

「ファイルB」(アドインを自動的に起動する)とファイルを閉じるコードを記述しましたが、アドインが終了するとMsgBoxが開き、ユーザーに通知されます。私は内部プロセスを完全に自動化しようとしているので、MsgBoxをプログラムで却下するのが理想的です。

MsgBoxをVBAで閉じることはできますか?私はVBAでTimed MsgBoxesを作成できますが、このMsgBoxを作成していないことを認識しています(アドインがあります)。私はちょうどそれを却下したい。 Wordファイルを作成し、必要に応じてマクロを呼び出すことはできますが、SendKeysを使用しない方が好きです。以来

+0

どのようなアドインですか?あなたはそれが呼び出される方法を変更する方法がありませんか? –

+0

私はタイマーやオープン時に手動でアドインを呼び出すことができます(すべての設定を通じて、私はVBAから直接対話できません) –

答えて

0

同じコンテキストで実行し、Excel/VBA「インを追加」、我々はそれを起動することはできませんし、各VBAアプリケーションがシングルスレッドのプロセスであるため、同じ VBAアプリケーション内でのメッセージボックスを監視。しかし、幸いにも、異なるVBAアプリケーションが異なるコンテキストで実行されるため、並列に実行できるという事実を利用できるソリューションがあります。

私の提案する解決策は、そのメッセージボックスの監視と終了専用のMS-Word文書を作成することです。監視コードとアドインのコードを別々のコンテキストで並行して実行するには、Word(または他のオフィスアプリケーション)でこれが必要です。

1- mboxKiller.docmという名前のWordマクロを有効にするドキュメントを作成し、それをいくつかのフォルダに配置します。私の例ではC:\SOです。 ThisDocumentにこのコードを配置し、保存します。

Private Declare PtrSafe Function FindWindow Lib "user32" Alias "FindWindowA" (ByVal lpClassName As String, ByVal lpWindowName As String) As Long 
Private Declare PtrSafe Function SendMessage Lib "user32" Alias "SendMessageA" (ByVal hwnd As Long, ByVal wMsg As Long, ByVal wParam As Long, ByVal lParam As Long) As Long 

Public Sub WaitAndKillWindow() 
    On Error Resume Next 
    Dim h As Long: h = FindWindow(vbNullString, "Microsoft Excel") 
    If h <> 0 Then SendMessage h, 16, 0, 0 ' <-- WM_Close 
    Application.OnTime Now + TimeSerial(0, 0, 1), "WaitAndKillWindow" 
End Sub 

Private Sub Document_Open() 
    WaitAndKillWindow 
End Sub 

2 - ExcelワークブックのVBAで、クラスモジュールを作成し、このコードでmboxKillerの名前:

Private killerDoc As Object 

Private Sub Class_Initialize() 
    On Error Resume Next 
    Set killerDoc = CreateObject("Word.Application").Documents.Open(Filename:="C:\SO\mboxKiller.docm", ReadOnly:=True) 
    If Err.Number <> 0 Then 
     If Not killerDoc Is Nothing Then killerDoc.Close False 
     Set killerDoc = Nothing 
     MsgBox "could not lauch The mboxKiller killer. The message-box shall be closed manuallt by the user." 
    End If 
End Sub 

Private Sub Class_Terminate() 
    On Error Resume Next 
    If Not killerDoc Is Nothing Then killerDoc.Application.Quit False 
End Sub 

3 - テストと使用方法。通常のクラスモジュールでは、次のコードを配置して手順をテストします。

Sub Test() ' <-- run this for testing after finishing the setup 
    Dim killer: Set killer = New mboxKiller 
    simulateAddin 
    simulateAddin 
    simulateAddin 
End Sub 

' Procedure supposed to do some calculation then display a message box 
Private Sub simulateAddin() 
    Dim i As Long 
    For i = 0 To 1000: DoEvents: Next ' simulates some calculations 
    MsgBox "This is a message box to simulate the message box of the addin." & VbCrLf & _ 
    "It will be automatically closed by the Word app mboxKiller" 
End Sub 
+0

これは別のウィンドウではなくMsgBoxを含むことが分かりました。その上でFindWindowを使用しないでください。あなたがMsgBoxesをプログラムで却下できるかどうかを解明できるかどうかを確認するには、 –

+0

私はwordからメッセージボックスを開始し、VBA/Excelからこれを閉じることができます: 'h = WaitMyWindow(" Microsoft Word "、10) h>> 0の場合SendMessage h、16、0、0'(ps * Microsoft Word *はメッセージボックスウィンドウのタイトル)。 –

+0

WaitMyWindow関数が実行されている間、他のすべてのVBAコードを一時停止します。私は私の最新の試みを表示するために私の質問を更新しました –

関連する問題