Using query yes/no field for checkbox record source? - sql

First of all, you start with a form named LoginF. Once you choose your login ID, and password; and log in it takes data from the table LoginIntoT for the login ID you chose, and creates a query with said data using this code:
On Error Resume Next
DoCmd.DeleteObject acQuery, "IsAdminQ"
On Error GoTo Err_LoginBtn_Click
Dim qdef As DAO.QueryDef
Set qdef = CurrentDb.CreateQueryDef("IsAdminQ", _
"SELECT IsAdmin " & _
"FROM LoginInfoT " & _
"WHERE EmployeeID = " & LoginCmBx.Value)
Exit_LoginBtn_Click:
DoCmd.Close acForm, "LoginF", acSaveNo
DoCmd.OpenForm "MenuF"
Exit Sub
Err_LoginBtn_Click:
MsgBox Err.Description
Resume Exit_LoginBtn_Click
From there in that query after you log in is only 1 column and 1 row; meaning one piece of data. This data is a yes/no field which is either Yes or No depending on who you logged in as.
On the form it opens after you click the login button it has a logout button. The logout button brings you to the previous login form, and deletes the query (IsAdminQ).
What I am trying to do is attach a yes/no button on a form to take that data, and output if it's yes or no on the query.
I've tried putting this in it's control source:
=[IsAdminQ].[IsAdmin]
Though what that does is output it as a filled in square instead of a checkmark or empty. I have triple state set as no.
How would I attach the checkbox to the query so if the data says yes, then it's a check mark and if it says no it is an empty box?

I understand you.
"On the form it opens after you click the login button it has a logout button", we call it frmLogout. You shall do this:
Solution I:
frmLogout.RecordSource = "IsAdminQ"
Then for your checkbox named MyCheckbox, we set it this:
Me.MyCheckbox.ControlSource = "IsAdmin"
You cannot use this:
Me.MyCheckbox.ControlSource = "[IsAdminQ].[IsAdmin]" ' <= here it's impossible.
Solution II:
On the form frmLogout without setting IsAdminQ as .RecordSource,
In a Public Module, insert this:
Function GetLoginStateIsAdmin()
'
Dim rst As DAO.Recordset
Set rst = CurrentDb.OpenRecordSet("IsAdminQ")
GetLoginStateIsAdmin = Nz(rst(0), False)
Set rst = Nothing
'
End Function
Then in the private module of any form, as frmLogout:
Private Sub Form_Open(Cancel As Integer)
'
Me.MyCheckbox.Value = GetLoginStateIsAdmin()
'
End Sub
Set it in addition in design mode:
Me.MyCheckbox.TripleState = false
And check also if the query IsAdminQ has been successfully created in the login step. And open it in Access Navigation Pane by double-clicking on it. And see the value of the query.

Related

prevent duplicates when passing values between two forms (with Args)

