Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations TouchToneTommy on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

FoxPro button status

Status
Not open for further replies.

mmerlinn

Programmer
May 20, 2005
745
US
Is there a way in FP (and maybe VFP) to test the status of a push button, that is to return whether a button is ENABLED or DISABLED?
 
There's an Enabled property of the button object. If it's true, the button is enabled.
 
Is there a way in FP (and maybe VFP) to test the status of a push button, that is to return whether a button is ENABLED or DISABLED?
Like many other FoxPro Properties, Enabled can be used to Set and Get values.

So you can do things like this...

Code:
IF MyButton.Enabled
   MyButton.Enabled = .F.
ELSE
   MyButton.Enabled = .T.
ENDIF
 
Not sure, if you actually mean the usual button, or the checkboix in style = 1 (grapohical), which displays the value it can have (.T./.F.) as pushed in or not.
Well, then it's not enabled disabled, but pushed, not pushed and the value is that "status", because in the end it's a checkbox that can be checked or not.
 
Like many other FoxPro Properties, Enabled can be used to Set and Get values.

So you can do things like this...

Code:
IF MyButton.Enabled
   MyButton.Enabled = .F.
ELSE
   MyButton.Enabled = .T.
ENDIF
Better:
MyButton.Enabled = not MyButton.Enabled
 
Programmatically You can check the Status of this button as above mentioned.

But if You like to react at runtime for click on this button while !enabled, there is no event what fires. Neither MouseDown- nor Click-Event.

The only events who fires are MouseEnter-/Leave. those are not blocked with !Enabled because to react with ToolTipText.
 
Is there a way in FP (and maybe VFP) to test the status of a push button, that is to return whether a button is ENABLED or DISABLED?
Normally, the "dimmed" appearance of the button tells you its Enabled status. All you have to do is reference the Enabled property maybe with something like this:

if TheButton.Enabled
*Do something here like call a procedure/method/function.
endif

But normally, the button would call such a method via its Click method and if it's enabled, the method will be called and if it's disabled the method will not be called. If you can give us a more concrete example of what you're trying to do, you'll likely get more specific answers.
 
Better:
MyButton.Enabled = not MyButton.Enabled
I agree. I just wanted the easiest way to illustrate reading the value and setting the value, so I opted for simple independent IF and = lines to make it easy to read.
 
Programmatically You can check the Status of this button as above mentioned.

But if You like to react at runtime for click on this button while !enabled, there is no event what fires. Neither MouseDown- nor Click-Event.

The only events who fires are MouseEnter-/Leave. those are not blocked with !Enabled because to react with ToolTipText.

PS... In my response, I was assuming the OP was not intending to put code like this in the same button that is being clicked, otherwise there would be no need to check the status of the button, and it definitely couldn't be reversed by clicking the same button.

For what it's worth, I like using buttons as toggles from time to time instead of checkboxes because you get a lot more flexibility with sizes, colors, fonts, etc., but I don't enable/disable them but change the color and/or the captions. For example, they can toggle black vs white backgrounds, or simply say YES vs NO each time they're clicked. Then I can read their background color or caption like a logical expression (if MyButton.Caption = "YES"...) and get a slick looking bunch of toggles.
 
Like many other FoxPro Properties, Enabled can be used to Set and Get values.

So you can do things like this...

Code:
IF MyButton.Enabled
   MyButton.Enabled = .F.
ELSE
   MyButton.Enabled = .T.
ENDIF
Thanks. You have given me some ideas to try.

Your code throws "Alias 'MyButton' not found" error which makes sense since MyButton.Enabled is trying to find the 'Enabled' field in a table named 'MyButton'.

IF MyButton = 'ENABLED' throws "Operator/operand mismatch" error.

I am thinking that I will need to use OBJNUM() in some way to get what I need.

When I get more time I will do more testing.

Yes, I changed 'MyButton' in your code to the actual name of my button.

BTW, I deliberately did not state exactly which version I am using because I wanted ideas from any version that might point me in the right direction.

That said, I am using FPM 2.6b.

