Link to home
Start Free TrialLog in
Avatar of oldbie
oldbie

asked on

Is there an indirect reference capability in VB?

I want to be able to do an indirect reference of properties in my application. For example, I have a list of properties I need to save, in the form of strings like "frmMain.Top", and I want to go through the list processing each property.  I'd want to write something like

propertyList = "frmMain.Top"
savedProperty = IndirectionThingy( propertyList )

and savedProperty would contain the numeric value of frmMain.Top .

I know other languages have features like &varname meaning, not the contents of varname, but the contents of the variable whose name is in varname.
Avatar of wsh2
wsh2

You can iterate through both the Forms and Controls collection to get what you need. Mind you.. the forms collection will only work with Forms that are LOADED.


<----- Code Begin ----->

Dim frmWork as Form
Dim ctlWork as Control

On Error Resume Next
For Each frmWork in Forms
  'YourVariableHere' = frmWork.Name  
  'YourVariableHere' = frmWork.Top
  " "
  For Each ctlWork in frmWork.Controls
    'YourVariableHere' = ctlWork.Name  
    'YourVariableHere' = ctlWork.Top
    " "
  Next ctlWork
Next frmWork

<----- Code End ----->

A useful function when iterating through the Controls collection is the TypeName(objControl) as it will return the type of the object being interrogated.. eg. Frame, Image, ImageList, Text, Combo, Label.

The above solution by wsh is ok if all the variables are properties of frmWork or ctlWork.  If not then it does not.

THe functionality dynamic list access with names is not supported in VB to the best of my knowledge.  Its supported in javascript or C++.

This has to be done eithe by using multiple arrays or creating different property/controls on each of those items in the list.  Sort of limitation of VB.
I'm not sure whether this is doable. Possibly with the Microsoft Script control, but there isn't anything intrinsic to VB that can evaluate a string which includes an object and a property of that object.

CallByName is about the only function that comes close, but to use it you need an instance of the class (such as a Form). The Property *can* be a string in this case.

kvedam writes: "The above solution by wsh is ok if all the variables are properties of frmWork or ctlWork.  If not then it does not."

<duh>!!!! However, for my solution to work, the forms must be LOADed.. <smile>.

kvedam:
As you are knew here.. let me point out that there are TWO options listed above your response box.. Answer and COMMENT.. <wink>. You hit answer when your response is definitive.. and the only possible solution.

Hitting answer locks down a question.. thus limiting any / all discussion of the topic. As your answer is hardly definitive and you have locked the question, the questioner (and you) can no longer benefit from other experts observations and comments.. and you defeat the whole purpose of Expert Exchange.

In the future try hitting comment instead of answer.. and let the Questioner decide to whom the points should go. I am absolutely certain that if yours is the appropriate answer for the questioner.. that the points will be most deservedly yours.

Welcome aboard Kvedam.. <smile>.

wsh2, I am sorry but I am definitive that that is the answer.  As it says, it is the 'proposed answer'.  If the questioner does not like it he may choose not to.

That is a limitation of VB that I have seen for a while.  I have been with C++ for 9 years and I know what he seems to want.
Kvedam,

I believe that is the *etiquette* around here...just to post comments and let the person who asked the question decide which solution is best for him/her, rather than locking down the question.

I just started posting here about a week or so ago and someone on the Access side beat me up for the same thing.

Anyway, you would be surprised how frequently some people accept the answer that *you* don't think is best. It's already happened to me on several occasions.

kvedam:
In locking down this question.. we'll never know if there is another answer, huh?

Additionally.. precisely what is your answer (without the dynamic list access mumbo jumbo -or- perhaps you mean data sector memory map)?. It appears, that all the questioner wants to do is dump his form / control property bags. How does your answer address that? Fortunately, I left my "proposed answer" as a comment so that you could refer to it and key that that is ok. I hardly find your answer definitive to the writer's need.

