Msgbox mittels X abbrechen
#1
Hallo!

Ich habe eine ganz normale Msgbox, welche mit OK bestätigt werden muss. Nun möchte ich aber, dass wenn ich in dieser MsgBox rechts oben das X drücke, dass abgebrochen wird. Derzeit tut es das nämlich nicht.
Wie kann ich das verwirklichen?
Excel Version 2016
Antworten Top
#2
Hallo

was soll denn abgebrochen werden?
bei einer normalen MsgBox schließt die Box doch durch das X

mfg Tom
Antworten Top
#3
Hallo!

Ja, die Msgbox wird eh geschlossen, aber ich will, dass alle weiteren Aktionen abgebrochen werden.
Excel Version 2016
Antworten Top
#4
Moin!
Verwende eine MsgBox mit Buttons:=vbOKCancel
Dann kannst Du Cancel auswerten.

Bei der MsgBox-Funktion gibt es kein QueryClose-Event!
Dafür müsstest Du ein UserForm nehmen.

Gruß Ralf
Gib einem Mann einen Fisch und du ernährst ihn für einen Tag. 
Lehre einen Mann zu fischen und du ernährst ihn für sein Leben. (Konfuzius)
Antworten Top
#5
(15.09.2022, 07:43)dertommy schrieb: … ich will, dass alle weiteren Aktionen abgebrochen werden.
Anders herum denken:
Nur, wenn die Rückgabe des Buttons vbOk ist, fahre fort. In allen anderen Fällen beende Prozedur.

Dokumentation und Codebeispiele:
OH
Antworten Top
#6
Moin EarlFred!
Ich widerspreche Dir höchst ungern.  Blush
Allerdings:
Sowohl OK als auch das Schließen-Kreuz übergeben 1 (entspricht vbOK)

Ich hatte zwischenzeitlich die gleiche Idee wie Du, habe einen kurzen Test geschrieben und mich eines Besseren belehren lassen.
Teste mal:
Sub MsgTest()
Select Case MsgBox("OK und QueryClose-Auswertung")
  Case 1: MsgBox "Es wurde OK gedrückt!"
  Case Else: MsgBox "Offensichtlich wurde das Schließen-Kreuz gedrückt!"
End Select
End Sub

Du wirst immer die erste Antwort erhalten, egal, wie Du "bestätigst".

Gruß Ralf
Gib einem Mann einen Fisch und du ernährst ihn für einen Tag. 
Lehre einen Mann zu fischen und du ernährst ihn für sein Leben. (Konfuzius)
Antworten Top
#7
Hallo, 19 

z. B. so: 21 

Code:
Option Explicit
Public Sub Main_1()
    Select Case MsgBox("Ja, Nein oder Abbrechen klicken!", vbYesNoCancel Or vbInformation Or vbSystemModal Or vbMsgBoxSetForeground, "MsgBox...")
        Case vbYes
            MsgBox "Ja!"
        Case vbNo
            MsgBox "Nein!"
        Case vbCancel
            MsgBox "Abgebrochen!"
    End Select
End Sub
Public Sub Main_2()
    Select Case MsgBox("Ja, Nein oder Abbrechen klicken!", 3 Or 64 Or 4096 Or 65536, "MsgBox...")
        Case 6
            MsgBox "Ja!"
        Case 7
            MsgBox "Nein!"
        Case 2
            MsgBox "Abgebrochen!"
    End Select
End Sub

Bei Abbrechen schreibst du dann...

Code:
End

Das beendet alles. Ist allerdings mit Vorsicht einzusetzen. Dodgy

Oder du nimmst die MessageBoxA function...

Code:
Option Explicit
Private Declare PtrSafe Function MyBoexle Lib "user32" Alias "MessageBoxA" (ByVal hwnd As Long, ByVal _
    lpText As String, ByVal lpCaption As String, ByVal wType As Long) As Long
Public Sub Main()
    Dim lngTMP As Long
    On Error GoTo Fin
    lngTMP = MyBoexle(0, "Im Tabellenblatt kann geklick werden!", "Auswahl...", vbYesNo + vbSystemModal)
    Select Case lngTMP
        Case 6
            MyBoexle 0, "Nun...", "Was?", 0
        Case 7
            MyBoexle 0, "Na, na, na...", "Wie?", 0
    End Select
