Hey,

This is my first time on a VB forum so this may well be a long post, as there are many questions I've been wanting to ask over the years - sorry! Oh yeah, and I'm using VB6.

1) Is there a way to make "global" variables - for instance, a variable that can be accessed by any object on any form, other than by using an object's Tag or creating an invisible label? Just that my forms often tend to be very cluttered by the end...

2) Again about clutter... Am I missing something in terms of form organization? Say I want 10 timers, is there a better way to have them as a part of the form other than having them all sitting there in corner, as this very quickly clutters up the form?

3) Clutter again, but for code... I've heard about modules, which I believe may be what I'm looking for, but how do these work? Basically I want a global function that can carry out certain code whenever called...

4) This one relates to a game I'm making. Is there a way I can make multiple "frames" to a form? As in, have a side panel that's always there, but toggle between other frames that cover the rest of the screen? I don't think an MDI form is what I'm looking for as I want the whole thing in fullscreen, with no title bars, but something like that.

5) Again for my game... Is there a way to reference objects on another form, like so:

FormName.ObjectName(Index).Visible = True

But with the form name and object name as strings and the index as a variable? It doesn't seem to work...

==========================

That's all I can think of for now, but I expect there will be more.

Thanks,

- Danjb

1. you need to declare the variable as public in a module (.bas file).
2.timers are not visible at runtime ,so what is the problem.
3.right click on project ans add module. it has no UI but only code window.
4.what is the problem with MDI ?
5. that should work for you.

Thanks for the reply.

1) Ok, I'll try that, thanks.

2) No, but it's during editing that the timers really start to build up sometimes. And I'm not being such a neat-freak that I worry about the appearance of all the timers on the form, but they do become rather hard to manage is all... but I guess that's life.

3) Thanks again. My only immediate question is - how do you call a module?

4) I had a brief look at MDI and couldn't find a decent way of hiding the main form's title bar (borderstyle = none). Plus all my child forms' co-ordinates got messed up, but I expect that's just a result of me not knowing how to use MDI, and would be fixable.

5) I haven't managed to get it to work, but maybe I'm doing something wrong. Here's what I've got:

Dim EName As String
Dim ENumber As Integer
Dim strFormName As String

EName = EStats.Caption
ENumber = EStats.Tag

strFormName = ("Map" + Map.X.Caption + "i" + Map.Y.Caption)
strFrmName.EName(ENumber).Visible = False

I get an "invalid qualifier", with the last line highlighted. I've also tried tweaking it a little with:

Dim frm As Form
Set frm = Forms.Add(strFormName)

frm.EName(ENumber).Visible = False

But I get an "Object doesn't support this property or method" message.

3) Thanks again. My only immediate question is - how do you call a module?

You need to call the procedures and functions directly.

A module is just a container for procedures, functions or global declarations.
All of the functions in all modules in a program are visible/available to be run from anywhere, unless they are declared Private, which, as I understand it, means that they can only be run by procedures or functions stored in the same module.
I use Modules to contain all procedures that are not form related, like "ReverseString", "LuhnM10ModAdd" . . . you get the idea.
I use multiple modules for large programs. Usually PublicDeclarations, GeneralProcs, FileProcs DBProcs, etc.

To call a public function stored in a module, you would do something like: intNumber = LuhnMod10Add( intInput ). The function would be declared something like Public Function LuhnMod10Add (intInput As Integer) As Integer . . . code . . . End Function

You don't need to use the module name to access the function.

Private functions inside a module would be like

Private Function NewFileHandle() as Integer
Dim intNewFileHandle As Integer

intNewFileHandle = FreeFile(0)

NewFileHandle = intNewFileHandle

End Function

I call it from the function in the same module that opens files for IO, and is public. It's decared Private because no other function in the application needs to create file handles.

Hope this helps.

Thanks, that does indeed help, should make things a whole lot easier for me :)

Can anyone help out with question 5? That's really the big one...

I haven't managed to get it to work, but maybe I'm doing something wrong. Here's what I've got:

Dim EName As String
Dim ENumber As Integer
Dim strFormName As String

EName = EStats.Caption
ENumber = EStats.Tag

strFormName = ("Map" + Map.X.Caption + "i" + Map.Y.Caption)
strFrmName.EName(ENumber).Visible = False

I get an "invalid qualifier", with the last line highlighted. I've also tried tweaking it a little with:

Dim frm As Form
Set frm = Forms.Add(strFormName)

frm.EName(ENumber).Visible = False

But I get an "Object doesn't support this property or method" message.

you can't use string variables in place of an object name. I'm building a program that reads commands and scripts and can build new forms and objects after runtime- I have a generic form that is invisible at runtime but to create a new one I have a FORM() variable, as such

dim FORM(0 to 499) as Form

it's an array so I can create up to 500 forms all represented by a FORM(integer) variable. I have another variable to represent the number of loaded forms and whenever I load a new one the value is increased by one, so I would have to do something like this

set FORM(numberOfForms) = new frmFORM
numberOfForms = numberOfForms + 1

it's the same way with objects... except you either use the Object data type, or a specific type of object... for example

dim LABELS(0 to 499) as Label

or

dim Objs(0 to 499) as Object

. As for the strFormName = ("Map" + Map.X.Caption + "i" + Map.Y.Caption) thing, I guess you could create a variable like formInfo(0 to 500) where formInfo(0) is the number of loaded forms and formInfo(#) is the name of the form... you would have to do a loop I suppose to see if ("Map" + Map.X.Caption + "i" + Map.Y.Caption) matches the name in the formInfo variable, and then when it matches, take # and put it into the FORMS(#) reference, and use FORMS(#).OBJS(ENumber).visible = false or something. I don't know how much sense that made I know I did something like that in my program, but I finished that part of it last year sometime so it's not exactly fresh in my memory as of now.

Of course if that fails, you can ALWAYS use this code:

End

Thanks, I think I might be getting somewhere...

I've pinpointed a more specific problem. When Index is a variable and ObjectName is NOT, the line:

ObjectName(Index).Visible = False

Does nothing. I didn't realise this was a limitation before, but I think you kinda explained it. How exactly do I get round it? I tried "Dim ObjectName As Object" but it said "Object variable not set". How exactly can I get around this?

Thanks.

I've done that - or at least, the object in questions have indices assigned to them... they work in other instances so I assumed I'd made a working control array. Have I done something wrong?
If not, why doesn't it work?

ObjectName, if it's dim-ed as an object, has to actually point to an existing object. You can't just dim it and then try and make it invisible... say you want to create a label and have it referenced by ObjectName(Index)... you would do something like

set ObjectName(*a number) = new Label

or

set ObjectName(*a number) = new lblLabel1

or something, I've never done it loading an object out of nowhere so I don't know, I just have object arrays. After you use that "set" statement, ObjectName(*a number) will now point to the object you've loaded or set it to... but you can also just create an object array for the objects on the forms if you can reference them with numbers, so instead of using ObjectName(Index).visible just use the object directly, lblLabel1(Index).visible. I suppose it depends what you're trying to do, which to me is unclear.

This article has been dead for over six months. Start a new discussion instead.