Microsoft Excel

Herbers Excel/VBA-Archiv

Informationen und Beispiele zum Thema MsgBox
BildScreenshot zu MsgBox MsgBox-Seite mit Beispielarbeitsmappe aufrufen
Informationen und Beispiele zum Thema Frame
BildScreenshot zu Frame Frame-Seite mit Beispielarbeitsmappe aufrufen

Makro mit App.OnTime läuft nicht

Betrifft: Makro mit App.OnTime läuft nicht von: Albert
Geschrieben am: 01.11.2012 15:48:47

Hallo Fachleute,

ich habe folgendes Makro von Nepumuk zur Verfügung gestellt bekommen:

Option Explicit
Private Declare Function EnumWindows Lib "user32.dll" ( _
ByVal lpEnumFunc As Long, _
ByVal lParam As Long) As Boolean
Private Declare Function GetClassName Lib "user32.dll" Alias "GetClassNameA" ( _
ByVal hWnd As Long, _
ByVal lpClassName As String, _
ByVal nMaxCount As Long) As Long
Private Const GC_CLASSNAME_EXPLORER = "CabinetWClass" 'ExploreWClass
'Private Const GC_CLASSNAME_FIREFOX = "MozillaUIWindowClass" 'Funktioniert nicht
Private Const GC_CLASSNAME_INTERNETEXPLORER = "IEFrame"

Private Function WindowCallBack(ByVal lngHwnd As Long, ByVal lngParam As Long) As Boolean
    Dim strClassName As String * 256
    Dim lngReturn As Long
    lngReturn = GetClassName(lngHwnd, strClassName, 256)
    Select Case Left$(strClassName, lngReturn)
        Case GC_CLASSNAME_EXPLORER
            MsgBox "Close Windows Explorer"
       ' Case GC_CLASSNAME_INTERNETEXPLORER
       '     MsgBox "Internetexplorer schließen"
       ' Case GC_CLASSNAME_FIREFOX
       '     MsgBox "Firefox ist geöffnet"
    End Select
    WindowCallBack = True
End Function
Public Sub OA1()
    Call EnumWindows(AddressOf WindowCallBack, ByVal 0&)
End Sub
Ich möchte dieses nun zeitverzögert starten und benutze dafür folgende Anweisung:
Public Sub CD2()
Application.OnTime Now + TimeValue("00:00:30"), "OA1"
End Sub
Es tritt nun folgendes Problem auf: wenn ich OA1 direkt starte -> Funktion einwandfrei:
Wenn ich es jedoch über CD2 starte kommt folgende sinngemäße Fehlermeldung: "OA1 in dieser Arbeitsmappe nicht verfügbar oder alle Makros wurden deaktiviert"
Wer weiß Rat?
Albert

  

Betrifft: AW: Makro mit App.OnTime läuft nicht von: Hajo_Zi
Geschrieben am: 01.11.2012 15:52:16

Hallo Albert,

ich würde den Makros nicht gerade eine Zellbezeichnung als Name geben.

GrußformelHomepage


  

Betrifft: AW: Makro mit App.OnTime läuft nicht von: Albert
Geschrieben am: 01.11.2012 16:50:32

Hallo Hajo,

danke für die Info. Ich habe die Makros umgetauft in OAp1 und Count2, Ergebnis ist leider das Selbe - Makro läuft unter Count2 nicht.

Albert


  

Betrifft: AW: Makro mit App.OnTime läuft nicht von: Nepumuk
Geschrieben am: 01.11.2012 17:16:15

Hallo Albert,

die Prozedur welche du per OnTime-Methode aufrufst muss in ein Standardmodul.

Ich habe mir gerade mal Firefox auf einem virtuellen Rechner installiert und dabei festgestellt dass die den Klassennamen geändert haben. Der neue Name ist "MozillaWindowClass".

Gruß
Nepumuk


  

Betrifft: AW: Makro mit App.OnTime läuft nicht von: Albert
Geschrieben am: 01.11.2012 18:18:13

Hallo Nepumuk,

vielen Dank für Deine Geduld und Deinen Einsatz. Firefox wird nun als offene Anwendung erkannt, den Aufruf Deines Makros per OnTime schaffe ich jedoch nicht. Ich habe ein neues Modul eingefügt, und nur in dieses Modul das folgende Makro eingefügt.

Option Explicit

