ABOUT Visual Basic Programmieren Programmierung Download Downloads Tips & Tricks Tipps & Tricks Know-How Praxis VB VBA Visual Basic for Applications VBS VBScript Scripting Windows ActiveX COM OLE API ComputerPC Microsoft Office Microsoft Office 97 Office 2000 Access Word Winword Excel Outlook Addins ASP Active Server Pages COMAddIns ActiveX-Controls OCX UserControl UserDocument Komponenten DLL EXE
Diese Seite wurde zuletzt aktualisiert am 09.03.2001

Diese Seite wurde zuletzt aktualisiert am 09.03.2001
Aktuell im ABOUT Visual Basic-MagazinGrundlagenwissen und TechnologienKnow How, Tipps und Tricks rund um Visual BasicAddIns für die Visual Basic-IDE und die VBA-IDEVBA-Programmierung in MS-Office und anderen AnwendungenScripting-Praxis für den Windows Scripting Host und das Scripting-ControlTools, Komponenten und Dienstleistungen des MarktesRessourcen für Programmierer (Bücher, Job-Börse)Dies&Das...

Themen und Stichwörter im ABOUT Visual Basic-Magazin
Code, Beispiele, Komponenten, Tools im Überblick, Shareware, Freeware
Ihre Service-Seite, Termine, Job-Börse
Melden Sie sich an, um in den vollen Genuss des ABOUT Visual Basic-Magazins zu kommen!
Informationen zur AVB-Web-Site, Kontakt und Impressum

Zurück...

Combo ohne Box

Zurück...

(-hg) mailto:hg_droplist@aboutvb.de

Eine Drop-Down-Auswahlliste wie bei einer ComboBox - aber ohne die ComboBox selbst? Dafür gäbe es einige praktische Einsatzmöglichkeiten, angefangen von einem CommandButton oder einer CheckBox im Button-Stil (Style = grafisch) bis hin zu Auswahllisten unter einem ListView-Item oder einem TreeView-Knoten. Wie sie die beiden letzteren Ideen realisieren, überlasse ich Ihnen. Hier in diesem Artikel geht es nur darum, wie Sie die Auswahlliste zur Anzeige bringen.

Eine Drop-Down-Auswahlliste mit verborgener ComboBox

Eine Drop-Down-Auswahlliste mit verborgener ComboBox

Der eigentliche Trick ist simpel - Sie brauchen nur dafür zu sorgen, dass die ComboBox selbst nicht erscheint und klappen die Liste selbst aus. Wie Sie das Aus- und Einklappen per Code bewerkstelligen, sehen Sie in Klappe auf - Klappe zu"Klappe auf - Klappe zu".

Das Verbergen der ComboBox könnten Sie nun etwa mit einem passgenau darüber gelegten Frame oder einer PictureBox erledigen. Doch dann hätten Sie noch ein wenig Arbeit damit. Denn sie hätten den Fokus während und nach dem Ausklappen der Auswahlliste richtig zu steuern. Sie müssten dafür sorgen, dass die ComboBox selbst auch nicht unvorhergesehen den Fokus erhalten kann. Und Sie müssten gegebenenfalls prüfen, wann die Auswahlliste wieder geschlossen wird, um beispielsweise die oben erwähnte CheckBox wieder in den Ruhezustand zurück versetzen zu können.

Da bietet es sich an, ein UserControl mit einer darauf platzierten ComboBox zu verwenden. Die Breite der Auswahlliste bestimmen Sie über die Breite des UserControls, an dessen innere Breite sich die ComboBox automatisch anpasst. Und indem Sie die Höhe des UserControls zur Laufzeit auf 0 setzen, verschwindet die ComboBox wie beabsichtigt. Nun schieben Sie die ComboBox noch gerade über die Oberkante des UserControls "ins Nichts" hinaus, damit die Oberkante der Auswahlliste mit der Oberkante des UserControls übereinstimmt. So können Sie zur Entwicklungszeit das UserControl gezielt positionieren. Von alledem wird die Auswahlliste jedoch nicht betroffen - sie erscheint wie gewohnt und wie erhofft an der gewünschten Stelle. Allerdings sollten Sie dabei berücksichtigen, dass die Auswahlliste nicht immer nach unten aufklappt. Denn wenn sich die nunmehr "virtuelle" ComboBox zu nahe an der Unterkante des Bildschirms befindet, klappt die Auswahlliste nach oben auf - oberhalb der virtuellen ComboBox. Sie erhalten dadurch entweder einen unschönen und eher unbeabsichtigten Versatz. Setzen Sie jedoch beispielsweise die Höhe einer zugehörigen CheckBox zur Entwicklungszeit auf die die Höhe des UserControls, erscheint eine nach oben hin aufklappende Auswahlliste dann auch wunschgemäß an der Oberkante dieser CheckBox.

Um das UserControl einfach zu halten und nicht alle Eigenschaften, Methoden und Ereignisse der darauf platzierten ComboBox durchreichen zu müssen, wird die ComboBox als Eigenschaft "Combo" über eine Nur-Lesen-Eigenschaft nach draußen gereicht. So haben Sie den gewohnten Zugriff auf die ComboBox. Und Sie können jederzeit eine Ereignisempfänger-Variable darauf setzen und so auch die Ereignisse der ComboBox wie gewohnt auswerten. Sie können dieses UserControl daher auch nur privat innerhalb eines Projektes verwenden, da eine Referenz auf ein VB-eigenes Steuerelement nicht über eine Eigenschaft öffentlich nach außen gegeben werden kann (und darf)!

