views:

409

answers:

4

I have made an Access 2007 db. I will be writing some basic vba for the appropriate event of a form so that a modal form is displayed when the original form is opened. This isn't difficult, but that form will have a drop down box of IDs from a particular table. The user will select an ID, but I want the selected ID from this form to go back to the parent form. E.g.:

  1. Car form opened
  2. Event is fired to open a modal form

IDs for a FK to cars has to be selected from a combobox (eg ID of driver - for simplicity, lets assume one car can have many drivers but not vice versa so 1:n only)

There is a button to confirm the selection. On clicking this button, the form closes, and the selected Driver ID is automatically inserted into a DriverID textbox on the car form (probably will be read only).

The last step I am not sure about. How can that be done in VBA?

A: 

You could write a function that will display the form modally and then return the user selected value as a return value of it (similar to msgbox/inputbox).

EDIT: You could write a function such as following.

Function GetUserSelectedCarID() as string
dim myPopupForm as Form
set myPopupForm = new Form

myPopupForm.Show vbModal
GetUserSelectedCarID = myPopupForm.UserSelectedCar
End Function

UserSelectedCar is a property that stored the user selection on the popup form.

EDIT2: You could also add a property on popup form to see if the user clicked OK or Cancel. It will return blank from the above function, if user clicked Cancel.

shahkalpesh
You're posting VB code for an Access application. That is, your answer will not work.
David-W-Fenton
Which part of it won't work? Also, this is not complete code, just a hint on how to proceed. Could you explain please?
shahkalpesh
@David: You are right. One cannot translate the above VB code to Access.
shahkalpesh
@David: This is how I used to do it in VB. Access seems to have different style of Forms programming model (more useful in a databound scenario, I guess).
shahkalpesh
I translate VB code all the time to work within Access. But I don't recognize what you're doing there well enough to translate it.
David-W-Fenton
shahkalpesh
+2  A: 

To gain 'access' (get it?!) to controls on separate running forms you can use the following:

Forms("AnOpenFormName").Controls("ControlName") = value

Edit: I used the wrong brackets AMG!

keith
Or Forms!AnOpenFormName!ControlName
Tony Toews
Thanks Tony, very true- just a friendly warning though- if you've got spaces in your form or control names use the ["Form Name"], otherwise this is also very acceptable syntax!
keith
This answer is wrong. Square brackets are not usable where you use them. That is, Forms["AnOpenFormName"].Controls["ControlName"] can only work if you replace the square brackets with parentheses: Forms("AnOpenFormName").Controls("ControlName"). Also, because the default collection of a form is superset of the Fields and Controls collection, it's unnecessary to specify the controls collection when you use Tony's syntax unless you have a reason to disambiguate, so Tony's syntax (with brackets if you've inherited a bad app with spaces in the names of objects) is more efficient.
David-W-Fenton
+ 1 for the 'access' joke :D
Sophia
@David W. Fenton: "Tony's syntax...is more efficient" -- if you are experience a noticeable difference in performance then it's time to get a new machine, methinks :) Seriously, beware of micro-optimization e.g. see http://www.codinghorror.com/blog/archives/000181.html.
onedaywhen
I prefer the parens and string method. It allows you to replace the string with a variable. And I also agree with oneday...don't worry about optimization until performance becomes an issue.Seth
Seth Spearman
I'm not optimizing the performance of the app, but of THE PROGRAMMER. Forms!OpenForm!ControlName is the Access way to do things. You use the collections when you need something other than what that supports, e.g., as you note, when you're using a variable.
David-W-Fenton
And, BTW, the standard Access syntax Forms!OpenForm!ControlName can handle objects with spaces and funny characters in the names simply by surrounding them in brackets, as in Forms!OpenForm![Badly-Named Control].
David-W-Fenton
A: 

All of the above answers are good. I especially like the third way of wrapping this kind of functionlity into reusable function calls. The only thing I would add is do not CLOSE the modal form...otherwise you cannot get the selected value. Instead do me.visible=false.

So you do somethiing like this.

Public Function GetCArKey as Integer

dim intReturn as integer

docmd.openform "MyModalForm",,,,,,acdialog

'(the click event of the okay button of this form does me.visible=false...clicking Cancel will close the form.)

if isloaded("MyModalForm") then
   intReturn=Forms("MyModalForm").Controls("ControlName").Value
end if

GetCarKey=intReturn

End Function
Seth Spearman
You cannot use square brackets in VBA, as in Forms["MyModalForm"].Controls["ControlName"].Value, which should more efficiently be Forms!MyModalForm!ControlName (.Value is the default property of Access controls).
David-W-Fenton
oops...you are right david...I must have morphed the two syntaxes together.S
Seth Spearman
Edited above to correct it.
Seth Spearman
+1  A: 

This is one of the worst Access threads I've ever seen on StackOverflow.com, because every answer is wrong in at least some crucial aspect -- not a single one of them would actually run if you pasted them into VBA in an Access database.

The key principles here:

Open the dialog form modally (with the acDialog arguments)

Don't close it when the value has been confirmed, but instead set it's .Visible property to False.

Then in the calling form, read the value out of the hidden form, and then close it.

Something like this:

  DoCmd.OpenForm "dlgPickDriver", , , , , acDialog 
  If IsLoaded("dlgPickDriver") Then
     Me!DriverID = Forms!dlgPickDriver!cmbDriver
     DoCmd.Close acForm, "dlgPickDriver"
  End If

[IsLoaded is a Microsoft-provided function; I posted it here on StackOverflow recently, but would assume that the vast majority of Access developers writing VBA would have been using it forever]

I would recommend against having code that runs in the dialog form poke the data into the parent form because it's then impossible to use the dialog form in multiple locations. Having the dialog form know as little as possible about the context in which it's called is good programming practice. On the other hand, it's true the calling form needs to know the control name it's getting the value from, but that's a more sensible context than the other way around, in my opinion.

David-W-Fenton
wow nicely handled, you weren't rude or downvoted every answer or anything.
keith
I do believe that with your level of reputation you are able to edit incorrect answers if they contain blatant errors. This is a community for helping others and I think complaining about others answers is the wrong way to go about it.
csjohnst
I did not know I could edit, though now that you mention it, I see an EDIT link on the answers from others. But I'm not going to edit someone else's answer, because I don't want people editing mine. If my name is on the post, I want the content to be mine, and I'll be responsible for it. I feel I should extend the same to others.
David-W-Fenton
See the stackoverflow faq: "Like Wikipedia, this site is collaboratively edited. If you are not comfortable with the idea of your questions and answers being edited by other trusted users, this may not be the site for you." Also Joel Spolsky encourages users to add to existing answers rather than create a new one, wiki style.
onedaywhen
David,I admit that I free-form type my answers rather than copy/paste. It is quicker than finding the code that the user needs. My hope is that my answers point people in the right direction and that they can figure out any issues using the compiler errors. I think you should edit answers. Certainly editing my issues with the brackets in my answer would have been fine with me instead of a public commenting on the flaws.But then again...that would have denied you your feeling of superiority which I imagine is something you don't give up easily.Seth
Seth Spearman
I get downvoted every time I post code with even the slightest error, so I don't see why others shouldn't be held to the same standard. I don't someone fixing my errors -- I want to do the edits myself. I am only extending that same courtesy to you.
David-W-Fenton