Vba global variable declaration - vba

In vba how to declare a global variable, which will be assigned from userform, but then used inside various sub procedures, functions in different modules?
Declaration of var (dim) above in module does not let from other modules to call the value of variable

You need to declare the variable on top of the first module you are using (outside subs and functions) and add the Option Explicit line above, like this :
Option Explicit
Public (Variable Name) As (Variable Type)
EDIT : Since I can't comment under your answer I'll try my best here.
If I understand right you have a "main" module where you do all your procedures and one userform where you gather data. Then initialize a public variable on top of the "main" module and use it in your userform.

Related

How to create a global function and pass variables to it in VBA Access?

In my program I am trying to cut down on repetitive code by putting it into global functions.
In my current setup I am calling the function like:
Call [Global variable].Close
(global variable is the name of the class module).
This function is looks like;
Public Function Close()
DoCmd.Close
Cancel = True
End Function
Unfortunately this wont compile properly. What am I doing wrong?? (As an aside I also want to pass variables to and from this function and want to know how this would be done).
Thanks for your help.
If you're using a class module, you need an instance of that module before you can call its members. That requires either creating the class module as pre-declared (which involves exporting the code, editing in Notepad, and re-importing), or creating an instance with the New keyword:
Dim myClassInstance As MyClass
Set myClassInstance = New MyClass
myClassInstance.Close
But, depending on your use-case, you might better off with the function being available in a standard module - then you can just call it from anywhere, including from within a query.

Make a global variable in Visual Basic for Applications

In VBA for Access, how do I make a global variable that I can access and change anywhere?
You can declare a variable at Global scope by declaring it in a Standard Module or a predeclared class module such as a Worksheet, UserForm or PreDeclared class, using the Public keyword:
Public myVar As String
You can also declare a Global variable using the now deprecated, but still valid Global syntax, which is functionally the same as Public
Global myVar As String
But note that declaring a variable with Public or Global will make the variable accessible across your entire project AND to any project that refers to that project, and even if your project is protected, a user could still query the variable from the Immediate window.
If you must have a variable that is available across your project, but only that project, then you should declare the variable in a standard module, and include an Option Private Module statement to make the module private to the project, but its variables as Public to the project only.
Option Private Module
Public myVar As String

Access Global not working

I have a Global Variable called EmployeeID. I set this by calling a function:
Global EmployeeID As Integer
Public Sub init_Globals(emp As Integer)
EmployeeID = emp
End Sub
On the main form, I used:
MsgBox EmployeeID
from a button and it works just fine; but the funny thing is when I use this from a subform it returns a 0:
I might add that this is a Continuous Form as well.
Private Sub cboWhichDate_AfterUpdate()
Me.txtEmployee = EmployeeID
End Sub
A "global" variable can only be "global" if its scope is global. Sticking a Global access modifier to a field declared in a class module doesn't make it global.
In fact, the Global keyword is deprecated, and is completely replaced/superseded by the Public access modifier.
What matters is the variable's scope. If that declaration is located in a class module (a form's code-behind is essentially a class module), then all you've done is declare a public instance field; you can only access the value via the object instance that owns it.
Dim MyObject As New MyForm
MyObject.EmployeeID = 42
MsgBox MyObject.EmployeeID
To make a global variable, add a standard module (.bas) to your project, and declare it there.
Public EmployeeID As Integer
Now everyone everywhere can access EmployeeID, because it's scoped to a module (i.e. not an instance of an object), and its accessibility is public.
That said, global variables are evil and can easily lead to unmaintainable spaghetti code; Consider passing values as parameters instead.

What is a public object module in VBA?

I'm trying to get as close to function pointers / abstract classes as I can in VBA.
I have a class called VerificationManager and verifies a bunch of cells in a couple of spreadsheets match up. This will be done in different ways depending on the information and spreadsheets being used with it.
I'd like to be able to make the code reusable by specifying a method to be called in a string using the Application.Run function. So I can rewrite the function that changes.
Now if I was using Java or C# I would be able to extend an abstract class and rewrite the internals to the function. If I was using JavaScript I could store a function in a variable and pass the variable to the class and call it from there.
Inside my class I have a public property called "verificationModule" which I set to the name of the function I want it to call.
Sub VerifyWorkLocations(empLoc As EmployerLocation)
...
For i = 0 To empLoc.numOfEmp
Application.Run verificationModule, empLoc.taxdescmatch, empLoc.employees(i)
Next i
...
End Sub
However, when I try to call Application.Run I receive the following error:
Compile Error:
"Only user-defined types defined in public object modules can be
coerced to or from a variant or passed to late-bound functions"
I already tried placing my User Defined Types in a Class Module but it basically said that a class module was the wrong place for a type.
The error comes from full-fledged VB, where you can create an ActiveX dll project, create a public class there and put a UDT into that class.
In VBA, you use classes instead of UDTs when you need to coerce to or from a variant.
So just declare a class with all the fields you have in your UDT, and delete the UDT.
Alternatively, create a DLL in VB6 that would only contain the declaration of the type, and reference that dll from VBA. Or, if you're comfortable with IDL, just create a TLB file directly.
To add a module to a VBA application, try the following steps (assuming you've already entered the VBA IDE):
From the Project Explorer, right-click on your project.
Click on "Insert..."
Select "Module."
If no modules exist, a new folder within the VBA/Excel project will be created, named "Modules," and a module with a default name of "Module1" will be created.
Double-click the module to open it in the source editor.
This is where you have to place UDT's. I believe this is because of the difference in the way such types are stored internally by VBA relative to the COM-style structure of elements/objects declared/manipulated as Classes...

How to specify a code module as the "Object Ref" parameter in VB.Net CallByName?

I am trying to call a public subroutine from a Windows form based on a string variable containing the name of the subroutine. The subroutine is a procedure in a code module and works fine when called by using the procedure name directly.
The VB.net function CallByName should work, but I don't know how to specify the module name as the "Object Ref" parameter.
In the code shown, "ReportLibrary" is a module containing the public sub with the name contained in the string strReportProcedure. This results in the following error helper:
The Help says this about the ObjectRef parameter:
ObjectRef
Type: System.Object
Required. Object. A pointer to the object exposing the property or method.
What am I missing or is it just not possible to call a routine from a module using CallByName?
CallByName will not work for code in VB.Net modules since the first parameter requires an object. You need to move the methods into a class, then create an instance of the class in order to make CallByName work.
Hmmm, I think the problem is somewhere else.
I think you haven't declared a variable like this:
Dim RL as NEW Reportlibrary
And after declaring it, use this:
CallByName(RL, strReportProcedure , CallType.Method , blnPreview)
Probably the problem was in declaration, because (in your case) your class doesn't let you access to your library's subroutines. That's why you need to declare "as New ReportLibrary".
Good Luck !
Dim object As NEW Reportlibrary and then just use that Object.