Yes.. I agree.. let the questioner choose which is the best answer. But leave the question open so that others can respond and that he the questioner has a list of options to decide from. I am only too happy to let others rejoin on my comment and /or add comments of their own, I am confident in what I propose as a solution. Are you?.. <smile>.
pclement Writes: "you would be surprised how frequently some people accept the answer that *you* don't think is best. It's already happened to me on several occasions."

<sighing>.. sad but true.. but in life you will always find lamers (frauds).. <groan>.

Very often this is not your fault, but rather a consequence of poorly written questions.. or perhaps because of people that bully the questioner into their answers. Communications and understanding what the user wants, are the real keys to success in programming. EE affords you the opportunity to hone these skills.. and with time you will become adroit enough to read between the lines to discover the true question.. and / or know when to request more information.. <wink>.

Don't lose heart pclement.. those people you do help.. truly do make it worthwhile.. and with that.. you will always recieve your just reward.. <smile>.



Avatar of oldbie

ASKER

Ok, here's all I'm trying to do: save the positions of all the windows so the next time the app runs, they all show up where the user left them.

I could list them as wsh2 suggests, i.e.   'YourVariableHere' = frmWork.Top
But what if I had dozens of items to deal with?

What I was hoping I could do was have the names of the properties in an array and loop through them. (Mainly I was hoping just to learn how to do indirection in VB. When you need indirection, you *really* need it.)

Here's what I have so far:

~~~~~~~~~~~~~

Public Sub UnloadAllForms()

  Dim Form As Form, winParams(4) As String, i As Integer
  Dim iniString As String, iniParam As String
 
  winParams(1) = "Left"
  winParams(2) = "Top"
  winParams(3) = "Width"
  winParams(4) = "Height"
 
  For Each Form In Forms
 
    For i = 1 To 4
      iniString = Form.Name & winParams(i)
      iniParam = IndirectionMagic(Form.Name & "." & winParams(i))
      Call iniPutData("Window Layout", iniString, iniParam, glIniFile)
    Next i
   
    Unload Form
    Set Form = Nothing
   
  Next Form

End Sub

~~~~~~~~~

Which will work great as soon as I find out the real name of IndirectionMagic().

But there must be a good way to save window positions, right? Apps do it all the time.

Thanks!
Avatar of oldbie

ASKER

Ok, here's all I'm trying to do: save the positions of all the windows so the next time the app runs, they all show up where the user left them.

I could list them as wsh2 suggests, i.e.   'YourVariableHere' = frmWork.Top
But what if I had dozens of items to deal with?

What I was hoping I could do was have the names of the properties in an array and loop through them. (Mainly I was hoping just to learn how to do indirection in VB. When you need indirection, you *really* need it.)

Here's what I have so far:

~~~~~~~~~~~~~

Public Sub UnloadAllForms()

  Dim Form As Form, winParams(4) As String, i As Integer
  Dim iniString As String, iniParam As String
 
  winParams(1) = "Left"
  winParams(2) = "Top"
  winParams(3) = "Width"
  winParams(4) = "Height"
 
  For Each Form In Forms
 
    For i = 1 To 4
      iniString = Form.Name & winParams(i)
      iniParam = IndirectionMagic(Form.Name & "." & winParams(i))
      Call iniPutData("Window Layout", iniString, iniParam, glIniFile)
    Next i
   
    Unload Form
    Set Form = Nothing
   
  Next Form

End Sub

~~~~~~~~~

Which will work great as soon as I find out the real name of IndirectionMagic().

But there must be a good way to save window positions, right? Apps do it all the time.

Thanks!
ASKER CERTIFIED SOLUTION
Avatar of wsh2
wsh2

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
The above code is if you want to load all your forms at once.. a better way to do this is in adding the directly code into the Form_Load event.

<----- pseudo code begin ----->

  Dim strWork() as String
  strWork() = Split(IniGetData ("ThisFormName"), " ")
  Me.Left = Csng(strWork(1))
  Me.Top = Csng(strWork(2))
  Me.Width = Csng(strWork(3))
  Me.Height = Csng(strWork(4))

