Access – Listbox und Combobox Funktionen

Access: VBA-Funktionen für Kombinationsfeld (Combobox) und Listenfeld (Listbox)

Im folgenden geht es um Listboxen und Comboboxen auf Access-Formularen. Die Methoden funktionieren nicht auf Formularen der MSForms-Bibliothek, die man z.B. mit Excel erstellen kann.

Es gibt einige Funktionen, die nicht direkt in den Objektmethoden einer Listbox oder einer Combobox enthalten sind. Beispielsweise „Selektiere alle Einträge einer Listbox“ oder „Finde einen bestimmten Eintrag in einer Listbox“.

Problem bei Listboxen mit Spaltenüberschrift

Außerdem gibt es eine Merkwürdigkeit im Umgang mit den VBA-Listbox-Eigenschaften: Wenn die Listbox Überschriften enthält, dann liefern die Eigenschaften ListCount, ItemData, Column und Selected unerwartete Ergebnisse, weil die Überschriften als Zeile mit dem Index 0 gezählt wird, d.h. die erste Daten-Zeile  hat den Index 1 !

Das führt z.B. dazu, dass der Versuch, via VBA die erste Zeile einer Listbox (ohne Mehrfachauswahl) zu selektieren:

ListBox = ListBox.ItemData(0)

nur klappt, wenn die Listbox keine Spaltenüberschriften hat!

Hier würde es also Sinn machen, eine Funktion dafür zu erstellen, die das erwartete Ergebnis liefert, unabhängig davon, ob die Liste Spaltenüberschriften hat oder nicht:

Public Sub LB_SelectIndex(lb_cb As Object, Index As Integer)
' Für Listbox und ComboBox
' selektiere zeile mit dem übergebenen Index
' Liefert mit und ohne Spaltenüberschriften das gleiche ergebnis
 
  lb_cb.Selected(Index - lb_cb.ColumnHeads) = True

End Sub

Statt mit ItemData wird hier aber die Selected-Eigenschaft verwendet, bei der das gleiche Problem besteht:

lb.Selected(0)=True markiert die erste Zeile nur, wenn die Liste keine Überschriften enthält!

Funktionen um etwas aus einer Listbox oder einer Combobox zu lesen

Selektierten Wert der gebundenen Spalte ermitteln. Oder Wert einer bestimmten Zeile in der gebundenen Spalte ermitteln.
Public Function LB_Value(lb_cb As Object, Optional Index As Integer = -1) As Variant
' Für Listbox (ohne Mehrfachauswahl) und Combobox
' Selektierter Wert der gebundenen Spalte, wenn Index fehlt (Null, wenn kein Eintrag selektiert)
' Wert der gebundenen Spalte einer best. Zeile, wenn Index angegeben
' Liefert mit und ohne Spaltenüberschriften den gleichen Wert
 
  If Index = -1 Then
    LB_Value = lb_cb.Value
  Else
    LB_Value = lb_cb.ItemData(Index - lb_cb.ColumnHeads)
  End If

End Function

Selektierten Wert einer beliebigen Spalte ermitteln
Public Function LB_Column(lb_cb As Object, iCol As Integer, Optional Index As Integer = -1) As Variant
' Für Listbox (ohne Mehrfachauswahl) und Combobox
' Selektierter Wert der Spalte iCol, wenn Index fehlt (Null, wenn kein Eintrag selektiert)
' Wert der Spalte iCol einer best. Zeile, wenn Index angegeben (Index beginnt bei 0)
' Liefert mit und ohne Spaltenüberschriften den gleichen Wert
 
  If Index = -1 Then
    LB_Column = lb_cb.Column(iCol, lb_cb.ListIndex)
  Else
    LB_Column = lb_cb.Column(iCol, Index - lb_cb.ColumnHeads)
  End If

End Function
Summe der numerischen Werte einer bestimmten Spalte einer Listbox oder Combobox
Public Function LB_Sum(lb_cb As Object, Optional iCol As Integer = -1) As Double
' Für Listbox und Combobox
' Summe der numerischen Werte in Spalte iCol (oder gebundene Spalte, wenn iCol fehlt)
' Liefert mit und ohne Spaltenüberschriften den gleichen Wert
' unabhängig von Selektion und Mehrfachauswahl
Dim i As Integer
 
  If iCol = -1 Then iCol = lb_cb.BoundColumn - 1
 
  For i = 0 To lb_cb.ListCount + lb_cb.ColumnHeads - 1
    If IsNumeric(lb_cb.Column(iCol, i - lb_cb.ColumnHeads)) Then
      LB_Sum = LB_Sum + lb_cb.Column(iCol, i - lb_cb.ColumnHeads)
    End If
  Next

