Warum sollte man Formulare per VBA erstellen, wenn Microsoft Access doch die gute alte, etwas in die Jahre gekommene Entwurfsansicht dafür bereitstellt Ganz einfach: Weil es für den effizient arbeitenden Access-Entwickler immer wieder Aufgaben gibt, die er einfach nicht von Hand erledigen möchte. Oder weil der Access-Entwickler immer wiederkehrende Aufgaben in ein Access-Add-In oder ein COM-Add-In auslagern möchte. Und dort gibt es nun einmal keine Entwurfsansicht – dort ist VBA-Code gefragt, um neue Formulare zu erstellen und die gewünschten Steuerelemente auf das Formular zu bringen. Dieser Beitrag liefert alle Techniken, die zum Erstellen von Formularen und zum Ausstatten mit Steuerelementen notwendig sind.
Neues, leeres Formular erstellen
Mit einer ersten Funktion wollen wir ein neues, leeres Formular mit einem vorher festgelegten Namen erstellen. Das erledigt die Funktion CreateNewForm. Diese erwartet als Parameter den Namen, den das Formular nach dem Erstellen erhalten soll:
Public Sub CreateNewForm(strName As String) Dim frm As Form Dim strNameTemp As String Set frm = CreateForm() strNameTemp = frm.Name DoCmd.Close acForm, frm.Name, acSaveYes DoCmd.Rename strName, acForm, strNameTemp End Sub
Die Prozedur deklariert Variablen für das neue Form-Element (frm) und für den temporären von Access beim Erstellen vergebenen Namen (strNameTemp). Dann erstellt es mit der CreateForm-Funktion ein neues Formular. CreateForm liefert einen Verweis auf das neu erstellte Form-Objekt zurück, welches wir mit der Variablen frm referenzieren. Wir würden nun gern den Namen des Formulars einstellen, aber das ist nicht ohne weiteres möglich: Die Eigenschaft Name des Form-Objekts ist nämlich schreibgeschützt. Wie also dem Formular den gewünschten Namen geben Klar: Wir könnten es einfach nach dem Speichern und Schließen umbenennen, dafür gibt es die DoCmd.Rename-Methode. Allerdings erwartet die auch den vorherigen Namen des Formulars, und den kennen wir nicht. Allerdings können wir diesen zuvor mit frm.Name auslesen und speichern ihn in der Variablen strNameTemp. Danach schließen wir dann das Formular mit der Methode DoCmd.Close und den Parametern acForm für den Objekttyp, frm.Name für den Namen des zu schließenden Objekts und acSaveYes, damit die Änderungen an dem neu erstellten Formular ohne Rückfrage gespeichert werden.
Nach dem Schließen rufen wir dann DoCmd.Rename auf und übergeben mit dem ersten Parameter den neuen Namen, mit dem zweiten den Objekttyp (acForm) und mit dem dritten den vorherigen Objektnamen.
Rufen wir diese Prozedur nun wie folgt auf, legt dies ein neues, leeres Formular unter dem angegebenen Namen an, das direkt im Navigationsbereich erscheint:
CreateNewForm "frmNeuesFormular"
Formular bereits vorhanden
Wenn man diese Prozedur zwei Mal hintereinander mit dem gleichen Formularnamen aufruft, erhält man die Meldung aus Bild 1. Diese wird durch den Versuch ausgelöst, dem neuen Formular den Namen eines bereits vorhandenen Formulars zu übergeben. Dem können wir bereits zuvor vorbeugen, indem wir abfragen, ob bereits ein Formular dieses Namens vorhanden ist. Ob ein Formular bereits vorhanden ist, können wir auf verschiedene Arten prüfen. Wir könnten zum Beispiel versuchen, es zu öffnen, oder wir durchlaufen eine der Auflistungen der Formulare.
Bild 1: Meldung beim Versuch, einem Formular einen bereits vorhandenen Namen zu geben
Wir wählen letztere Variante. Die Funktion heißt ExistsForm und erwartet den Formularnamen als Parameter. Sie liefert das Ergebnis als Booleanwert zurück. Hier deklarieren wir für die Formulare eine Variable des Typs AccessObject. Warum nun AccessObject und nicht Form wie oben in der Prozedur CreateNewForm Weil die dort verwendete Funktion CreateForm ein Objekt des Typs Form erstellt, die Auflistung CurrentProject.AllForms, die wir durchsuchen wollen, jedoch Elemente des Typs AccessObjects liefert.
Mit objForm durchlaufen wir in einer For Each-Schleife alle Elemente der Auflistung CurrentProject.AllForms und prüfen, ob das aktuell mit objForm referenzierte Formular den mit strForm übergebenen Namen hat. Falls ja, stellen wir den Funktionswert auf True ein und verlassen die Funktion. Wenn die Funktion alle Elemente aus CurrentProject.AllForms durchläuft, ohne dass das passende Formular gefunden wird, liefert sie den Rückgabewert False (also den Standardwert für Rückgabewerte des Datentyps Boolean):
Public Function ExistsForm(strForm As String) As Boolean Dim objForm As AccessObject For Each objForm In CurrentProject.AllForms If objForm.Name = strForm Then ExistsForm = True Exit Function End If Next objForm End Function
Formular neu erstellen
Wenn das Formular bereits existiert, können wir den Benutzer fragen, ob das vorhandene Formular überschrieben werden soll. Ist das der Fall, löschen wir das Formular und erstellen es neu. Dazu erweitern wir die Prozedur CreateNewForm wie in Listing 1. Hier fügen wir direkt hinter der Deklaration der Variablen einen Aufruf der Funktion ExistsForm ein.
Public Function CreateNewForm(strName As String) As Boolean Dim frm As Form Dim strNameTemp As String If ExistsForm(strName) Then If MsgBox("Formular ''" & strName & "'' ist bereits vorhanden. Überschreiben", vbYesNo + vbExclamation, _ "Formular überschreiben") = vbYes Then If DeleteForm(strName) = False Then Exit Function End If Else Exit Function End If End If Set frm = CreateForm() strNameTemp = frm.Name frm.Visible = True DoCmd.Close acForm, frm.Name, acSaveYes DoCmd.Rename strName, acForm, strNameTemp CreateNewForm = True End Function
Listing 1: Erstellen eines neuen Formulars
Liefert diese den Wert True, dann zeigen wir ein Meldungsfenster an, das den Benutzer fragt, ob er das Formular überschreiben möchte. Falls ja, rufen wir eine Funktion namens DeleteForm auf (siehe weiter unten) und übergeben den Namen des zu löschenden Formulars. Diese könnte fehlschlagen, weil beispielsweise das zu löschende Formular gerade geöffnet ist. In diesem Fall soll die Prozedur einfach verlassen werden – die passende Fehlermeldung soll die Funktion DeleteForm liefern. Wenn der Benutzer die Frage, ob das vorhandene Formular gelöscht werden soll, mit Nein antwortet, soll die Prozedur auch verlassen werden.
Nur wenn das Formular noch nicht existiert oder gelöscht werden konnte, werden die anschließenden Schritte zum Erstellen des neuen Formulars ausgeführt.
Löschen eines vorhandenen Formulars
Wenn das Formular bereits vorhanden ist und der Benutzer es überschreiben möchte, müssen wir es löschen. Dazu haben wir die Funktion DeleteForm definiert, die den Namen des zu löschenden Formulars entgegennimmt und einen Boolean-Wert zurückliefert.
Die Funktion probiert bei deaktivierter eingebauter Fehlerbehandlung aus, ob das Formular mit DoCmd.DeleteObject gelöscht werden kann. Falls ja, erhält die Funktion den Rückgabewert True. Anderenfalls gibt die Funktion die entsprechende Fehlermeldung aus Err.Description aus und gibt den Standardwert False als Funktionsergebnis an die aufrufende Prozedur zurück:
Public Function DeleteForm(strName As String) As Boolean On Error Resume Next DoCmd.DeleteObject acForm, strName If Err.Number = 0 Then DeleteForm = True Else MsgBox Err.Description, vbCritical + vbOKOnly, _ "Löschen fehlgeschlagen" End If End Function
Damit haben wir bereits eine Funktion zum Erstellen eines neuen Formulars, das allerdings noch komplett leer ist und für das wir auch noch keine Eigenschaften eingestellt haben.
Formular weiterverarbeiten
Nun stehen zwei Aufgaben an: Die erste ist das Einstellen verschiedener Eigenschaften für das Formular. Die zweite ist das Erstellen von Steuerelementen im Formular. Letzteres beschreibt der Beitrag Steuerelemente erstellen (www.access-im-unternehmen.de/1336). Um die Eigenschaften kümmern wir uns jetzt gleich.
Um Eigenschaften einstellen zu können, benötigen wir einen Verweis auf das Formular in der Entwurfsansicht. Das heißt also, dass wir das Formular auch öffnen müssen. Da stellt sich die Frage: Könnten wir mit der Funktion CreateNewForm nicht direkt einen Verweis auf das neu erstellte und in der Formularansicht geöffnete Formular zurückgeben Das könnten wir tun, wir müssten dazu das Formular allerdings auch in dieser Funktion wieder öffnen.
Das Schließen ist dort unbedingt nötig, da wir es sonst nicht umbenennen können. Da wir nicht wissen, ob und wie das Formular nach dem Erstellen direkt weiterverarbeitet werden soll, geben wir einfach nur einen Boolean-Wert zurück, der angibt, ob das Formular erfolgreich erstellt wurde.
Eigenschaften des Formulars einstellen
In der Prozedur, welche die Funktion CreateNewForm aufgerufen hat, können wir nun das Formular in der Entwurfsansicht öffnen und die gewünschten Änderungen vornehmen.
Wie bereits erwähnt, wollen wir uns in diesem Beitrag zunächst um das Einstellen der verschiedenen Eigenschaften des Formulars kümmern und schauen uns diese dabei im Detail an. Das Öffnen gestalten wir wie folgt:
Public Sub Test_CreateNewForm() Dim frm As Form Dim strForm As String strForm = "frmNeuesFormular" If CreateNewForm(strForm) = True Then DoCmd.OpenForm strForm, acDesign Set frm = Forms(strForm) With frm ''Eigenschaften einstellen End With End If End Sub
Hier schreiben wir den Namen des zu erstellenden Formulars direkt in eine Variable, weil wir diesen mehr als einmal benötigen und anschließende Änderungen so nur an einer Stelle erfolgen müssen. Dann erstellen wir das neue Formular mit der Funktion CreateNewForm.
Ist dies erfolgreich, öffnen wir das neu erstellte Formular mit DoCmd.OpenForm in der Entwurfsansicht. Dazu stellen wir den zweiten Parameter View auf acDesign ein.
Damit wir danach komfortabel die Eigenschaften des Formulars einstellen können, referenzieren wir das Formular dann über die Forms-Auflistung und den Namen des Formulars mit der Form-Variablen frm. Für frm stellen wir dann die nachfolgend beschriebenen Eigenschaften ein.
Einstellungen für die Titelleiste
Die Titelleiste des Formulars (siehe Bild 2) verwendet gleich mehrere Eigenschaften.
Bild 2: Elemente der Titelleiste eines Formulars
- Die Titelleiste des Formulars stellen wir mit der Eigenschaft Caption ein.
- Ob das Formular das gleiche Icon anzeigen soll wie die Hauptanwendung, legen Sie übrigens nicht mit einer Formular-Eigenschaft fest, sondern in den Access-Optionen mit der Option Als Formular- und Berichtssymbol verwenden. Dies gilt dann für alle Formulare und Berichte.
- Ob die Schließen-Schaltfläche aktiviert ist, stellen sie mit der Eigenschaft CloseButton ein. Legen Sie den Wert auf False fest, wird die Schaltfläche ausgegraut dargestellt und der Benutzer kann sie nicht betätigen.
- Die Schaltflächen in der Titelleiste zum Minimieren und Maximieren des Fensters können Sie über die Benutzeroberfläche mit der Eigenschaft MinMaxSchaltflächen einstellen, über VBA mit MinMaxButtons. Die möglichen Werte sind: 0 (Keine), 1 (Min vorhanden), 2 (Max vorhanden) oder 3 (Beide vorhanden).
- Die Eigenschaft Mit Systemfeldmenü (ControlBox) stellt ein, ob überhaupt Steuerelemente in der Titelleiste angezeigt werden sollen. Falls nicht, sieht die Titelleiste wie in Bild 3 aus.
Bild 3: Titelleiste nur mit Überschrift
Abmessungen
Die Abmessungen des Formulars wie die Höhe und die Breite stellen Sie mit Eigenschaften für verschiedene Elemente ein. Die Breite ist eine Formular-Eigenschaft, diese entspricht der VBA-Eigenschaft Width. Eine Eigenschaft namens Höhe beziehungsweise Height vermissen wir allerdings im Eigenschaftenblatt. Der Grund ist einfach: Ein Formular kann mehrere Bereiche enthalten, die jeweils eine eigene Höhe haben – zum Beispiel der Detailbereich oder Formularkopf und -Fuß. Die Einstellungen dieser Bereiche besprechen wir weiter unten.
Standardansicht
Die Standardansicht stellt die Eigenschaft DefaultView ein. Diese nimmt die Werte der Enumeration acDefView entgegen:
- acDefViewContinuous (1): Endlosformular
- acDefViewDatasheet (2): Datenblatt
- acDefViewSingle (0): Einzelnes Formular
- acDefViewSplitForm (5): Geteiltes Formular
Beispiel zum Einstellen der Eigenschaft Standardansicht auf Datenblatt:
frm.DefaultView = acViewDatasheet
Erlaubte Ansichten einstellen
Wenn Sie verhindern wollen, dass die Benutzer zwischen verschiedenen Ansichten wechseln, nutzen Sie die Eigenschaft ViewsAllowed dazu.
Mögliche Werte:
- 0: Formularansicht und Datenblattansicht möglich
- 1: Kein Wechsel von der Formularansicht zur Datenblattansicht möglich
- 2: Kein Wechsel von der Datenblattansicht zur Formularansicht möglich
Sichtbarkeit
Mit der Eigenschaft Sichtbar (Visible) können Sie das Formular ein- und ausblenden.
Eigenschaften für geteilte Formulare
Wenn das Formular über die Eigenschaft DefaultView als geteiltes Formular angezeigt wird, werden die folgenden Eigenschaften ausgewertet:
- Größe des geteilten Formulars (SplitFormSize) gibt je nach der mit SplitFormOrientation gewählten Position die Höhe oder Breite des Detailbereichs des geteilten Formulars an. Diese wird im Eigenschaftenblatt in Zentimeter und unter VBA in Twips angegeben.
- Ausrichtung des geteilten Formulars (SplitFormOrientation): Gibt an, wo das Datenblatt angezeigt werden soll. Es gibt die folgenden Werte: acDatasheetOnBottom (1), acDatasheetOnLeft (2), acDatasheetOnRight (3) und acDatasheetOnTop (0).
- Teilerleiste des geteilten Formulars (SplitFormSplitterBar): Gibt an, ob die Leiste zwischen den beiden Formularbereichen angezeigt werden soll. Wenn der Benutzer die Höhe/Breite der Bereiche nicht anpassen können soll, stellen Sie diese Eigenschaft auf False ein.
- Datenblatt des geteilten Formulars (SplitFormDatasheet): Hier können Sie festlegen, ob Bearbeitungen im Datenblatt zulässig sein sollen. Es gibt die beiden Werte Bearbeitungen zulassen (acDatasheetAllowEdits) oder Schreibgeschützt (acDatasheetReadOnly.).
- Drucken des geteilten Formulars (SplitFormPrinting): Hiermit legen Sie fest, welcher Bereich des geteilten Formulars im Fall der Fälle gedruckt werden soll. Die Eigenschaft nimmt die Werte Nur Datenblatt (acGridOnly) oder Nur Formular (acFormOnly) entgegen.
- Position der Teilerleiste speichern (SaveSplitterBarPosition): Legt fest, ob die Position der Teilerleiste gespeichert werden soll, wenn diese beim Bearbeiten des geöffneten Formulars mit der Maus verschoben wurde. Beim Schließen wird dann abgefragt, ob die Position so wie geändert erhalten werden soll.
Einstellungen für die Anzeige des Formulars
Die folgenden Einstellungen blenden verschiedene Formularelemente ein- oder aus, außerdem enthalten sie Informationen über den Zustand zu modalen und Popup-Fenstern.
Die nachfolgend beschriebenen Elemente finden Sie teilweise im Screenshot aus Bild 4.
Bild 4: Ein- und ausblendbare Elemente im Formular
- Automatisch zentrieren (AutoCenter): Legt fest, ob das Formular beim Öffnen automatisch im Access-Fenster zentriert werden soll.
- Datensatzmarkierer (RecordSelectors): Aktiviert die Anzeige des Datensatzmarkierers (siehe Screenshot unter 1)
- Navigationsschaltflächen (NavigationButtons): Aktiviert die Anzeige der Navigationsschaltflächen (siehe Screenshot unter 3).
- Navigationsbeschriftung (NavigationCaption): Stellt die Beschriftung der Navigationsschaltflächen ein. Diese Beschriftung wird dort angezeigt, wo normalerweise Datensatz: steht (siehe Screenshot unter 2).
- Trennlinien (DividingLines): Legt fest, ob im Endlosformular Trennlinien zwischen den Datensätzen angezeigt werden.
- Bildlaufleisten (ScrollBars): Stellt ein, ob Bildlaufleisten angezeigt werden sollen. Es gibt die folgenden Einstellungen: 0: Nein, 1: Nur horizontal, 2: Nur vertikal und 3: In beide Richtungen (siehe Screenshot unter 4)
- Rahmenart (BorderStyle): Gibt an, welche Rahmenart für Titelzeile, Formularrahmen et cetera verwendet werden soll. Es gibt die Werte 0 (Keine), 1 (Extra dünn), 2 (Veränderbar) und 3 (Dialog).
Außerdem gibt es noch zwei Eigenschaften, welche beide auf True eingestellt werden, wenn Sie das Formular mit DoCmd.OpenForm mit dem Wert acDialog für den Parameter WindowMode öffnen:
DoCmd.OpenForm "frmBeispiel", WindowMode:=acDialog
Die Eigenschaften lauten Popup (im Eigenschaftenblatt und unter VBA) und Modal (nur unter VBA verfügbar). Wenn Sie ein Formular wie oben öffnen, weisen diese beiden Eigenschaften beide den Wert True auf. Wenn Sie beide beim Erstellen auf True einstellen, wird das Formular immer als modaler Dialog geöffnet.
Ribbon und Menüs
Auch zum Festlegen des Ribbons, das mit einem Formular angezeigt werden soll und zu den Menüs, die mit Access 2003 abgekündigt wurden, gibt es einige Eigenschaften. Das Ribbon eines Formulars stellen Sie mit der Eigenschaft Name des Menübands (RibbonName) ein. Hier geben Sie den Namen eines der Einträge der Tabelle USysRegInfo ein. Die übrigen Eigenschaften wollen wir nur der Vollständigkeit halber erwähnen. Mit Menüleiste (MenuBar) und Symbolleiste (Toolbar) geben Sie die mit einem Formular anzuzeigenden Menüs an. Die Eigenschaft Kontextmenüleiste (ShortcutMenuBar) hingegen können Sie auch unter Access 2007 und neuer noch verwenden. Voraussetzung ist, dass Sie beispielsweise mit dem folgenden Code eine solche Kontextmenüleiste erstellt haben:
Dim cbr As CommandBar Dim cbc As CommandBarButton On Error Resume Next CommandBars("cbrKontextmenue").Delete On Error GoTo 0 Set cbr = CommandBars.Add("cbrKontextmenue", msoBarPopup, False, True) Set cbc = cbr.Controls.Add(msoControlButton) With cbc .Caption = "Beispielbutton" End With
Danach können Sie das Kontextmenü aus der Liste im Eigenschaftenblatt auswählen und es auch der Eigenschaft ShortCutMenuBar zuweisen:
frm.ShortCutMenuBar = "cbrKontextmenue"
Mit der Eigenschaft Kontextmenü (ShortcutMenu) legen Sie fest, ob das Formular überhaupt ein Kontextmenü anzeigen soll. Damit deaktivieren Sie sowohl eingebaute als auch benutzerdefinierte Kontextmenüs.
Dateneinstellungen
Die Eigenschaft Datensatzquelle (RecordSource) stellt die Tabelle oder Abfrage ein, deren Daten im Formular angezeigt werden können.
Mit der Eigenschaft Zyklus (Cycle) stellen Sie ein, ob beim Verlassen des letzten Feldes zum ersten Feld der Aktivierreihenfolge oder umgekehrt etwa mit der Tabulator- oder der Eingabetaste der Datensatz gewechselt werden soll. Die Eigenschaft kann die Werte 0 (Alle Datensätze), 1 (Aktueller Datensatz) und 2 (Aktuelle Seite) annehmen.
Die Eigenschaft Standardwerte abrufen (FetchDefaults) gibt an, ob Standardwerte für Datensätze schon vor dem Speichern angezeigt werden sollen.
Datenoperationen erlauben oder verbieten
Die folgenden Eigenschaften dienen dazu, verschiedene Operationen mit Daten zu erlauben oder zu unterbinden:
- Daten eingeben (DataEntry): Legt fest, ob das Formular beim Öffnen nur einen neuen, leeren Datensatz anzeigt (True) oder ob alle Datensätze angezeigt werden sollen (False).
- Anfügen zulassen (AllowAdditions): Legt fest, ob neue Datensätze hinzugefügt werden können.
- Löschen zulassen (AllowDeletions): Legt fest, ob Datensätze gelöscht werden können.
- Bearbeitungen zulassen (AllowEdits): Legt fest, ob Datensätze bearbeitet werden können.
- Filter zulassen (AllowFilters): Legt fest, ob Filter gesetzt werden dürfen.
- Recordsettyp (RecordsetType): Legt den Recordset-Typ für das Formular fest. Kann die folgenden Werte annehmen: 0 (Dynaset), 1 (Dynaset mit inkonsistenten Updates) und 2 (Snapshot)
- Datensätze sperren (RecordLocks): Gibt an, ob Datensätze beim Bearbeiten gesperrt werden sollen. Mögliche Werte: Keine Sperrungen (0), Alle Datensätze (1) oder Bearbeiteter Datensatz (2).
Filter und Sortierung
Ende des frei verfügbaren Teil. Wenn Du mehr lesen möchtest, hole Dir ...
den kompletten Artikel im PDF-Format mit Beispieldatenbank
diesen und alle anderen Artikel mit dem Jahresabo