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 IamaSherpa on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Conditional Display of Text / Background Colour

Status
Not open for further replies.

David Higgs

Programmer
May 6, 2012
392
GB
Hi,

On my Form I have drawn a "shape" in the form of a square. I have made a grid of 10 x 10 Squares and each square contains a "text box" (containing the number of the square). I would like to conditionally display the contents of the "text box" and also the "backcolor" of each "shape". I have tried "thisform.textbox.text56.Visible =.F." but this produces an error "unknown member TEXTBOX".

Any help would be most appreciated.



Regards,
David
 
First, the error you mentioned has got nothing to do with conditional formatting. It is simply a matter of an incorrect object reference.

If your textbox is named text56, and you place it directly on the form (as opposed to in a pageframe or other container), then you refer to its properties like this: THISFORM.text56.Visible, for example. You don't include .Textbox.

As far as conditional formatting is concerned, it's not clear what your "shape" is? Do you have one Shape object surrounding all 100 textboxes? Or does each textbox have its own shape? And is it the shape's backcolor that you want to change, or that of the textbox?

To conditionally change the backcolor of a single textbox, you need to do something like this:

Code:
THISFORM.Text56.BackColor = ; 
  IIF(THISFORM.Text56.Value) = "whatever", RGB(225, 225, 225), RGB(0, 128, 128))

(the colours in the above line are just examples, of course).

The place to put this code is in the Init of the form, assuming that you know the values in the texbox as that point. If not, you might put it in the Refresh, either of the form or of the individual textboxes.

Given that you have a hundred textboxes, you will need to this in a loop. I can give you some code for that, but I don't want to go too far with this until you have given some feedback and explained the requirement in a little more detail.

Mike



__________________________________
Mike Lewis (Edinburgh, Scotland)

Visual FoxPro articles, tips and downloads
 
If your textbox is named text56, and you place it directly on the form (as opposed to in a pageframe or other container), then you refer to its properties like this: THISFORM.text56.Visible, for example.
If I create a new form with a textbox named text56 and insert THISFORM.text56.Visible in the INIT of the form I get an error "property VISIBLE is not a method or event".

Regards,
David
 
insert THISFORM.text56.Visible =.T.
or.
insert THISFORM.text56.Visible =.F.
 
Please tell us, what does Messagebox(Thisform.text56.Class) display, when you put that in form init?

Bye, Olaf.
 
I see. Mike said "refer to", that means adressing the property. But you have to do something with the preoperty expression, either you use it for reading the property value, then the minimum code is VAR = THISFORM.someobject.someproperty or you set it's value, then the minimum code is THISFORM.someobject.somepreoprty = somevalue.

If you only write a line with the correct object property reference, then VFP still wants to exeecute code. But this isn't code doing something, it's incomplete code, therefore you get the message "property VISIBLE is not a method or event", it's telling you can't call VISIBLE, it's only a property, you could only call a method or event of that name. It's like an incomplete sentence, like saying "I visible". What do you want to say or aks? The question "Am I visible?", or just stating "I am visible!", or being philosophical "I may be visible.", or what?

Bye, Olaf.
 
If I create a new form with a textbox named text56 and insert THISFORM.text56.Visible in the INIT of the form I get an error "property VISIBLE is not a method or event"

There are several issues here.

First, you can't just write [tt]THISFORM.text56.Visible[/tt] on its own. [tt].Visible[/tt] is a property, so you have to set it to something - in this case, to .T. or .F. So, to make the textbox invisible, you need to do this:

[tt]THISFORM.text56.Visible = .F.[/tt]

Secondly, there's no point in running that from the Init. During the processing of the Init event, the entire form is invisible. You can't change that by changing the visibility of individual controls.

And, thirdly, none of this has got anything to do with your original question, which was how to conditionally change the background colour of a textbox. I have already given you part of a possible answer for that, but we need answers to the questions I asked earlier before we can take that further.

Mike


