New record only, when subform has records - ms-access

Five month ago, I got help with this problem:
Auto next number count to specific selection
I needed this auto count for daily reports at constuction sites.
Now my Problem is, the code
Dim NextNumber As Long
NextNumber = Nz(DMax("[raumBTBNR]", "[tbl_RaeumstellenErfassung]", "[raeumKostenstelleIDRef] = " & Me!KostenstelleAuswahl.Value & ""), 0) + 1
Me!Nummer = NextNumber
is placed at SelectingCostCentre_AfterUpdate ( Its working correctly )
The consequence:
If an employee wants to write the daily report:
He opens the program, selects the matching construction site he is at and the daily report number counts +1. So far so good...
If he is now leaving the program, or is clicking at another form without
adding employees at the activity form, Access saved the record in spite of this.
When he now wants to enter the record again, he has to type in his construction site again, but the auto report number isn't correct anymore, because he counts +1 again. This relates to an DoCmd.GoToRecord , , acNewRec at Form_Open
Form looks like this
What i want access to do is:
When opening the form, check if the last record (of the specific constr. site) at table
"Constructionsite entry" has entries at the table "activity log"
If True
DoCmd.GoToRecord , , acNewRec
Else
Open Last Record of the matching constuction site
EDIT:
or something like:
If no data entries at table "activity log" available
Recordset current delete
Apparently my VBA skills are very basic .. if any.
I looked at function DLookup, but don't know how to handle syntax with this type of problem.
EDIT2
Got a first step of a Solution:
If DCount("*", "tbl_RaeumstellEnerfassung", _
"RaeumKostenstelleIDRef=" & Me!KostenstelleAuswahl & " " & _
"AND raeumDatum =" & Format(Me!raeumDatum, _
"\#yyyy-mm-dd\#")) > 1 Then
If MsgBox("Die Räumstelle " & Me![KostenstelleAuswahl].Column(1) & " ist am " & Me![raeumDatum] & " schon eingetragen worden!" & vbCrLf & "Trotzdem fortfahren?", vbQuestion + vbYesNo) = vbNo Then
DoCmd.GoToRecord , , acLast
DoCmd.SetWarnings False
DoCmd.RunCommand acCmdDeleteRecord
DoCmd.SetWarnings True
Else
Cancel = False
End If
End If
He checks if a constructionsitenumber and a date is already entered.
What I would like to do is having a third MsgBox button as Dlookup or DLast, which shows me the last data related to this construction site.
DLookup("[raeumID]", "tbl_RaeumstellenErfassung", "[KostenstellenIDRef] ="Forms![frm_RaeumstellenErfassung]![KostenstellenAuswahl]")
apperently this isnt working .. more precisly I dont get this to work with a 3d button

Related

Many to Many Relationship problem with MS Access

I'm building an Access database for one of my University's administrators to track faculty information. There's a section for tracking what faculty is on what committee. This is a many to many relationship, as faculty can be on more than on committee and committees obviously have more than one faculty. Here's a screenshot of my relationship with a Junction Table. I have a demographic table (faculty) with a committees table and a junction table in between them:
What I want to have is a Multi Select List Box populated with committees I can select to populate the Junction Table. This works if I have the List Box set to only have one selection. If I have it set to Multiple selections, I get an error that says "You must enter a value in the jctDemographicsCommitteess.committeeID" field.
Does anyone know how to get this to work?
The List box is in a subform with the Record Source being the junction table. Also, when I set the ListBox up, I set "Store that value in this field:" to CommitteeID.
Let me know if you need more information!
I think that using a set of combo boxes on a continuous subform is the way to go here.
Start by creating a form that is based on the junction table In its properties, change the "Default View" from "Single Form" to "Continuous Forms". Add a combo box to this form, and set the Control Source to be CommitteeID, the RowSource to be based on the Committee table with the CommitteeID being the bound column. Set the Column Count to be 2, and the column widths to be "0;6".
Go back to your form that is based on the Demographics table. On the toolbox there should be an option to insert a subform/subreport. Add it to the detail section of the Demographics form, and when the wizard starts guiding you through, select "Use an existing form", select the sub form that you have just created, and when asked which fields to use to link, select "DEM_ID" to "DemographicID".
You should end up with something like this:
I've added a "Remove" button next to the combo box that simply has the following code:
CurrentDb.Execute "DELETE * FROM Junction WHERE DemographicID=" & Me.DemographicID & " AND CommitteeID=" & Me.CommitteeID
Me.Requery
Regards,
I went and grabbed some code I wrote a long time ago to help. I cleaned it up a little bit but I left things for you to figrue out on your own. Im sorry Im lazy, but you got free code out of it. Its thoroughly documented with inline notes/comments.
Happy coding!
Private Sub SampleListBoxLoop()
On Error GoTo SampleListBoxLoopErr
Dim arr(0 To 4) As String ' you might need to vchange this too
Dim lCol As Long, lRow As Long
Dim vbsql As String
With Me.ListBox
'I wrote this in Access97. Not sure if listbox looping is still backwards or not - find out!
'Looping through multi column list boxes is transposed.
'Which is why we loop through columns first
For lCol = 0 To .ColumnCount + 1 'needs to be plus due to column header
If .Selected(lCol) Then
'You'll need to change the next line based on your scenario.
'Since I gave you free code, you'lll have to figure this one out for yourself :P
For lRow = 0 To 4 'this is to 4 due to Ubound of array and not row count since row count changes with each run
'Assign to the array transposed so that it is filled in normally.
arr(lRow) = Nz(.Column(lRow, lCol))
Next lRow
End If
Next lCol
'needed for deselecting
For lRow = 0 To .ListCount - 1
.Selected(lRow) = False
Next lRow
End With
If arr(0) <> "" Then 'Cannot run this if empty array
'Build your SQL statements herre
CurrentDb.Execute vbsql, dbFailOnError
End If
Me.Requery
Me.ListBox.Requery
Me.Subform.Requery
Exit_Sub:
Exit Sub
SampleListBoxLoopErr:
If DBEngine.Errors.Count > 1 Then
'ODBC Error
For Each errany In DBEngine.Errors
msgbox "ODBCExecute: Err# " & errany.Number & " raised by " _
& errany.Source & ": " & errany.Description, _
vbCritical, "cmdExecuteAttached()"
Next errany
Else 'Access Error
msgbox "ODBCExecute: Err# " & ERR.Number & " raised by " _
& ERR.Source & ": " & ERR.Description, _
vbCritical, "cmdExecuteAttached()"
End If
GoTo Exit_Sub
Resume
End Sub

"Could not update; currently locked" Error caused by VBA?

I have inherited and MS Access application. There are many issues that could be changed within the application but unfortunately it was rushed to production and major redesign changes cannot be made.
I have split and given FEs to 6 different users. for the most part there does not seem to be many issues with this, however some users are getting the error "Could not update; currently locked" intermittently when they create a new record on one of the forms and enter into a subform to insert information into it. The main form contains a customers details and the subform contains information on the product that they have.
Optimistic locking being used throughout the application and this doesn't seem to be occurring because two users are updating a single record, as they will basically never being looking at the same records.
I think that the issue may be code that is being used to generate that customer ID. The form where the error occurs is (1_1)Customer Subform. There is a subform within that subform called (1_1_1)Product Subform. These are linked by a PID, which is present in each subform. When the mouse is clicked within the product subform, the application hangs for a few seconds before giving the error "Could not update; currently locked".
There is a button on the form that does the following:
Private Sub NewCustomerRecord_Click()
DoCmd.Close acForm, "1Main_IPCOR"
DoCmd.OpenForm "1Main_IPCOR", acNormal, "", "", , acNormal
Forms![1Main_IPCOR]![1IPCOR_Sform]![(1_1)Customer Subform].SetFocus
DoCmd.GoToRecord , , acNewRec
Forms![1Main_IPCOR]![1IPCOR_Sform]![CREATED_DATE] = Now()
Forms![1Main_IPCOR]![1IPCOR_Sform]![P_ID] = NewP_ID()
Forms![1Main_IPCOR]![1IPCOR_Sform].Form.Refresh
Exit_New_record_Click:
Exit Sub
Err_New_record_Click:
MsgBox Err.Description
Resume Exit_New_record_Click
End Sub
Private Function NewP_ID() As String
Dim strTemplate As String
strTemplate = Replace("CUSXX", "XX", Right(Year(Date), 2))
NewP_ID = Nz(DMax(Expr:="Right([P_ID], 5)", _
Domain:="[(1_1)_Customer]", _
Criteria:="[P_ID] Like '" & strTemplate & "*'"), "0")
NewP_ID = strTemplate & Format(Val(NewP_ID) + 1, "00000")
'Exit function now after successful incrementing or after error message
Exit_P_ID:
Exit Function
'If an error occurred, display a message, then go to Exit statement
P_ID_Err:
MsgBox "Error " & Err & ": " & Error$
Resume Exit_P_ID
End Function
What the function is doing is closing the main form and reopening it with a new ID so a new customer can be added.
Is there anything within the method that may be causing the record to be locked, and never unlocked?
Thanks!

Text Box to search records in access vba with a button Click()

I have seen this post Referancing form in DoCmd.SearchForRecord when using Navigation form - Access
And I have followed the #matt-hall solution. It works fine for me but it only searchs one record. I want to search every record that contains the criteria in the text box until the end of file. I have tried this
strsearch = DLookup("id_fosas", "memoria_vista1", "apelativo_fosa like" & "'%" & Me.Texto24 & "%'" & "or toponimos like '%" & Me.Texto24 & "%' or bando like '%" & Me.Texto24 & "%'")
With Me.Form
Set oRs = .RecordsetClone
oRs.FindFirst "id_fosas=" & strsearch
Do Until oRs.EOF
If oRs.NoMatch Then
MsgBox "Subform record not match to mainform record"
Else
oRs.MoveNext
Me.Bookmark = oRs.Bookmark
End If
Loop
End With
End Sub
But this procedure makes the form to go from first to last in one click and the gives an error. I want that every click takes you to every record that contains the criteria the user gives until the end of file. Can anybody help?
Thanks in advance!!

DoCmd.OutputTo fails intermitantly on different items within a list - Error 2501

The DoCmd.OutputTo command fails on different items within a list with Error 2501. Pictured below is my subroutine (much code removed). It loops through a list of vendors, sending invoices via email. We are running Access 365 with linked tables to a SQL Server 2008R2. Each time I run the routine, the code fails on a different supplier (sometimes no failures). There is one attachment per outgoing email. Each attachment has a unique file name. Attachments are written to the hard drive to avoid network lag. The report is fairly complex, sometimes calling functions which hit linked tables. Need help with how to make the function more robust to not fail.
Sub EmailInvoices()
InvFilePath = "C:\temp\"
On Error GoTo EmailInvoicesProblem
' loop through the list of suppliers, this invoice type, this date
For x = 1 To SupplierCount
SQLStr3 = "SELECT * from " & RptTypeDtlQry & WhereClause
DoCmd.OpenReport RptName, acViewDesign, , , acHidden
Set Inv_rpt = Reports(RptName)
Inv_rpt.RecordSource = SQLStr3
Inv_rpt.Caption = "Supplier " & rst!supplier_code & " " & InvType & " Invoices"
DoCmd.Close acReport, RptName, acSaveYes
'image the invoice, attach the invoice to the email, and then delete the image
InvFileName = InvFilePath & rst!supplier_code & ".pdf"
TryAgain:
DoCmd.OutputTo acOutputReport, RptName, acFormatPDF, InvFileName, False
objOutlookMsg.Attachments.Add (InvFileName)
fso.DeleteFile (InvFileName)
' send all the invoices of this supplier, this invoice type, this date in a single email.
objOutlookMsg.Send
NextSupplier:
rst.MoveNext
Next x
rst.Close
Exit Sub
End Sub 'EmailInvoices()
Perhaps the report file name has invalid characters? (would have posted this as a comment but don't have enough points)
Can you put some Debug.Print statements in to show what the variables are when it works and when it doesn't?

Microsoft Access - Saving New Record to Linked Database

I am creating a user interface based off of one internal and two linked (external) Access datasheets in Access 2013.
Two of the fields on my UI are combo boxes that read from the linked datasheets and display the options. This is so that the entries for suppliers and material types are called-out consistently and typos are avoided. However, I would like to add the following functionality:
-If a new value is entered into the combo box the user will be prompted to fill out the necessary information on the new value. This information will subsequently be saved to the appropriate linked datasheet.
How would I go about setting up the prompt from the combo boxes themselves? It would require Access to open a form or sub-form that will, in turn, save to the linked datasheet.
I'd prefer it to be automatic, instead of end-user prompted so that it isn't skipped. It's been years since I played around with VB, so I would like to avoid that if possible and use Access' built-in functions (even if it requires a little more time). Thank you in advance!
Alright, so I was able to do it after researching the "OnNotInList" function and a little VB code.
In the OnNotInList section of the 'Event' properties sheet, I chose 'Code Builder' and entered the following:
Private Sub Supplier_NotInList(NewData As String, Response As Integer)
Dim ctl As Control
Dim dbsCustomerDatabase As Database
On Error GoTo Supplier_NotInList_Err
Dim intAnswer As Integer
Dim strSQL As String
intAnswer = MsgBox("The supplier " & Chr(34) & NewData & _
Chr(34) & " is not currently listed." & vbCrLf & _
"Would you like to add it to the list now?" _
, vbQuestion + vbYesNo, "Spire Manufacturing Solutions")
' Adding the new entry to the list:
If intAnswer = vbYes Then
strSQL = "INSERT INTO CustomerList([CustomerName]) " & _
"VALUES ('" & NewData & "');"
DoCmd.SetWarnings False
DoCmd.RunSQL strSQL
DoCmd.SetWarnings True
MsgBox "The new supplier has been added to the list." _
, vbInformation, "Spire Manufacturing Solutions"
Response = acDataErrAdded
' Opening the Supplier datasheet to add details
' to the new entry:
MsgBox "Opening Supplier database for new entry..."
DoCmd.OpenTable "CustomerList", acViewNormal, acEdit
End If
Supplier_NotInList_Exit:
Exit Sub
Supplier_NotInList_Err:
MsgBox Err.Description, vbCritical, "Error"
Resume Supplier_NotInList_Exit
End Sub
This allowed me to automatically prompt the user to add the details for a new supplier if they enter a new supplier name. Or, cancel the entry if they simply misspelled it. I'd quite forgotten how versatile VB was. Thank you all for your assistance in getting me headed in the right direction!