<----- pseudo code end ----->

Avatar of oldbie

ASKER

Adjusted points from 50 to 150
Avatar of oldbie

ASKER

Yes! With a slight modification:

  For Each Form In Forms
    With Form
      iniString = .Name
      iniParam = .Left & " " & .Top & " " & .Width & " " & .Height
      Call iniPutData("Window Layout", iniString, iniParam, glIniFile)
    End With
    Unload Form
    Set Form = Nothing
  Next Form

because iniPutData takes a name and a parameter string, and creates a line like:

frmMain=1320 1320 5460 3135

~~~~~~~~~~~~

Thanks wsh2!

50 points for answering the question so thoroughly.

And 100 more for your diplomacy in dealing with kvedam: "I hardly find your answer definitive to the writer's need." Couldn'ta said it better myself! Cuz I woulda cussed!

I figure "keeping a civil tongue" is probably at least twice as hard as giving helpful answers.
Thank YOU for your generosity.. <smile>.. But I don't want to give you the wrong impression.. I'm just too lazy to hit the !@#$%%^&*()_+| keys.. and <expletive deleted> is just out of the question.. <LOL>.

Be careful with using the Form word as it is a Type cast in VB.

  For Each Form In Forms

really should read..

  Dim frmWork as Form
  For Each frmWork in Forms

frmWork will then act as an alias to the real form (polymorphism).. and you can use it as though you were explicitly addressing the Form. In the For Each statement, in effect it is the same as a

  Set frmWork = Form1

statement.

Good Luck with your Project !!!!... <smile>.
wsh2:

Thanks for your previous comments. The points don't matter much to me -- but it's more the principle (how many times have you heard that one). ;-)

Mostly I'm just here to help and teach and learn from other's responses. I spend most of my time on the Microsoft News and DevX side of peer-level support, but I thought I'd venture over here out of curiosity.

wsh2, I dont have time to answer all your frustrations.  Look at the main question -- Is there an ....?

And the answer is no.  Thats all.  I gave the reason and a work around.  If you want me to tell how the compiler was designed etc, we can talk offline.
Avatar of oldbie

ASKER

Well, kvedam, I've tried to hold my tongue. But now I feel I have to state for the record that

1) wsh2 has been extremely helpful and friendly through this entire exchange, spending much more time and providing much more information than would have been required to earn the points.

2) Your "answer" was not helpful at all, and I find your combative attitude counter-productive.

Whan someone asks if something is possible, assume that they don't want to see a one-line "no" answer followed by a one-line "workaround" that is of no utility in solving the problem. What they want is a way to accomplish the task at hand. Thanks.
kvedam:
Feeling rejected?.. LOL.

In the future.. try and have more than a 2 second attention span.. and read beyond the first line:

Oldbie writes:
"I have a list of properties I need to save, in the form of strings like "frmMain.Top", and I want to go through the list processing each property."

oldbie also writes:
"And 100 more for your diplomacy in dealing with kvedam: "I hardly find your answer definitive to the writer's need." Couldn'ta said it better myself! Cuz I woulda cussed!"

Keep up the good work kvedam.. <smile>.

------------------------------------
Your thoughts will be much better appreciated here if you show a bit more decorum.. and some pride.. by submitting them (your thoughts) as comments rather than answers. Trust me, your points will easily come if you fulfill the questioners needs.. rather than your own.. <smile>
As your send.. hit while I was writing  mine.. all I can say is.. Atta oldbie !!!.. <smile> and a <wink>
Sorry i answered.  I dont have time for this ****.  Have fun with it anyways.  I thought this was a q & a forum not a place to write a research paper.
bye ...
kvedam:
Your 'comments' ARE greatly appreciated.. <passing kvedam a roll of toilet paper>.. take your time and enjoy the moment.. we all could learn something.. <smile>.