Basically, I need to do something like this (which obviously will not work ):

IF MyButton1 = ENABLED
SHOW GET MyButton2 DISABLED
ENDIF
 
Last edited:
Thanks. You have given me some ideas to try.

Your code throws "Alias 'MyButton' not found" error which makes sense since MyButton.Enabled is trying to find the 'Enabled' field in a table named 'MyButton'.

IF MyButton = 'ENABLED' throws "Operator/operand mismatch" error.

I am thinking that I will need to use OBJNUM() in some way to get what I need.

When I get more time I will do more testing.

Yes, I changed 'MyButton' in your code to the actual name of my button.

BTW, I deliberately did not state exactly which version I am using because I wanted ideas from any version that might point me in the right direction.

That said, I am using FPM 2.6b.

Basically, I need to do something like this (which obviously will not work ):

IF MyButton = ENABLED
SHOW GET MyButton DISABLED
ENDIF
I'm sorry, I was trying to simplify by using essentially Pseudo code, since I don't know the name of your button, or where it is.

If the button is on the top of a form, it would read:

If Thisform.MyButton.Enabled

If it's someplace inside another control such as a container or in a page within a pageframe, it could be a long string such as...

If thisform.MyPageFrame.Page2.MyContainer.MyButton.Enabled

etc.

In some cases with lots of levels, you can keep it short with This.Parent.MyButton.Enabled.
 
A form essentially is a treeview of objects, especially when objects are containers that can contain further objects, like the containerr classs or like a pageframe is a container of several pages, which each is a container for further controls, even further pageframes or containers.

And as Joe already explained that can lead to long hieraarchical object names. They always start at the root object THISFORM. If you want to address a button from outside a form, though, in a function of a PRG, for example, you'd pass in either the form object as a parameter or know the form object as some global variable or can get it from a form handler that stores it in an array or collection of forms.

To not need working with series of such long names, you can also make use of the WITH...ENDWITH construct or store a root object other than the form into a variable first, and go from that variable - that's essentially what WITH..ENDWITH does, it just stores the object reference nameless, which means you address objects starting with a dot that indicates the root object specified in the WITH line.

So instead of
Code:
If thisform.MyPageFrame.Page2.MyContainer.MyButton.Enabled
   thisform.MyPageFrame.Page2.MyContainer.MyButton.Enabled = .F.
Else
   thisform.MyPageFrame.Page2.MyContainer.MyButton.Enabled = .T.
Endif
You can shorten that to only need to specify the long hierarchical name once:
Code:
With thisform.MyPageFrame.Page2.MyContainer.MyButton
   If .Enabled
       .Enabled = .F.
   Else
       .Enabled = .T.
   Endif
EndWith

or you could do:

Code:
Local loButton
loButton = thisform.MyPageFrame.Page2.MyContainer.MyButton

If loButton.Enabled
   loButton.Enabled = .F.
Else
   loButton.Enabled = .T.
Endif

The second just to illustrate what the WITH..ENDWITH does internally anonymously, without a variable name. There's one weakness in that: The object reference the WITH line generates is not really becoming a local variable, that is automatically released, if you would leave the code with RETURN before the ENDWITH. So it keeps a lingering object reference that can cause quirks. If you don't RETURN from within WITH..ENDWITH it's fine to shorten code that way.

There's one more advantage in using variables: You can use two variables addressing two separate root objects on the form that are not nested into each other and write code "moderating" between these two root objects and their inner objects. You can nest WITH..ENDWITH, but the inner WITH can only address objects nested within the object the outer WITH..ENDWITH addresses, so you'd need to keep the long hierarchical name of a second object, or you apply the pattern to store it into a variable and address it by that variables name.
 
Last edited:
I just drove 200 miles thinking about my problem.

I never thought to check whether any of the SET/SYS functions might do what I need done. When I get a chance I will check them out.
 
Last edited:
All in all the question you had was more about how to address an object on a form, which back then you didn't realize it was actually about.