Fin:
    If Err.Number <> 0 Then MsgBox "Error: " & Err.Number & " " & Err.Description
End Sub
Antworten Top
#8
@RPP63: Das gilt wenn nur vbOKOnly (Standardwert für buttons) für den buttons Parameter verwendet wurde.
Antworten Top
#9
Hallo zusammen,

wer das Klicken des System-Kreuzes gesichert abfangen möchte und den etwas erhöhten Aufwand nicht scheut, kann vielleicht mit dieser Idee hier etwas anfangen....

Erklärung: Wir setzen einen Timer und ermitteln in der Timerproc die Koordinaten des gerade aktiven Fenster, das sollte die Msgbox sein.
Hieraus erstellen wir die Position des Systemkreuzes und sichern diese in einer globalen Variablen.
Nach Beenden der Msgbox durch beliebigen Klick, fragen wir ab, ob die Maus innerhalb des Systemkreuzes ist.

Code:

Private Declare PtrSafe Function SetTimer Lib "user32" ( _
        ByVal hwnd As LongPtr, ByVal nIDEvent As LongPtr, _
        ByVal uElapse As Long, ByVal lpTimerFunc As LongPtr) As LongPtr
Private Declare PtrSafe Function KillTimer Lib "user32" ( _
        ByVal hwnd As LongPtr, ByVal nIDEvent As LongPtr) As Long
Private Declare PtrSafe Function GetActiveWindow Lib "user32" () As LongPtr
Private Declare PtrSafe Function GetWindowRect Lib "user32" ( _
        ByVal hwnd As LongPtr, lpRect As RECT) As Long
Private Declare PtrSafe Function GetCursorPos Lib "user32" (lpPoint As POINTAPI) As Long

Private Type POINTAPI
    x As Long
    y As Long
End Type
Dim PtSys As POINTAPI

Private Type RECT
    Left   As Long
    Top    As Long
    Right  As Long
    Bottom As Long
End Type
Dim R As RECT

Dim hTimer As LongPtr, mPtSys As POINTAPI

Private Sub MsgBox_Callback()
' Ermittelt die Systemkreuz-Position
  KillTimer 0&, hTimer: hTimer = 0                  ' Timer löschen
  GetWindowRect GetActiveWindow(), R                ' Koordinaten der MsgBox holen
  mPtSys.y = R.Top + 40: mPtSys.x = R.Right - 40    ' Position des  roten Systemkreuzes
End Sub

Sub Test()
  Dim iErg As Long, PT As POINTAPI
  
  If hTimer = 0 Then hTimer = SetTimer(0&, 0&, 15, AddressOf MsgBox_Callback)
  iErg = MsgBox("Systemkreuz abfangen", vbOKOnly, "Test")
  
  GetCursorPos PT                                   ' Mausposition holen
  If PT.y < mPtSys.y Then
     MsgBox "Das Systemkreuz wurde geklickt!"
  Else
     MsgBox iErg & " wurde geklickt"
  End If
End Sub

_________
viele Grüße
Karl-Heinz
Antworten Top
#10
(15.09.2022, 12:13)DeltaX schrieb: @RPP63: Das gilt wenn nur vbOKOnly (Standardwert für buttons) für den buttons Parameter verwendet wurde.

Ja, weiß ich!
Ich habe ja auch nichts anderes behauptet.  21

Das hiesige Thema ist ja auch Auswerten des "Schließen-Kreuzes" in einer Standard-MsgBox.

Gruß Ralf

P.S.:
Bevor ich hier mit der Kanone API auf die arme MsgBox schieße, nehme ich lieber ein UserForm, welches exakt wie die MsgBox aussieht, aber folgendes Event zur Verfügung stellt:
Code:
Private Sub UserForm_QueryClose(Cancel As Integer, CloseMode As Integer)
Gib einem Mann einen Fisch und du ernährst ihn für einen Tag. 
Lehre einen Mann zu fischen und du ernährst ihn für sein Leben. (Konfuzius)
Antworten Top


Gehe zu:


Benutzer, die gerade dieses Thema anschauen: 1 Gast/Gäste