luni, 10 februarie 2020

DoCmd.GoToRecord doesn't work on subforms

Presupun că orice programator VBA Access a simțit la un moment dat nevoia unei comenzi de genul DoCmd.GoToRecord , , acNext care să acționeze într-un subformular. Dar, nu merge. O comandă de acest tip va genera o eroare ca cea de mai jos:

I suppose that any VBA Access programmer at one point felt the need for a command like DoCmd.GoToRecord , , acNext, to work in a subform. But it is not working. An order of this type will generate an error like the one below:




Această eroare apare indiferent de felul în care este apelat subformularul, așa
This error occurs regardless of how the subform is called, this way

DoCmd.GoToRecord acDataForm, "Table2 subform", acNext

sau așa
or that way

DoCmd.GoToRecord acDataForm, Forms!Form1![Table2 subform].Form.Name, acNext


Astfel, trebuie găsită o altă cale.
Să presupunem că avem un formular care conține două subformulare și avem nevoie să scriem într-un subformular și în acealși timp să vedem rezultatul în al doilea subformular. Voi pune mai jos codul și felul în care trebuie construite formularele.

Thus, another way must be found.
Suppose we have a form that contains two subforms and we need to write in a subform and at the same time see the result in the second subform. I will put below the code and the way in which the forms must be build.

Mai întâi, voi construi două tabele Table1 și Table2 astfel:
First, I will build two tables Table1 and Table2 as follows:







Apoi, voi construi un formular Form1 și două subformulare corespondente celor două tabele, Table1 subform și Table2 subform. Acestea vor putea arăta astfel:

Then I will build a Form1 form and two subforms corresponding to the two tables, Table1 subform and Table2 subform. They will look like this:



Sursele datelor pentru Tabel1 subform și Tabel2 subform sunt
SELECT [Table1].[ID], [Table1].[Field1] FROM Table1
respectiv 
SELECT Table2.Table1_ID, Table2.Table1_Field1 FROM Table2

Data sources for Table1 subform and Table2 subform are
SELECT [Table1]. [ID], [Table1]. [Field1] FROM Table1;
respectively
SELECT Table2.Table1_ID, Table2.Table1_Field1 FROM Table2;


Ca să fie evitate orice erori de introducere, Table2 subform nu trebuie să permită scrierea. Puteți seta proprietățile controlului care conține subformularul Enabled = No sau Locked = Yes.

In order to avoid any input errors, Table2 should not allow writing. You can set Enabled = No or Locked = Yes for the control properties that contain the subform.





Acum, obiectele bazei de date vor arăta astfel:
Now, the database objects will look like this:




În Module1 voi scrie codul pentru resetarea tabelelor după fiecare încercare:
In Module1 I will write the code to reset the tables after each attempt:

Option Compare Database
Option Explicit

Sub BackCounter()
With CurrentDb
     .Execute "DELETE FROM Table1"
     .Execute "DELETE FROM Table2"

     .Execute "ALTER TABLE Table1 ALTER COLUMN ID COUNTER (1,1)"
End With
End Sub


În modulul subformularului Table1 subform voi scrie următorul cod, pentru evenimentele Form_AfterInsert, Form_Current și Form_Delete:
In Table1 subform VBA module I will write the following code for Form_AfterInsert, Form_Current and Form_Delete events:

Option Compare Database
Option Explicit

Private Sub Form_AfterInsert()
With Forms!Form1![Table2 subform].Form
     .Recordset.AddNew
     !Table1_ID = Me!ID
     !Table1_Field1 = Me!Field1
     .Refresh
End With
End Sub

Private Sub Form_Current()
'there is an error with OnOpen event, because Table2_subform is not initialized yet
On Error GoTo ErrEx
With Forms!Form1![Table2 subform].Form.Recordset
     .MoveFirst
     .Move Me.Recordset.AbsolutePosition
End With

ErrEx:
End Sub

Private Sub Form_Delete(Cancel As Integer)
Forms!Form1![Table2 subform].Form.Recordset.Delete
'after Delete, Table2 was going to the first record
'so, to make sure the both tables are on the same record, put the Table1 on the first record:
Me.Recordset.MoveFirst
End Sub


Rezultatul arată astfel:
The result looks like this:



Când se va introduce rând nou în Tabel1 subform, se va adăuga și în Tabel2 subform. Dacă se va șterge un rând din Tabel1 subform, în Tabel2 subform va fi șters rândul corespunzător.

When a new row is inserted into Table1 subform, it will be added to Table2 subform as well. Deleting a row from Table1 subform will delete the corresponding row in Table2 subform.



























Niciun comentariu:

Trimiteți un comentariu