I have two forms: transfert Form with its subform and intransfert Form. I am using
DoCmd.OpenForm "intransfert", , , , acFormAdd, acDialog, Me!Text83
(where text83 is =[transfertasubform].[Form]![transfertadetailid] under
Private Sub Command78_Click()
in transfet form and
Private Sub Form_Load()
On Error Resume Next
If Me.NewRecord Then Me!trnrin = Me.OpenArgs
in intransfet form. intransfert form is based in transfertdetailquery. i wont to prevent passing text83 value more then one time
i tried to explain my problem and expect a help to prevent duplicates when used Arge
assuming trnrin is the name of a variable in your record source. assuming you mean that you want to avoid adding two records where trnrin has the same value and the user sent the same open args twice. assuming trnrin is also the name of a control in the detail section of the intransfert form.
'form load only runs when the form is opened so you have to close the form to pass new args
'but you can just move the same code to a button or whatever
Private Sub IntransferForm_Load()
If Len(Me.OpenArgs) > 0 Then
Me.txtBoxintheHeader = Me.OpenArgs 'the load event is the right place to set controls
'most of this code is to check if there is already an instance where trnrin = the OpenArgs in the record source
Dim lookedupArgs As String
lookedupArgs = Nz(lookedupArgs = DLookup("trnrin", "MyTable", "trnrin = " & "'" & Me.OpenArgs & "'"), "ValuethatisneveranArg")
If lookedupArgs = "ValuethatisneveranArg" Then
'Debug.Print "trnrin = '" & Me.OpenArgs & "'" 'note the string delimiters
'Me.trnrin = Me.OpenArgs 'this surprisingly works but will break easily and doesn't handle complex cases
Dim rs As Recordset
Set rs = Me.Recordset 'if recordset is bound to a table then table will also be updated.
'you can also bind to the table directly but you may need to call me.requery to show the changes
rs.AddNew
rs!trnrin = Me.OpenArgs
rs.Update
End If
End If
End Sub

CommandBarControl executing .OnAction before click on button

The code in my question in inspired by the solution in the answer provided by this question:
How to add a menu item to the default right click context menu
I have a ListBox object on a form showing a list of Actions. I want the user to be able to right click an item of this list to show a contextual menu where he can either :
open a new form where he can view and edit the action (corresponds to the execution of a double click event on the list item)
delete the item from the list
Private Sub List_actions_MouseUp(Button As Integer, Shift As Integer, X As Single, Y As Single
'set up commandBar
Dim combo As CommandBarControl
'Since it may have been defined in the past, it should be deleted,
'or if it has not been defined in the past, the error should be ignored
On Error Resume Next
CommandBars("RCActionContextMenu").Delete
On Error GoTo 0
'Make this menu a popup menu
With CommandBars.Add(Name:="RCActionContextMenu", Position:=msoBarPopup)
Set combo = .Controls.Add(Type:=msoControlButton)
combo.BeginGroup = True
combo.Caption = "View action" ' Add label the user will see
combo.OnAction = "List_actions_DblClick" 'Add the name of a function to call
Set combo = .Controls.Add(Type:=msoControlButton)
combo.Caption = "Delete action"
combo.OnAction = DelAction()
End With
If Button = acRightButton Then
DoCmd.CancelEvent
CommandBars("RCActionContextMenu").ShowPopup
End If
End Sub
Public Function DelAction()
If Not IsNull(Me.Controls("RCActionContextMenu").Column(0)) Then
CurrentDb.Execute "DELETE * FROM T_ACTIONS " & _
"WHERE ID = " & List_actions.Column(9) & ";"
MsgBox "Action supprimée", vbInformation, "Information"
End If
End Function
Private Sub List_actions_DblClick(Cancel As Integer)
Dim vStatus As String
'Get the record's index of the action
rowNumber = Me.List_actions.ListIndex + 1
id_action = List_actions.Column(9, rowNumber)
vStatus = List_actions.Column(5, rowNumber)
'Open the action
DoCmd.OpenForm "F_ACTIONS", , , "[ID] = " & List_actions.Column(9)
Form_F_ACTIONS.Effective_date.Visible = Effdatefunction(vStatus)
End Sub
The problem i get is that the DelAction() function is executed before the pop-up is shown and i get a run-time error 2465 stating "Microsoft Access can't find the field 'RCActionContextMenu' referred to in your expression."
I've tried repalcing the row combo.OnAction = DelAction() by combo.OnAction = "DelAction". It results in the conextual menu showing itself but nothing happens when i click on either button.
There are a few problems here.
combo.OnAction = DelAction()
This will call the function, as you have seen. You need to set a string here.
combo.OnAction = "DelAction()"
This still won't work, since DelAction() is in your form module.
Either move the function to a public module, with parameters, or hardcoding the object names there,
combo.OnAction = "DelAction(""MyFormName"", ""List_actions"")"
or try (not sure if this works):
combo.OnAction = "Form_YourFormName_DelAction()"
It's the same with "List_actions_DblClick" - the function needs to be called "from the outside", like from the Immediate window.
If Not IsNull(Me.Controls("RCActionContextMenu").Column(0)) Then
You context menu command bar isn't a control, what you want is the list box:
If Not IsNull(Me.Controls("List_actions").Column(0)) Then
or simply
If Not IsNull(Me!List_actions.Column(0)) Then
After deleting an action, you need to requery the listbox.
CurrentDb.Execute "DELETE * FROM T_ACTIONS " ...
Me!List_actions.Requery

MS Access vba save button error 3021

For various reasons, I want to set up a custom button on my forms to save the current record. I use a navigation form and want to trigger the same process (integrity-checks, user input etc.) whenever the entry is saved, thus whenever the user presses the "save"-button or switches to another form. The user will conditionally be asked to confirm the process and is thus able to cancel it as well.
Everything is running smoothly with one really odd and annoying exception: Whenever I click the save button on a new record and prompt a message within the "BeforeUpdate" event, I receive
RTE 3021 ("no current record")
Without the MsgBox, everything is fine. Even more strange:
When I trigger the save process by switching to another form using the navigation form (or simply press "outside" the form used for data entry), everything is fine as well.
Here is a minimalistic example (similar results with DoCmd.Save, Requery or acCmdSaveRecord):
Private Sub vt_save_Click()
Me.Dirty = False
End Sub
Private Form_BeforeUpdate(Cancel As Integer)
Cancel = True
MsgBox "Test"
End Sub
Any ideas? I simply can't wrap my head around that error.
You could maybe try to run a query using the values in the form while checking if the record exists or not.
Is there a primary key on the table? if so, the primary key will be your focal point.
Private Sub vt_Save_Click()
dim rst as DAO>Recordset
Dim strSQL as String
Dim strID as string
strID = me.YourPrimaryKeyField
strSQL = "SELECT * " & _
"FROM YourTableName " & _
"WHERE (((YourTableName.YourFieldName) =" & me.PrimaryKeyField & "));"
set rst = currentdb.openrecordset(strsql)
if rst.recordcount = 0 then
currentdb.execute "INSERT INTO YourTableName ( List All Fields to Add ) " & _
"SELECT List All Field controls with values to add;"
End IF
'Anything else you want the code to do from here
EndCode:
If not rst is nothing then
rst.close
set rst = nothing
End IF
End Sub
Repeat this process for the Form_LostFocus() event. If you want to make it easier, make this code a module and call within both event triggers on your form.
If this doesn't work please let me know and I will be happy to further assist.
The most straight forward and reasonable solution is to use an Error Handler - which I ignored so far tenaciously.
Private Sub save_Click()
On Error GoTo Err_Handler
Me.Dirty = False
Exit_Here:
Exit Sub
Err_Handler:
If Err.Number = 2101 Then
'ignore or message
Else
MsgBox Err.Description
End If
Resume Exit_Here
End Sub

More info when you click a field in a subform table in pop up form

I am trying to get a window to popup when you click that small box beside a field in my subform table, and then click the button "more info". This form would pop up with all the extra information about that record; in text boxes so you can edit it. On this form it pops out, it only has a button that has back and when you click back, it saves all the changes made in the text boxes in the record you were viewing more information about... and updates it. It then brings back up the previous form, and updates the subform on that form so it shows all changes made to the table. I am not looking for the More Info button to show more info for all records. I am looking for it to bring up more info for that one record you selected only, and to get more info on another, you must click back and select a new one. How would I go about setting up the More Info button so it pops up the new form with the information?
For an example of what I mean by pressing the more info button, here is a picture:
In the picture, it is a table. Clicking that small space highlights the whole record, and you are able to push DEL on your keyboard to delete the record (though that doesn't matter in the case, just pointing out it's a table.)
Code I have in my More Info button:
Private Sub CustomerMoreInfoBtn_Click()
On Error Resume Next
DoCmd.Close acForm, "CustomerInfoF"
DoCmd.DeleteObject acQuery, "CustomerMoreInfoQ"
On Error GoTo Err_CustomerMoreInfoBtn_Click
Dim qdef As DAO.QueryDef
Set qdef = CurrentDb.CreateQueryDef("CustomerMoreInfoQ", _
"SELECT * " & _
"FROM CustomersT " & _
"WHERE CustomerID = " & txtCustID.Value)
DoCmd.OpenForm "CustomerInfoF"
Exit_CustomerMoreInfoBtn_Click:
Exit Sub
Err_CustomerMoreInfoBtn_Click:
MsgBox Err.Description
Resume Exit_CustomerMoreInfoBtn_Click
End Sub
Code in the form it self:
Private Sub Form_Close()
On Error Resume Next
DoCmd.DeleteObject acQuery, "CustomerMoreInfoQ"
End Sub
In the below example your button is named cmdMoreInfo. When you click on the button it creates the MyCustDetail query based on the value of the customer id. Then it opens the frm_CustDetailEdit form. Set the forms Record Source to MyCustDetail.
In order to be able to create the query it must not already exist. Therefore, I check beforehand and delete it if it exists. Also, when closing the main form it also will delete the query since it would no longer be needed anyway.
Private Sub cmdMoreInfo_Click()
On Error Resume Next
DoCmd.Close acForm, "frm_CustDetailEdit"
DoCmd.DeleteObject acQuery, "MyCustDetail"
On Error GoTo Err_cmdMoreInfo_Click
Dim qdef As DAO.QueryDef
Set qdef = CurrentDb.CreateQueryDef("MyCustDetail", _
"SELECT * " & _
"FROM tbl_Customer " & _
"WHERE CustomerID = " & txtCustID.value)
DoCmd.OpenForm "frm_CustDetailEdit"
Exit_cmdMoreInfo_Click:
Exit Sub
Err_cmdMoreInfo_Click:
MsgBox Err.Description
Resume Exit_cmdMoreInfo_Click
End Sub
Private Sub Form_Close()
On Error Resume Next
DoCmd.DeleteObject acQuery, "MyCustDetail"
End Sub

Print Dialog in MS-Access

I want to open a print dialog box. I haven't programmed in VB for a decade and I am more than a little rusty.
I got a copy of an MS Access VB script that selects an MDB file and then prints only one copy. My thought process was:
Open up a dialog box;
Select the printer;
Type in number of copies;
Print.
Currently, the portion of the original script I want to modify is:
[SQL query above this]
....
' Open form
Dim rs As DAO.Recordset
Set rs = db.OpenRecordset("select##identity")
Debug.Print rs(0)
Dim q As String
q = "transfer_id=" & rs(0)
DoCmd.OpenForm "Transfer Report", acNormal, , q, ,acDialog
DoCmd.PrintOut
...
[End If, End Sub, etc.]
This only prints out one instance of the report and the company does not have the ability to print out other copies at the same time. Since it is in the field, they don't have access to a copier but still need multiple copies.
One answer I found, by David-W-Fenton (thank you!), shows how to create a dialog box; Would the following script accomplish what I want to do? And, how do I add a portion to the dialog box to specify how many copies to print?
...
Dim varPrinter As Printer
Dim strRowsource As String
Dim q As String
Dim rs As DAO.Recordset
Set rs = db.OpenRecordset("select ##identity")
Debug.Print rs(0)
If Len(Me.OpenArgs) > 0 Then
q = Me.OpenArgs
Me.Tag = q
For Each varPrinter In Application.Printers
strRowsource = strRowsource & "; " & varPrinter.DeviceName
Next varPrinter
Me!cmbPrinter.RowSource = Mid(strRowsource, 3)
' first check to see that the report is still open
If (1 = SysCmd(acSysCmdGetObjectState, acReport, q)) Then
With Reports(q).Printer
Me!cmbPrinter = .DeviceName
Me!optLayout = .Orientation
End With
Me!txtPageTo = Reports(q).Pages
End If
End If
Public Function PrintReport(q As String) As Boolean
q = "transfer_id=" & rs(0)
' open report in PREVIEW mode but HIDDEN
DoCmd.OpenReport q, acViewPreview, , , acHidden
' open the dialog form to let the user choose printing options
DoCmd.OpenForm "dlgPrinter", , , , , acDialog, q
With Forms!dlgPrinter
If .Tag <> "Cancel" Then
Set Reports(q).Printer = Application.Printers((!cmbPrinter))
Reports(q).Printer.Orientation = !optLayout
Application.Echo False
DoCmd.SelectObject acReport, q
DoCmd.PrintOut acPages, !txtPageFrom, !txtPageTo
PrintReport = True
End If
End With
DoCmd.Close acForm, "dlgPrinter"
DoCmd.Close acReport, q
Application.Echo True
End Function
Here is a late reply, some times it may help others.
In order to open the print dialogue:
Place a command button for PRINT on the report, and write the code as below.
Private Sub CmdbtnPrint_Click()
DoCmd.RunCommand acCmdPrint
End Sub
Change the 'Display When' property of button to 'Screen Only'.
Open the report in 'acViewReport' view mode.
Click the PRINT command button, and the systems print dialogue box will be open. Set the parameters and print the report.
Check the documentation about the PrintOut method:
http://msdn.microsoft.com/en-us/library/office/ff192667.aspx
In your original script to modify, just add the Copies argument to the DoCmd.PrintOut statement, like:
DoCmd.PrintOut Copies:=x
where x is a variable representing the number of copies you want to print.
Reviewing the documentation for the DoCmd.OpenForm method,
http://msdn.microsoft.com/en-us/library/office/ff820845.aspx
I don't think the code you have can allow a user-input for the number of copies. I do not program in Access, but I'm certain there are other ways to allow user input at run-time. In Excel/PowerPoint we would use an InputBox or a UserForm.
I think you can use an InputBox in Access:
http://office.microsoft.com/en-us/access-help/inputbox-function-HA001228856.aspx