Sub Count2()
Application.OnTime Now + TimeValue("00:00:03"), "OAp1"
End Sub
OAp1 ist Dein Startmakro dass in einem anderen Modul liegt:
Sub OAp1()
    Call EnumWindows(AddressOf WindowCallBack, ByVal 0&)
End Sub
Wenn ich OAP1 über "Worksheet_selectionChange" aufrufe funktioniert es auch. Es wäre nur gut, dass der Anwender Zeit hat den Windows Explorer zu schließen, bevor die Meldung erscheint - deshalb möchte ich das Makro zeitversetzt aufrufen.
Vielleicht hast Du auch hierfür eine Lösung.
Wie kann ich Klassennamen auslesen, für den Fall dass ich Deinen Code nochmals erweitern müsste?

Danke
Albert


  

Betrifft: AW: Makro mit App.OnTime läuft nicht von: Nepumuk
Geschrieben am: 01.11.2012 18:43:46

Hallo Albert,

der Prozedurname ist immer noch eine Zelladresse. Mit Call wie im Worksheet_SelectionChange-Event kannst du so eine Prozedur aufrufen, aber nicht mit OnTime (auch in einer OnAction-Eigenschaft oder per Run-Methode kannst du eine Prozedur mit dem Namen einer Zelle-Adresse nicht aufrufen).

Die Klassennamen aller sichtbaren Fenster bekommst du so:

Option Explicit

Private Declare Function EnumWindows Lib "user32.dll" ( _
    ByVal lpEnumFunc As Long, _
    ByVal lParam As Long) As Boolean
Private Declare Function GetWindowText Lib "user32.dll" Alias "GetWindowTextA" ( _
    ByVal hwnd As Long, _
    ByVal lpString As String, _
    ByVal cch As Long) As Long
Private Declare Function GetWindowTextLength Lib "user32.dll" Alias "GetWindowTextLengthA" ( _
    ByVal hwnd As Long) As Long
Private Declare Function GetClassName Lib "user32.dll" Alias "GetClassNameA" ( _
    ByVal hwnd As Long, _
    ByVal lpClassName As String, _
    ByVal nMaxCount As Long) As Long
Private Declare Function GetWindowLong Lib "user32.dll" Alias "GetWindowLongA" ( _
    ByVal hwnd As Long, _
    ByVal nIndex As Long) As Long

Private Const GWL_STYLE = (-16)
Private Const WS_VISIBLE = &H10000000
Private Const WS_BORDER = &H800000

Private llngRow As Long

Public Sub Start()
    llngRow = 1
    Columns("A:C").ClearContents
    With Range("A1:C1")
        .Value = Array("Hwnd", "Klasse", "Caption")
        .Font.Bold = True
    End With
    Call EnumWindows(AddressOf WindowCallBack, ByVal 0&)
    Columns("A:C").AutoFit
    Tabelle1.Sort.SortFields.Clear
    Tabelle1.Sort.SortFields.Add Key:=Columns(2)
    With Tabelle1.Sort
        .SetRange Columns("A:C")
        .Header = xlYes
        .MatchCase = False
        .Apply
    End With
End Sub

Private Function WindowCallBack(ByVal pvlngHwnd As Long, ByVal pvlngParam As Long) As Long
    Dim strCaption As String, strClassName As String
    Dim lngReturn As Long, lngStyle As Long
    lngStyle = GetWindowLong(pvlngHwnd, GWL_STYLE)
    If Cbool(lngStyle And (WS_VISIBLE Or WS_BORDER)) Then
        strClassName = Space$(256)
        lngReturn = GetClassName(pvlngHwnd, strClassName, 256)
        lngReturn = GetWindowTextLength(pvlngHwnd)
        strCaption = Space$(lngReturn)
        Call GetWindowText(pvlngHwnd, strCaption, lngReturn + 1)
        llngRow = llngRow + 1
        Cells(llngRow, 1).Resize(1, 3) = Array(pvlngHwnd, Trim$(strClassName), strCaption)
    End If
    WindowCallBack = 1
End Function

Gruß
Nepumuk


  

Betrifft: Herzliches Dankeschön!!! von: Albert
Geschrieben am: 01.11.2012 19:27:40

Hallo Nepumuk,

vielen lieben Dank, ich habe mir noch nie angesehen, wie viele Spalten es in der neuen Excelversion gibt und deshalb einfach nicht bedacht, dass ich noch immer eine Zelladresse verwende.
Jetzt funktioniert dank Deiner Hilfe alles Bestens. Auch Danke für den Code zum Auslesen der Klassennamen.

LG

Albert