__________________________________
Mike Lewis (Edinburgh, Scotland)

Visual FoxPro articles, tips and downloads
 
Hello Mike (and others),

Apologies, I did write a reply in response to your original post but I see it has not displayed on the Forum; I guess I didn’t post it correctly. I did preview it, but must have forgot to submit it!

The Form in my application is to do with the Ordnance Survey Maps. It displays a “Large Square” (100kM x 100kM) which contains 100 “Small Squares” (10kM x 10kM). Each Small Square contains a number (00 to 99).

Depending on certain criteria, I want the option of:-

(a) displaying / hiding the “Number” in a Small Square
(b) changing the backcolor of individual small squares

THISFORM.text56.Visible = .F.

Secondly, there's no point in running that from the Init.

Ok, maybe you could advise further on this? i.e where I should place the code? I currently have it in the Form INIT and appears to be working ok. I have also managed to set the backcolor on a given criteria, this is also in the Form INIT.
Update: I have moved the code to REFRESH
Regards,
David
 
Well, the code has to go whereever you want to set these things. If you know in advance before the form starts and if you never need to update this, while the form runs, then the init is a good spot.

You know better than us, where the code is needed. Mike certainly has a point saying that, as it's easier to make use of the code when you later want to be able to get another settings without restarting the form, you better put it into refresh. If you have no idea what events happen in what order or by what they are triggered, you better make yourself comfortable with understand object events.

You most probably want this data driven and not by giving 100 parameters for colors and another 100 for number visibility, etc., this control data could come from a dbf, of course. But it's up to you, what you want and where its easiest to get at all the resources you need to let the form look the way you want it. So the code location depends on where you have all you need at hand. You might not even know you can create your own methods and name them as you like and call them. For sure you want that code inside the form and not somewhere outside not having access to THISFORM. Code should be in the context of the objects it handles, ideally itself, that's also a part of the principle of encapsulation of code, even if you don't define a form class but only a specific form.

Bye, Olaf.
 
The Form in my application is to do with the Ordnance Survey Maps. It displays a “Large Square” (100kM x 100kM) which contains 100 “Small Squares” (10kM x 10kM). Each Small Square contains a number (00 to 99).

My initial reaction to that is that you shouldn't be using textboxes (unless you want to also let the user enter or edit the data in each square, but as you didn't mention that, I'll assume that's not a requirement).

I suggest you use a label for each of the small squares. Set its Height and Width to the actual size that you want, and set its BorderStyle to 1. By carefully arranging the labels, you should be able to get a visually pleasing effect. If you also want to delineate the large square, you can do that with a Shape object; set its BackStyle to 0 (transparent), its BorderStyle to 1, and its BorderWidth probably to 2 (but experiment with different settings to get the effect you want).

To set the visibility and background colour of any of the small squares, set the label's Visible and/or BackColor properties, using the code we've already shown. As you have surmised, the best place to do that is in the Refresh of the form. But you might alternatively do it at whatever other point you determine the condition that affects the visibility and colour.

Mike


__________________________________
Mike Lewis (Edinburgh, Scotland)

Visual FoxPro articles, tips and downloads
 
Hello Olaf,

Thank you for your input.

My Form is basically a Report Form showing the result of data stored in a DBF; so it’s basically static, although for future proofing, the Code is best placed in Refresh.

So the criteria for each square is read from a DBF, placed in a variable and the Form will decide whether to Display the Square Number and if the backcolor is to be green.




Regards,
David
 
Well, REPORT FORM is not a form (SCX) but the command to print a report (FRX), you don't have textboxes there, but the field control. You can't address this via object reerence, but it has an expression.
If you want an FRX, that'll be a totally different approach of feeding it with data and setting its look.

A report is, well, simply printable. A form is not. So decide what you want, there is no easy transfer to the other, if you have one of them, as SCX form and FRX reports use totally differnt approaches.

Bye, Olaf.
 
I guess it's down to my interpretation. My Form is used to display selected data which I term a Report. I understand that a REPORTFORM is something completely different.