End Function

Bestimmten Wert in bestimmter Spalte finden
Public Function LB_Find(lb_cb As Object, varFind As Variant, Optional iCol As Integer = -1) As Variant
' Für Listbox und Combobox
' Gibt zeilen-Index der zeile zurück, wenn bestimmter wert in Spalte iCol gefunden wird (bzw. in gebundener Spalte, wenn iCol fehlt)
' Gibt Null zurück, wenn Wert nicht gefunden wird
' varFind kann Wildcards * oder ? haben
' Liefert mit und ohne Spaltenüberschriften den gleichen Wert
' unabhängig von Selektion und Mehrfachauswahl
Dim i As Integer
Dim strValue As String
 
  If iCol = -1 Then iCol = lb_cb.BoundColumn - 1
 
  LB_Find = Null
 
  For i = 0 To lb_cb.ListCount + lb_cb.ColumnHeads - 1
    strValue = lb_cb.Column(iCol, i - lb_cb.ColumnHeads)
    If strValue Like varFind Then
      LB_Find = i
      Exit Function
    End If
  Next

End Function
Anzahl der Zeilen einer Listbox oder Combobox

Die Eigenschaft ListCount zählt tatsächlich 1 dazu, wenn die Liste Überschriften enthält!
-> Hier die Funktion, die mit und ohne Überschriften das richtige Ergebnis liefert.

Public Function LB_ListCount(lb_cb As Object) As Long
' Für Listbox und Combobox
' gibt Anzahl der Zeilen zurück
' Liefert mit und ohne Spaltenüberschriften den gleichen Wert
' unabhängig von Selektion und Mehrfachauswahl
 
 ' bei tatsächlich 0 eintägen in der liste liefert .ListCount richtigerweise 0 bei mit und ohne Überschriften
 ' aber wenn Eintäge vorhanden sind, dann zählt .ListCount 1 dazu, wenn Überschriften=ja
 
 LB_ListCount = lb_cb.ListCount + lb_cb.ColumnHeads
 
 If LB_ListCount = -1 Then LB_ListCount = 0
 
End Function

Array mit Werten einer Spalte

Die folgende Funktion verwendet die Funktion ArrayAdd, die im Beitrag Nützliche Array-Funktionen aufgelistet ist.

Public Function LB_Array(lb_cb As Object, Optional iCol As Integer = -1) As Variant
 ' Für Listbox und Combobox
 ' Gibt Array mit Werten einer Spalte zurück (gebundene Spalte, wenn iCol fehlt)
 ' Gibt Empty zurück, wenn Liste leer
 ' Liefert mit und ohne Spaltenüberschriften den gleichen Wert
 ' unabhängig von Selektion und Mehrfachauswahl
 Dim i As Integer
 Dim strValue As String

  If iCol = -1 Then iCol = lb_cb.BoundColumn - 1

  For i = 0 To lb_cb.ListCount + lb_cb.ColumnHeads - 1
    ArrayAdd LB_Array, lb_cb.Column(iCol, i - lb_cb.ColumnHeads)
  Next

End Function

Auswahl-Aktionen mit Listboxen und Comboboxen

Selektiere eine bestimmte Zeile, d.h. Zeilenindex, einer Listbox oder Combobox
Public Sub LB_SelectIndex(lb_cb As Object, Index As Integer)
' Für Listbox und ComboBox
' selektiere zeile mit dem übergebenen Index (beginnend bei 0)
' Liefert mit und ohne Spaltenüberschriften das gleiche ergebnis
 
  lb_cb.Selected(Index - lb_cb.ColumnHeads) = True

End Sub