An eigenen, zusätzlichen Eigenschaften bietet das UserControl lediglich die Eigenschaft IsDropped (siehe ebenfalls Klappe auf - Klappe zu"Klappe auf - Klappe zu"), die Sie darüber informiert, ob die Auswahlliste aktuell ausgeklappt ist, und die Eigenschaft Enabled, die das Ausklappen der Auswahlliste sperrt.

Das Ausklappen und gegebenenfalls manuelle Einklappen der Auswahlliste erfolgt über die Methode DropDown. In deren Parameter ShowHide geben Sie True an, um die Auswahlliste auszuklappen, und False, um sie einzuklappen. Wird sie ausgeklappt, wird zunächst mittels der API-Funktion MSDN-Library - API GetFocusGetFocus festgestellt, welches andere Steuerelement aktuell noch den Fokus inne hat, um ihn nach dem Schließen der Auswahlliste wieder dorthin zurück setzen zu können. Die interne, auf False voreingestellte Enabled-Eigenschaft des UserControls wird nun auf True gesetzt, damit die ComboBox den Fokus erhalten kann. Und eben die Zuweisung des Fokus an die ComboBox ist hier dann die letzte Aktion.

Ein Timer, der nach dem Ausklappen aktiviert wird, prüft in kurzen Abständen, ob die Auswahlliste noch geöffnet ist. Wird festgestellt, dass sie geschlossen ist, deaktiviert sich der Timer und setzt den Fokus über die API-Funktion MSDN-Library - API SetFocusAPISetFocusAPI wieder auf das beim Ausklappen gemerkte Fenster-Handle. Dann wird die interne Enabled-Eigenschaft des UserControls wieder auf False zurück gesetzt - und damit wird auch die ComboBox wieder gesperrt. Das Schließen der Auswahlliste wird nun noch über das Ereignis Closed an Ihre Anwendung gemeldet.

Die ausgeklappte Auswahlliste verhält sich vollkommen wie gewohnt. Die Navigation per Tastatur, das Verhalten beim Darüberfahren mit dem Mauszeiger, das Scrollen, und auch das Schließen per Mausklick auf ein Element in der Liste oder irgendwo anders hin oder per Escape- oder Enter-Taste sind identisch.

Private Declare Function GetFocus Lib "user32" () As Long
Private Declare Function SendMessage Lib "user32" _
 Alias "SendMessageA" (ByVal hwnd As Long, ByVal wMsg As Long, _
 ByVal wParam As Long, lParam As Any) As Long
Private Declare Function SetFocusAPI Lib "user32" _
 Alias "SetFocus" (ByVal hwnd As Long) As Long

Private mStartFocus As Long

Public Event Closed()

Private pEnabled As Boolean

Public Property Get Combo() As Object
  Set Combo = cbo
End Property

Public Property Get Enabled() As Boolean
  Enabled = pEnabled
End Property

Public Property Let Enabled(New_Enabled As Boolean)
  pEnabled = New_Enabled
  If pEnabled = False Then
    Me.DropDown False
  End If
End Property

Public Property Get IsDropped() As Boolean
  Const CB_GETDROPPEDSTATE = &H157
  
  IsDropped = CBool(SendMessage(cbo.hwnd, CB_GETDROPPEDSTATE, 0, 0))
End Property

Public Sub DropDown(Optional ByVal ShowHide As Boolean = True)
  Const CB_SHOWDROPDOWN = &H14F
  
  If ShowHide Then
    If Not pEnabled Then
      Exit Sub
    End If
    mStartFocus = GetFocus()
  End If
  SendMessage cbo.hwnd, CB_SHOWDROPDOWN, ShowHide, 0
  If ShowHide Then
    UserControl.Enabled = True
    cbo.SetFocus
    tmr.Enabled = True
  End If
End Sub

Private Sub tmr_Timer()
  If Not Me.IsDropped Then
    SetFocusAPI mStartFocus
    tmr.Enabled = False
    UserControl.Enabled = False
    RaiseEvent Closed
  End If
End Sub

Private Sub UserControl_Initialize()
  pEnabled = True
End Sub

Private Sub UserControl_InitProperties()
  If Ambient.UserMode Then
    With UserControl
      .BackStyle = 0
      .Enabled = False
    End With
  Else
    With cbo
      .AddItem Ambient.DisplayName
      .ListIndex = 0
      .ForeColor = vbHighlightText
      .BackColor = vbHighlight
    End With
  End If
End Sub

Private Sub UserControl_ReadProperties(PropBag As PropertyBag)
  UserControl_InitProperties
  pEnabled = PropBag.ReadProperty("Enabled", True)
End Sub

Private Sub UserControl_WriteProperties(PropBag As PropertyBag)
  PropBag.WriteProperty "Enabled", pEnabled, True
End Sub

Private Sub UserControl_Resize()
  Static sInProc As Boolean
    
  If sInProc Then
    Exit Sub
  Else
    sInProc = True
  End If
  If Ambient.UserMode Then
    UserControl.Height = 0
    With cbo
      .Move 0, -.Height, UserControl.ScaleWidth
    End With
  Else
    With UserControl
      .Height = cbo.Height
      cbo.Move 0, 0, .ScaleWidth
    End With
  End If
  sInProc = False
End Sub

UserControl DropList und Beispiel-Projekt (droplist.zip - ca. 4,1 KB)



Komponenten-Übersicht

Schnellsuche




Zum Seitenanfang

Copyright © 1999 - 2023 Harald M. Genauck, ip-pro gmbh  /  Impressum

Zum Seitenanfang

Zurück...

Zurück...