Regards,
David
 
Good. So, what do you already have at hand. Do you have a table with all the needed infos? What fields are in it?
If you like the approach with variables, you could do a query INTO ARRAY and feed the numbers via array elements.

You can't bind properties like visibility or color to data, but obviously you can also make a number invisible by havin a NULL instead of the number to display in data and you may let the color be set depending on the value in the control refresh.

In any case, it'd be a good idea you'd not put 10x10 native shapes or textboxes on the form and need to write the code into each of them, but first create a class.

Bye, Olaf.
 

If you like the approach with variables, you could do a query INTO ARRAY and feed the numbers via array elements.
I'm quite happing in extracting the data from the DBF and placing into the appropriate Variable for the Form to display. I am aware of "copy to array" but have not used it before; so will need to read up on this.

You can't bind properties like visibility or color to data, but obviously you can also make a number invisible by havin a NULL instead of the number to display in data and you may let the color be set depending on the value in the control refresh.
That sounds like a good plan; if variable is not "null" then change backcolor to Green etc.
In any case, it'd be a good idea you'd not put 10x10 native shapes or textboxes on the form and need to write the code into each of them, but first create a class.
Creating a Class is something I've not done before, so I would need to read up on this and report back.

Regards,
David
 
David,

Have you had a chance to consider my last post (about five posts ago), where I suggested an approach using labels rather than textboxes? The reason I ask is that I can give you some more code to amplify my suggestion, but I won't do that if you prefer not to take this approach.

Mike

__________________________________
Mike Lewis (Edinburgh, Scotland)

Visual FoxPro articles, tips and downloads
 
>I'm quite happing in extracting the data from the DBF and placing into the appropriate Variable for the Form to display
THE variable is good. You have 100 textboxes, you need 100 variables. This is no fun.

You also won't have 100 fields in one record, so you best use an array and set the controlsources in a loop. You might then also not use controlsources and instead set values directly. You might then also use a scan loop on data instead of array. It all depends on what data you have at hand. We still don't know what the rules are about what conditions should be mapped to what color or number.

You have enough food for though to read up and experiment with.

Bye, Olaf.
 
Have you had a chance to consider my last post (about five posts ago), where I suggested an approach using labels rather than textboxes?
I did have a look at your suggestion but I don't understand how I would extract data from a DBF into a LABEL.

Regards,
David
 
It all depends on what data you have at hand. We still don't know what the rules are about what conditions should be mapped to what color or number.
Basically in Amateur Radio there is an 'Award Scheme' where you have to work (make contact) with another Radio Amateur located in each 'Small Square'. So the data stored is the "Callsign" of the Station Worked, the "Small Square" (e.g SP83) the other station is located in, plus the date of the contact. As there are several different types of awards some of data is duplicated e.g You can collect an "all time" award where all of the contacts you make count or you could also collect an award based on a particular "Band" for which there are 6 or more "bands" of interest. It gets complicated ! !

As a casualty of the Steel Industry decline all this makes the day go by! Maybe a bit out of my depth at times though!

Regards,
David
 
I don't understand how I would extract data from a DBF into a LABEL

Well, I don't know what data you are storing in your DBF. But, essentially, you set the Caption property of the label to whatever you want to display in it.

For example, if you have a field in your table named Location, you would do something like this:

[tt]THISFORM.Label56.Caption = ALLTRIM(Location)[/tt]

Then, if, in a given record, the Location field contains, say, "Scunthorpe", that is the text that the label will show.

But the point that I am trying to make is that, regardless of whether you are using a label or a texbox, you will need a way of looping through the controls in order to show the text, or to make the text invisible, or whatever you want to do. I didn't want to go too far down the road of showing you how to do that before you had made some basic decisions about which type of control to use.

Mike

Mike



__________________________________
Mike Lewis (Edinburgh, Scotland)

Visual FoxPro articles, tips and downloads
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top