Die Frage: Der Befehl speichert und schließt das formluar frm_liste_neu. Aber er refresht nicht frm_liste.
frm_liste befindet sich als Unterformular in frm_frame und heißt dort frm_liste.
Was muss man anstelle von Forms.frm_liste.Requery schreiben?
Private Sub Befehl122_Click()
On Error GoTo Err_Befehl122_Click
DoCmd.Close acForm, "frm_liste_neu", acSaveYes
Forms.frm_liste.Requery
'Me!frm_frame.Form.Requery
'Me!frm_frame.Form.Reload
Exit_Befehl122_Click:
Exit Sub
Err_Befehl122_Click:
'MsgBox Err.Description
Resume Next
Resume Exit_Befehl122_Click
End Sub
Hallo,
es gibt zwei Dinge, die du bei Access beachten mußt:
- Unterformulare erscheinen nicht in der Forms-Auflistung, könnenn also darüber nicht direkt angesprochen werden.
- Access benennt ein SubForm-Control im Designer immer nach dem zugewiesenen Formular. Das muss man nachträglich ändern und dem SubForm-Control einen anderen Namen vergeben, z.B. mit einem Präfix "sub" oder "sfc", je nach Namenskonvention.
Aus dem o.a. folgt dann: wenn du ein Requery auf ein geladenes UF aus dem HF veranlassen möchtest, warum auch immer, kannst du das einfach über das Steuerelement (SubForm-Control) ansprechen:
me.<subformcontrolname>.form.requeryEigentlich sollte das aber nicht notwendig sein.
Knobbi38
PS:
ZitatResume Next
Resume Exit_Befehl122_Click
Der Code ist leider fehlerhaft. "Resume Next" gehört da nicht hin und kann u.U. eine Endlosschleife verursachen!
Mein Text sieht jetzt so aus. Er gibt an, dass er "ufofrm_liste" nicht finden kann. Das SubForm-Control heißt aber so. Das darin befindliche Formular ist "frm_liste" und soll aktualsiert werden. Was kann falsch sein?
Private Sub Befehl122_Click()
On Error GoTo Err_Befehl122_Click
DoCmd.Close acForm, "frm_liste_neu", acSaveYes
Me.ufofrm_liste.Form.Requery
Exit_Befehl122_Click:
Exit Sub
Err_Befehl122_Click:
Resume Exit_Befehl122_Click
End Sub
Hier kannst du nachlesen, wie in Access die Referrer aufgebaut sind:
http://access.mvps.org/access/forms/frm0031.htm (http://access.mvps.org/access/forms/frm0031.htm)
Wenn du Me.ufofrm_liste.Form.Requery im HF aufrufst und ufofrm_liste sich im HF befindet, sollte das UF die Daten neu laden.
Und noch ein Tipp:
DoCmd.Close acForm, "frm_liste_neu", acSaveYes
speichert nur die Änderungen eines Formulars im Entwurfsmodus, nicht die Daten!
Knobbi38
Hallo,
DoCmd.Close acForm, "frm_liste_neu", acSaveYes
Me.ufofrm_liste.Form.RequeryProbiere mal die Reihenfolge umzudrehen. Denn wenn der Vorgang
des Schliessens genau umgekehrt zum Öffnen (UFo -> HFo) abläuft
(habe jetzt keine Lust das auszuprobieren/nachzuschlagen) ist
das UFo schon nicht mehr geladen, und die Referenz läuft ins
Leere.
gruss ekkehard
Zitat von: Knobbi38 am August 28, 2026, 18:57:47Hier kannst du nachlesen, wie in Access die Referrer aufgebaut sind:
http://access.mvps.org/access/forms/frm0031.htm (http://access.mvps.org/access/forms/frm0031.htm)
Wenn du Me.ufofrm_liste.Form.Requery im HF aufrufst und ufofrm_liste sich im HF befindet, sollte das UF die Daten neu laden.
Und noch ein Tipp:
DoCmd.Close acForm, "frm_liste_neu", acSaveYes
speichert nur die Änderungen eines Formulars im Entwurfsmodus, nicht die Daten!
Knobbi38
Und wie müsste der Befehl lauten, wenn ich "Me.ufofrm_liste.Form.Requery" aus einem anderen Formular heraus aufrufe? Mir ist gerade aufgefallen, dass der Befehl in einem Popup steht, daher funktioniert nicht.
Ich versuche das jetzt mit einem Formular mit der Eigenschaft Daten/Daten eingeben, wo alle Felder drin sind. Dort gibt Access auch unter (1) an, dass er "Forms!frm_liste" nicht finden kann, das aber geöffnet ist in einem Unterformular-Steuerelement. Woran kann das liegen? In einer anderen Datenbank funktioniert das normal.
Private Sub Befehl152_Exit(Cancel As Integer)
Dim datensatzID As Long
Dim targetForm As Form
' 1. Verweis auf das geöffnete Endlosformular setzen
Set targetForm = Forms!frm_liste
' 2. Aktuelle ID aus dem steuernden Formular merken (Anpassung je nach Feldname)
datensatzID = Me!ID
' 3. Endlosformular komplett neu laden
targetForm.Requery
' 4. Den aktualisierten Datensatz im Endlosformular wieder ansteuern
With targetForm.RecordsetClone
.FindFirst "ID = " & datensatzID
If Not .NoMatch Then
targetForm.Bookmark = .Bookmark
End If
End With
Set targetForm = Nothing
End Sub
ZitatDort gibt Access auch unter (1) an, dass er "Forms!frm_liste" nicht finden kann, das aber geöffnet ist in einem Unterformular-Steuerelement
Du musst auch die Antworten lesen! Diese Frage wurde schon in #1 beantwortet, warum das nicht geht
und auch dieser Frage
ZitatUnd wie müsste der Befehl lauten, wenn ich "Me.ufofrm_liste.Form.Requery" aus einem anderen Formular heraus aufrufe?
wurde schon mit dem Link beantwortet, wo du passende Beispiele findest.
Hallo,
Du kannst ein UFo-Form nur aus dem HFo ansprechen
Me.UFoControlName.Form.Requeryoder von AUSSEN nur über das HFo
Forms.NameDesHFos.UFoControlName.Form.Requery
Hier noch ein zweiter Link, der dir vlelleicht helfen kann[/td][/tr][/table]
https://www.donkarl.com?FAQ4.2 (https://www.donkarl.com?FAQ4.2)
Ich habe das jetzt mit Hilfe von Beakers Link hinbekommen. Extra Formular zum hinzufügen beim klick.
If Me.Dirty Then
Me.Dirty = False
End If
DoCmd.Close acForm, Me.Name, acSaveNo
Forms!frm_frame!ufofrm_liste.Form.Requery
Exit Sub
Jetzt versuche ich, die Funktion dazu zu bringen, zum neu hinzugefügten Datensatz zu springen.
' 1. Verweis auf das geöffnete Endlosformular setzen
Set targetForm = Forms!frm_frame!ufofrm_liste!frm_liste
' 2. Aktuelle ID aus dem steuernden Formular merken (Anpassung je nach Feldname)
datensatzID = Me!ID
' 3. Endlosformular komplett neu laden
targetForm.Requery
' 4. Den aktualisierten Datensatz im Endlosformular wieder ansteuern
With targetForm.RecordsetClone
.FindFirst "ID = " & datensatzID
If Not .NoMatch Then
targetForm.Bookmark = .Bookmark
End If
End With
Set targetForm = Nothing
Problem: Er erkennt den selben Ausdruck plötzlich nicht mehr. Woran kann das liegen?
Forms!frm_frame!ufofrm_liste!frm_liste
Du hast einen Schreibfehler:
Forms!frm_frame!ufofrm_liste!frm_liste
Aber das ist doch der selbe Ausdruck. Wo ist da ein Schreibfehler?
Du hast oben den Verweis auf das Unterformular
Forms!frm_frame!ufofrm_liste.Form.Requery
Und unten hast Du
Set targetForm = Forms!frm_frame!ufofrm_liste!frm_liste
Nach der Schreibweise würde ich jetzt vermuten, dass frm_liste den Fehler verursacht.
Hallo,
du kannst doch nicht einfach eine eigene Syntax entwerfen und dann hoffen, dass so etwa funktioniert. ::)
Mehrfach hat man dir jetzt erklärt, wie eine Referenz auf ein Unterformular gesetzt wird und alles geflissentlich ignoriert.
@Beaker s.a. hat dir doch die Lösung in #8 gegeben. Vielleicht solltest du doch mal ein Buch über Access/VBA zur Hand nehmen und dort das ein oder andere nachlesen. Das sind Grundkenntnisse, welche du zwingend für die Umsetzung deines Projekts brauchst. Anders als mit Excel ist Access "nur" ein Tool, mit dem man Datenbankanwendungen erstellen kann und man kann nicht wie in Excel einfach mit ein paar Formeln so etwas zusammen klicken. Mit Access ist die Lernkurve eine ganz andere und ohne Einarbeitung läuft da gar nichts.
Tip: Beschäftige dich mal mit dem Bang-Operator (!). Hilfestellungen und Informationen dazu gibt es im Internet zu hauf, so dass das hier nicht nochmal aufgegriffen werden muss.
Knobbi38
Kannst du deinen Code mal im Zusammenhang posten.
DoCmd.Close acForm, Me.NameWelches Form ist das?
Wenn das dieses ist,
ZitatAktuelle ID aus dem steuernden Formular merken
dann gibt es nach dem Schliessen keine ID mehr, und ein Zugriff
von aussen ist auch nicht mehr möglich.
Warum willst du überhaupt von aussen (steuerndes Formular) auf
das UFo zugreifen?
Zitatgibt es im Internet zu hauf
@Ulrich Leider aber auch Widersprüchliches.
@Thüringer Nimm lieber den ., dann hast du auch Intellisense.
Nach meinen Erfahrungen ist das ! nur in Abfragen mit Form-Bezug
(wenn man sie denn verwendet) zwingend.
Hier ist das mal ganz praktisch in deutsch erklärt:
http://www.dbwiki.net/wiki/VBA_Grundlagen:_Verwendung_des_%21-Operators (https://web.archive.org/web/20190805163849/http://www.dbwiki.net/wiki/VBA_Grundlagen:_Verwendung_des_!-Operators)
und hier etwas ausführlicher, allerdings in englisch:
https://eident.co.uk/2016/04/using-bang-dot-microsoft-access/ (https://eident.co.uk/2016/04/using-bang-dot-microsoft-access/)
Weil der neue Eintrag über ein Popup hinzu gefügt werden soll und nicht unten im Endlosformular. Dadurch soll man sich das scrollen ersparen.
Dann gehört der Code zum Positionieren auf den zuletzt angelegten Record in das Subformular und der Primarykey wird per Property oder Funktion aus dem Dialog-Formular ausgelesen, bevor dieses endgültig geschlossen wird. Der PK wird dann an die Prozedur im UF weitergeben, wo dann alles abläuft, um auf den neuen DS zu positionieren.
Knobbi38
Hallo,
ZitatWeil der neue Eintrag über ein Popup hinzu gefügt werden soll
Dann kannst du das Vorhaben direkt vom UFo aus steuern. Voraussetzung:
HFo und UFo sind über die ID im HFo verknüpft, PKs sind AutoWerte.
Platziere einen Button im UFo (Kopfbereich), - Name: cmdNeuerDS
Das Popup hat die gleiche DS-Herkunft wie das UFo.
(Luftcode, ungetestet)
Private Sub cmdNeuerDS_Click()
Dim lHFoID As Long
Dim lUFoLastID As Long
With Me
lHFoID = .Parent.NameDesIDFeldes
DoCmd.OpenForm _
FormName:="NameDesPopups", _
DataMode:=acFormAdd, _
WindowMode:=acDialog, _
OpenArgs:=lHFoID
'nach dem Schliessen des Popups
'UFo aktualisieren
.Requery
'navigieren zum neuen DS
DoCmd.GoToRecord acDataForm, .Name, acLast
'hier bin ich mir nicht sicher ob das zuverlässig ist *)
End With
End SubacFormAdd = Form wird mit neuem, leerem DS geöffnet
acDialog = Codeausführung wird an das Popup übergeben,
und erst nach Schliessen hier fortgeführt
OpenArgs: Da das Popup ja keine Verknüpfung zum UFo hat
muss der FK im Popup per Code gesetzt werden:
Private Sub Form_Open(Cancel As Integer)
Me.NameDesFKFeldes = Me.OpenArgs 'ID im HFo
End Sub*) Du könntest das UFo nach der ID absteigend sortieren, dann
hättest du den letzten (neuen) DS immer in der ersten Zeile,
und das Springen dorthin entfällt.
gruss ekkehard
Zitat von: Beaker s.a. am September 03, 2026, 12:23:21DoCmd.GoToRecord acDataForm, .Name, acLast
'hier bin ich mir nicht sicher ob das zuverlässig ist *)
Nein, das funktioniert so nicht, weil hier "nur" zum letzten DS eines Recordset, einer Abfrage oder Tabelle positioniert wird, was nicht zwangsläufig der aktuellste sein muss.
Um das Ganze zuverlässig zu gestalten, muss der zuletzt hinzugefügte PK aus dem Dialog-Formular an die aufrufenden Instanz zurückgegeben werden, wofür es mehrere Möglichkeiten gibt. Dieser Wert wird dann zum Positionieren herangezogen, aber wie gesagt, ganz so einfach wie in deinem Beispiel geht es dann doch nicht.
Im Anhang ein älteres kleines Beispiel, wo vielleicht etwas ungewöhnlich, eine Tempvar zur Übergabe der ID verwendet wird. Normalerweise würde man eine Property im Dialog-Formular dafür verwenden.
Knobbi38
Hallo Ulrich,
ZitatNein, das funktioniert so nicht,
Daher auch mein einschränkender Kommentar.
ZitatNormalerweise würde man eine Property im Dialog-Formular dafür verwenden.
Das ist aber an der Stelle doch schon geschlossen. Wie wäre es mit
.Requery
'navigieren zum neuen DS
lUFoLastID = DMax("IDImUfo", "DsHerkunftDesUFo")
.Recordset.FindFirst "FKFeld = " & lUFoLastID Wenn ich es aber in einem der anderen Posts des OP richtig gelesen habe,
hat er sein Projekt wohl inzwischen aufgegeben, und wir müssen uns damit
nicht mehr beschäftigen.
gruss ekkehard
Zitat von: Beaker s.a. am September 04, 2026, 12:58:47Das ist aber an der Stelle doch schon geschlossen.
Die Aufrufende Instanz öffnet und schließt das Dialog-Formular. Das Dialog-Formular schließt sich nicht selbst, sondern es blendet sich nur selbst aus ("hidden"), wodurch es den Fokus veriert. Dadurch wird der aufrufende Code weiter fortgesetzt und kann auf das versteckte Dialogformular zugreifen.
Es ist übrigens "Best Practice", wenn sich geöffnete Objekte, in diesem Fall das Formular, nicht selbst schließen.
Mit DMax den neuesten DS zu ermitteln kann funktionieren, muss aber nicht, denn bei konkurrierenden Zugriffen in einer DB kann schon zwischenzeitlich eine anderer DS hinzugefügt worden sein. Außerdem ist der PK nicht immer ein Autowert und könnte auch alphanumerisch sein. Ob DMAX dann die geeignete Funktion ist, muss abgeklärt werden. Da die Dialogform aber auf jeden Fall selber weiß, welchen PK der zuletzt hinzugefügte DS hat, braucht man keinen weiteren Zugriff auf die Tabelle machen.
Mal abgesehen davon, könnte das Hinzufügen ja auch abgebrochen werden und dann?
Gruß
Ulrich
Hallo,
ich würde in diesem Fall die ID hier überhaupt nicht zurückgeben. Sie ist eh die neueste ID, also einfach im aufrufenden Formular Requery und auf den letzten Datensatz springen. Immerhin könnte man in einem "Add"-Formular ja auch mehr als einen Datensatz eingeben.
Gruß
Christian
Zitat von: Bitsqueezer am September 04, 2026, 14:36:47und auf den letzten Datensatz springen.
Hier ist genau das Problem. Der letzte DS muss nicht der aktuellste sein.
Zitat von: Bitsqueezer am September 04, 2026, 14:36:47Immerhin könnte man in einem "Add"-Formular ja auch mehr als einen Datensatz eingeben.
Richtig und dann würde man die ID des zuletzt hinzugefügten DS zurückgeben, was ja nicht so falsch sein kann.
Knobbi38
Hallo,
für gewöhnlich sind IDs AutoIDs und PKs Clustered und daher wird auch die Sortierung zumeist auf ID eingestellt. In dem Fall ist der letzte Datensatz immer der Neueste.
Wenn man das Endlosformular nach einem anderen Feld sortiert, dann natürlich nicht, dann würde das Positionieren auf den zuletzt eingegebenen Datensatz vielleicht Sinn machen, wobei die anderen gleichzeitig eingegebenen dann "wild verstreut" sein können.
Gruß
Christian
Nach einem Autowert zu sortieren, gibt oft wenig Sinn - meistens wird der sogar gar nicht angezeigt. Ich dachte dabei eher an die üblichen Verdächtigen, wie z.B. Name, allg. Bezeichnungen usw. In der Praxis kommt es auch seltener vor, dass mehrere DS mit einem Dialog-Formular erfasst werden. Bei Unterformularen kann ich mit das schon eher vorstellen, aber dann wird dabei eigentlich nicht immer auf den neuesten DS positioniert, wenn überhaupt.
Ein paar Möglichkeiten, zu positionieren, sind ja jetzt aufgezeigt worden, alles andere ergibt sich dann aus der konkreten Problemstellung.
Gruß
Ulrich