Well, let me focus a bit on the Enabling of a control from code outside of the control. It's natural, at first sight, you have to control the enabled state from outside of a control, because a disabled control won't be able to do it from within itself, will it?

Yes, it could. Your disabling the user interactions, not the whole control and all it's workings and events. There's a major thought of OOP programming, that is encapsulation, one aspect of that is that any class mainly cares for itself, so how about thinkin of enabling as something the button (or any control) does itself, based on conditions it knows itself and checks itself? You then mainly address a control from within itself and only need THIS, not the full path like name. That's how you rarely need these long hierarchical names of objects.

It takes a lot of rethinking to get there, but once you do you get to elegant and short code.
 
BTW, I deliberately did not state exactly which version I am using because I wanted ideas from any version that might point me in the right direction.

That said, I am using FPM 2.6b.

Basically, I need to do something like this (which obviously will not work ):

IF MyButton1 = ENABLED
SHOW GET MyButton2 DISABLED
ENDIF

I don't think you can check the enabled status of a control in FoxPro 2.6. That said, I haven't had to write FP2.6 code for 25 years or so, so maybe I've just forgotten.

Tamar
 
BTW, I deliberately did not state exactly which version I am using because I wanted ideas from any version that might point me in the right direction.

That said, I am using FPM 2.6b.

Basically, I need to do something like this (which obviously will not work ):

IF MyButton1 = ENABLED
SHOW GET MyButton2 DISABLED
ENDIF
I didn't notice the version.

Since 2.6 lacks properties, methods, and events, you will only be abled to do what you're asking if you create your own environment where you track the status in a variable, then generate the screens on the fly in some sort of loop.

For example, if you paint the screen in a loop full of @ SAY / GETs, then conditionally enable or disable controls based on a variable that you programmatically toggle based on other interactions on the screen.
 
Your code send "MyButton not found" error which makes sense since MyButton.Enabled is trying to find the 'Enabled' field in a table.

IF MyButton = 'ENABLED' throws "Operator mismatch" error.
MyButton.Enable=not mybutton.enable
 
Last edited:
Do you have a help file about FPM 2.6b?

It may help to refer to it - https://www.vfphelp.com/help/_5wn12pwjw.htm has a legacy help chapter on @...GET Buttons.
I have read through and it describes how to create disabled buttons, but there is no mention about getting the status. So as Joe suggested you'd have to keep track of what you designed a button (set) to be reagarding enabled/disabled.

As far as I understand legacy FP screen logic, you'll have to use a READ or READ CYCLE for points a user can interact with the UI as it is (with disabled or enabled buttons besides anything else), so if I understand this correctly you can only deal with changes after a user interaction ends a READ and at that stage you may recreate the buttons in the new state yoiu want them, but not change their status, So you'd vary the @...GET command button calls to then create a buttont or button set that has disabled/enabled as you need it as the aftermath of the last interaction.
 
Do you have a help file about FPM 2.6b?

It may help to refer to it - https://www.vfphelp.com/help/_5wn12pwjw.htm has a legacy help chapter on @...GET Buttons.
I have read through and it describes how to create disabled buttons, but there is no mention about getting the status. So as Joe suggested you'd have to keep track of what you designed a button (set) to be reagarding enabled/disabled.

As far as I understand legacy FP screen logic, you'll have to use a READ or READ CYCLE for points a user can interact with the UI as it is (with disabled or enabled buttons besides anything else), so if I understand this correctly you can only deal with changes after a user interaction ends a READ and at that stage you may recreate the buttons in the new state yoiu want them, but not change their status, So you'd vary the @...GET command button calls to then create a buttont or button set that has disabled/enabled as you need it as the aftermath of the last interaction.
That's exactly right. Believe it or not, I still have some legacy code that uses @ SAY / GETs in sections and the approach I used there was to clear the screen, create an endless loop with DO WHILE .T. that paints the screen with all sorts of conditional variations and continues to loop after READ potentially re-painting with different effects, then after the user hits a key such as F10, Exits the loop. That's exactly what the OP needs to do here.
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top