Selektiere eine Zeile, bei der die gebundene Spalte oder eine bestimmte Spalte einen bestimmten Wert hat. Auch mit Wildcards.
Public Function LB_Select(lb As ListBox, varValue As Variant, Optional iCol As Integer = -1, Optional bAdditional As Boolean) As Boolean
' Für Listbox
' selektiere zeile (auch mehrere bei mehrfachauswahl), bei der Spalte iCol den Wert varValue hat (wenn iCol nicht angegeben ist, dann gebundene Spalte!)
' varValue kann Wildcards * und ? haben
' Liefert mit und ohne Spaltenüberschriften das gleiche ergebnis
' bAdditional: wenn false, dann wird initial die Listbox geleert
' wenn true, dann wird die bestehende selektion beibehalten
' Rückgabe: true, wenn zeile(n) markiert wurde(n)
Dim i As Integer
 
  If iCol = -1 Then iCol = lb.BoundColumn - 1
 
  For i = 0 To lb.ListCount - 1
    If lb.Column(iCol, i) Like varValue Then
      lb.Selected(i) = True
    ElseIf Not bAdditional Then
      lb.Selected(i) = False
    End If
  Next

End Function

Funktionen für Listboxen mit Mehrfachauswahl

Ist eine bestimmte Zeile selektiert?
Public Function LB_Selected(lb As ListBox, Index As Integer) As Boolean
' Für Listbox mit Mehrfachauswahl
' Liefert True, wenn Zeile Index selektiert ist
' Liefert mit und ohne Spaltenüberschriften den gleichen Wert
 
  ' selected(0) ist bei MitÜberschriften immer 0, weil es die Überschriftenzeile ist
  LB_Selected = lb.Selected(Index - lb.ColumnHeads)
 
End Function

Wieviele Zeilen sind selektiert?
Public Function LB_SelectCount(lb As ListBox) As Integer
' Für Listbox mit Mehrfachauswahl
' Liefert Anzahl der selektierten Einträge
' Liefert mit und ohne Spaltenüberschriften den gleichen Wert
 
  LB_SelectCount = lb.ItemsSelected.Count
 
 
End Function
Array mit den selektierten Werten (gebundene oder beliebige Spalte) einer Listbox mit Mehrfach-Auswahl
Public Function LB_ArrayOfSelected(lb As ListBox, Optional iCol As Integer = -1) As Variant
' Für Listbox mit Mehrfachauswahl
' Gibt Array zurück, mit den selektierten Values einer Listbox (Gebunden Spalte, wenn iCol nicht übergeben wird, sonst Spalte iCol)
' Empty, wen nichts selektiert
' Liefert mit und ohne Spaltenüberschriften den gleichen Wert
Dim varItem As Variant
 
  If iCol = -1 Then iCol = lb.BoundColumn - 1
 
  For Each varItem In lb.ItemsSelected
    ArrayAdd LB_ArrayOfSelected, lb.Column(iCol, varItem)
  Next varItem
 
End Function

Ist Zeile mit bestimmtem Wert (in gebundener oder beliebiger Spalte) selektiert in einer Listbox mit Mehrfach-Auswahl?
Public Function LB_ValueSelected(lb As ListBox, varValue As Variant, Optional iCol As Integer = -1) As Boolean
' Für Listbox mit Mehrfachauswahl
' Gibt True zurück, wenn varValue unter den selektierten Werten ist, wobei die Spalte iCol maßgeblich ist (wenn iCol fehlt, dann gebundene Spalte)
' varValue kann Wildcards * und ? haben
' Empty, wenn nichts selektiert
' Liefert mit und ohne Spaltenüberschriften den gleichen Wert
Dim varItem As Variant
 
  If iCol = -1 Then iCol = lb.BoundColumn - 1
 
  For Each varItem In lb.ItemsSelected
    If lb.Column(iCol, varItem) Like varValue Then
      LB_ValueSelected = True
      Exit Function
    End If
 Next varItem

End Function

Selektiere oder deselektiere alle Zeilen in einer Listbox mit Mehrfachauswahl
Public Sub LB_SelectAllOrNone(lb As ListBox, bSelect As Boolean)
' Alle Zeilen einer Listbox selektieren oder deselektieren
Dim i As Integer

  For i = 0 To lb.ListCount - 1
    lb.Selected(i) = bSelect
  Next

End Sub

Access – Listbox und Combobox Funktionen
Markiert in:    

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert.