From: Joseph M. Newcomer on
See below...
On Wed, 19 May 2010 17:41:02 -0500, "JCO" <someone(a)somewhere.com> wrote:

>Okay both of you agree that the Lose Focus is not a great way to do it and I
>agree.
>
>This is an EditBox that is set to accept only Integers because it is the
>Clients Age. VS2008 gives me a property to set that forces it to be an
>Integer only.
****
If all you want to set is a simple integer, this should be sufficient. It doesn't allow
you to check the range of the integer
****
>Since this is the case, I should not have to SubClass CEdit
>for my purpose. This is to simple. I changed the Handler from OnFocusKill
>to EN_CHANGE. This seems to work just fine.
****
There are people who think "subclassing" is a heavy-duty concept. The last time someone
asked "how do I do this without subclassing?" I pointed out that I had subclassed six
controls before breakfast that day. It is a tiny amount of typing, plus adding the
subclass functionality.
****
>
>This should be okay.... right? I think it should be okay because the
>Property that sets it to Integers only already does all of the validation I
>need.
****
But note that the age 0 and ages 150 and 4999 are acceptable if you accept only digits.

What I typically do is place all my "validation" code in a single function,
updateControls, and might do something of the form

CString s;
c_Age.GetWindowText(s);
int age = _ttoi(s);

....typically lots of other stuff

c_OK.EnableWindow(...usually other conditions here... && age > 0 && age < 120);

On OnChange handler simply calls updateControls() and if the control is not valid, the OK
button is disabled (as far as I know, there are no documented records of someone exceeding
the age of 120. OTOH, in Norway truant officers showed up to take someone to school
because the school had no record he was attending, and he was 7 years old. Actually, it
turned out he was 107, so you have to accept ages > 100.

THe trick is that there is exactly one or two EnableWindow calls for each window. If
there is a complex boolean expression as above, there is exactly one call; otherwise, the
idiom is of the form
if(conditions)
ctl.EnableWindow(TRUE);
else
ctl.EnableWindow(FALSE);

Another model is the "monotonically mutable" approach

BOOL enableOK = TRUE;

....stuff

enableOK &= condition

....stuff

enableOK &= anothercondition

....stuff

enableOK &= yetanothercondition;

c_OK.EnableWindow(enableOK);

I use these techniques interchangeably, depending on which one seems most appropriate for
the task.

The advantage is that there is NEVER a question about what enables or disables a control;
it is always in exactly ONE function, which examines the dependencies from first
principles (not little boolean flags set from random places). so you have complete control
of what is going on.
joe

>
>"Joseph M. Newcomer" <newcomer(a)flounder.com> wrote in message
>news:0gk8v51vln9ml0vhirgk01060qmov1kgjj(a)4ax.com...
>> One of the things I discovered the hard way was that doing
>> validation-on-focus-loss is not
>> the best way to handle validation. So about 20 years ago, I adopted the
>> idea of
>> "realtime" validation; for example, that the edit control contains code to
>> validate the
>> age (whatever that means) and re-validates on every character typed; an
>> example of this is
>> my Validating Edit Control which is on my MVP Tips site, which validates
>> the format of a
>> floating-point number.
>>
>> But when you select a menu item, you don't actually lose (not loose)
>> focus, but when the
>> app comes up, you should lose focus when one of its controls gets focus.
>> Note, however,
>> that if the app doesn't actually do a SetFocus,then there is no
>> loss-of-focus.
>>
>> One particularly bad feature of validation-on-focus-loss is what do you do
>> if the value is
>> "invalid" by whatever determines validity? If you pop up a MessageBox,
>> this is the wrong
>> approach, because it means you can't even hit the "cancel" button because
>> it keeps popping
>> up an annoying messagebox.
>>
>> When I have complex dialogs, I tend to do things like have a CStatic which
>> displays an
>> error message if any one control fails to validate; in extreme cases I've
>> used a CListBox
>> to display ALL the reasons that validation has failed. A variant of this
>> is to use a
>> ToolTip on the OK button, which I disable if any control fails validation;
>> the tooltip
>> displays one of reasons for validation failure.
>>
>> There are lots of different approaches to validation; for example, if you
>> only want
>> digits, you can use the ES_NUMBER property of the edit control (Property:
>> Number=true) to
>> make sure that illegal characters cannot be typed. If there is other
>> validation (for
>> example, that the age is < 120), I prefer to do these with realtime
>> validation.
>> joe
>>
>> On Wed, 19 May 2010 13:52:21 -0500, "JCO" <someone(a)somewhere.com> wrote:
>>
>>>Using VS2008
>>>I have an app that has an edit box that contains the Clients Age. I'm
>>>doing
>>>the validity check when the edit box looses focus. This works great when
>>>the user clicks a button that runs the application. However, if the user
>>>clicks Run App from the menu, the edit box does not loose the focus...
>>>therefore the check is not made.
>>>
>>>I can tell you that the code for File>Run does nothing more that call the
>>>::OnFileRunapplication
>>>
>>>What's the easiest way to resolve this? Seems like I need to loose the
>>>focus of the edit box before making a call to ::OnFileRunapplication.
>>>
>>>Thanks
>> Joseph M. Newcomer [MVP]
>> email: newcomer(a)flounder.com
>> Web: http://www.flounder.com
>> MVP Tips: http://www.flounder.com/mvp_tips.htm
Joseph M. Newcomer [MVP]
email: newcomer(a)flounder.com
Web: http://www.flounder.com
MVP Tips: http://www.flounder.com/mvp_tips.htm
From: JCO on
Ah.. makes sense. I will absorb this more and let you know. I also change
the Edit Box for the Client's name to use EN_CHANGE. What I don't like
about this is the fact that I have to run thru my code on each letter. I'm
not sure this is practical although I'm sure it's done a lot.

Again... I will get back to you.
Thanks

"Joseph M. Newcomer" <newcomer(a)flounder.com> wrote in message
news:u7s8v5tjksdq49gtfurg91dq1jg7f4ki9l(a)4ax.com...
> See below...
> On Wed, 19 May 2010 17:41:02 -0500, "JCO" <someone(a)somewhere.com> wrote:
>
>>Okay both of you agree that the Lose Focus is not a great way to do it and
>>I
>>agree.
>>
>>This is an EditBox that is set to accept only Integers because it is the
>>Clients Age. VS2008 gives me a property to set that forces it to be an
>>Integer only.
> ****
> If all you want to set is a simple integer, this should be sufficient. It
> doesn't allow
> you to check the range of the integer
> ****
>>Since this is the case, I should not have to SubClass CEdit
>>for my purpose. This is to simple. I changed the Handler from
>>OnFocusKill
>>to EN_CHANGE. This seems to work just fine.
> ****
> There are people who think "subclassing" is a heavy-duty concept. The
> last time someone
> asked "how do I do this without subclassing?" I pointed out that I had
> subclassed six
> controls before breakfast that day. It is a tiny amount of typing, plus
> adding the
> subclass functionality.
> ****
>>
>>This should be okay.... right? I think it should be okay because the
>>Property that sets it to Integers only already does all of the validation
>>I
>>need.
> ****
> But note that the age 0 and ages 150 and 4999 are acceptable if you accept
> only digits.
>
> What I typically do is place all my "validation" code in a single
> function,
> updateControls, and might do something of the form
>
> CString s;
> c_Age.GetWindowText(s);
> int age = _ttoi(s);
>
> ...typically lots of other stuff
>
> c_OK.EnableWindow(...usually other conditions here... && age > 0 && age <
> 120);
>
> On OnChange handler simply calls updateControls() and if the control is
> not valid, the OK
> button is disabled (as far as I know, there are no documented records of
> someone exceeding
> the age of 120. OTOH, in Norway truant officers showed up to take someone
> to school
> because the school had no record he was attending, and he was 7 years old.
> Actually, it
> turned out he was 107, so you have to accept ages > 100.
>
> THe trick is that there is exactly one or two EnableWindow calls for each
> window. If
> there is a complex boolean expression as above, there is exactly one call;
> otherwise, the
> idiom is of the form
> if(conditions)
> ctl.EnableWindow(TRUE);
> else
> ctl.EnableWindow(FALSE);
>
> Another model is the "monotonically mutable" approach
>
> BOOL enableOK = TRUE;
>
> ...stuff
>
> enableOK &= condition
>
> ...stuff
>
> enableOK &= anothercondition
>
> ...stuff
>
> enableOK &= yetanothercondition;
>
> c_OK.EnableWindow(enableOK);
>
> I use these techniques interchangeably, depending on which one seems most
> appropriate for
> the task.
>
> The advantage is that there is NEVER a question about what enables or
> disables a control;
> it is always in exactly ONE function, which examines the dependencies from
> first
> principles (not little boolean flags set from random places). so you have
> complete control
> of what is going on.
> joe
>
>>
>>"Joseph M. Newcomer" <newcomer(a)flounder.com> wrote in message
>>news:0gk8v51vln9ml0vhirgk01060qmov1kgjj(a)4ax.com...
>>> One of the things I discovered the hard way was that doing
>>> validation-on-focus-loss is not
>>> the best way to handle validation. So about 20 years ago, I adopted the
>>> idea of
>>> "realtime" validation; for example, that the edit control contains code
>>> to
>>> validate the
>>> age (whatever that means) and re-validates on every character typed; an
>>> example of this is
>>> my Validating Edit Control which is on my MVP Tips site, which validates
>>> the format of a
>>> floating-point number.
>>>
>>> But when you select a menu item, you don't actually lose (not loose)
>>> focus, but when the
>>> app comes up, you should lose focus when one of its controls gets focus.
>>> Note, however,
>>> that if the app doesn't actually do a SetFocus,then there is no
>>> loss-of-focus.
>>>
>>> One particularly bad feature of validation-on-focus-loss is what do you
>>> do
>>> if the value is
>>> "invalid" by whatever determines validity? If you pop up a MessageBox,
>>> this is the wrong
>>> approach, because it means you can't even hit the "cancel" button
>>> because
>>> it keeps popping
>>> up an annoying messagebox.
>>>
>>> When I have complex dialogs, I tend to do things like have a CStatic
>>> which
>>> displays an
>>> error message if any one control fails to validate; in extreme cases
>>> I've
>>> used a CListBox
>>> to display ALL the reasons that validation has failed. A variant of
>>> this
>>> is to use a
>>> ToolTip on the OK button, which I disable if any control fails
>>> validation;
>>> the tooltip
>>> displays one of reasons for validation failure.
>>>
>>> There are lots of different approaches to validation; for example, if
>>> you
>>> only want
>>> digits, you can use the ES_NUMBER property of the edit control
>>> (Property:
>>> Number=true) to
>>> make sure that illegal characters cannot be typed. If there is other
>>> validation (for
>>> example, that the age is < 120), I prefer to do these with realtime
>>> validation.
>>> joe
>>>
>>> On Wed, 19 May 2010 13:52:21 -0500, "JCO" <someone(a)somewhere.com> wrote:
>>>
>>>>Using VS2008
>>>>I have an app that has an edit box that contains the Clients Age. I'm
>>>>doing
>>>>the validity check when the edit box looses focus. This works great
>>>>when
>>>>the user clicks a button that runs the application. However, if the
>>>>user
>>>>clicks Run App from the menu, the edit box does not loose the focus...
>>>>therefore the check is not made.
>>>>
>>>>I can tell you that the code for File>Run does nothing more that call
>>>>the
>>>>::OnFileRunapplication
>>>>
>>>>What's the easiest way to resolve this? Seems like I need to loose the
>>>>focus of the edit box before making a call to ::OnFileRunapplication.
>>>>
>>>>Thanks
>>> Joseph M. Newcomer [MVP]
>>> email: newcomer(a)flounder.com
>>> Web: http://www.flounder.com
>>> MVP Tips: http://www.flounder.com/mvp_tips.htm
> Joseph M. Newcomer [MVP]
> email: newcomer(a)flounder.com
> Web: http://www.flounder.com
> MVP Tips: http://www.flounder.com/mvp_tips.htm

From: Joseph M. Newcomer on
Keep this in mind:

The sound of a key hitting bottom is transmitted to your ear at 1100 ft/sec; so about 2'
from the ear means about 2ms delay. The feel of a keystroke hitting bottom is transmitted
from the fingertip to the brain, a distance of about 3', at 300'/sec, or about 10ms delay.
The brain takes something between 100ms and 200ms to recognize a change on the screen
(such as the appearance of a new character).

A highly-skilled typist might be able to type 50 words per minute, where a "word" is
nominally 5 characters (allow 6 characters for the space bar), so that is 300 characters
per minute or about 5 characters per second. That's 200ms/character, about the forebrain
perception rate.

How many instructions does a modern 3GHz pipelined superscalar execute in those intervals?

Unless you were to do a database query on every keystroke (or something else seriously
time-consuming) your EN_CHANGE handler has NO DETECTABLE IMPACT on the perceived
keystroke processing. In the list of things to worry about in terms of performance, this
is approximately the least important issue to worry about.

On each character, I typically examine 20-30 controls, and enable/disable 5-10 controls,
and there is no detectable performance hit.
joe

On Wed, 19 May 2010 18:41:14 -0500, "JCO" <someone(a)somewhere.com> wrote:

>Ah.. makes sense. I will absorb this more and let you know. I also change
>the Edit Box for the Client's name to use EN_CHANGE. What I don't like
>about this is the fact that I have to run thru my code on each letter. I'm
>not sure this is practical although I'm sure it's done a lot.
>
>Again... I will get back to you.
>Thanks
>
>"Joseph M. Newcomer" <newcomer(a)flounder.com> wrote in message
>news:u7s8v5tjksdq49gtfurg91dq1jg7f4ki9l(a)4ax.com...
>> See below...
>> On Wed, 19 May 2010 17:41:02 -0500, "JCO" <someone(a)somewhere.com> wrote:
>>
>>>Okay both of you agree that the Lose Focus is not a great way to do it and
>>>I
>>>agree.
>>>
>>>This is an EditBox that is set to accept only Integers because it is the
>>>Clients Age. VS2008 gives me a property to set that forces it to be an
>>>Integer only.
>> ****
>> If all you want to set is a simple integer, this should be sufficient. It
>> doesn't allow
>> you to check the range of the integer
>> ****
>>>Since this is the case, I should not have to SubClass CEdit
>>>for my purpose. This is to simple. I changed the Handler from
>>>OnFocusKill
>>>to EN_CHANGE. This seems to work just fine.
>> ****
>> There are people who think "subclassing" is a heavy-duty concept. The
>> last time someone
>> asked "how do I do this without subclassing?" I pointed out that I had
>> subclassed six
>> controls before breakfast that day. It is a tiny amount of typing, plus
>> adding the
>> subclass functionality.
>> ****
>>>
>>>This should be okay.... right? I think it should be okay because the
>>>Property that sets it to Integers only already does all of the validation
>>>I
>>>need.
>> ****
>> But note that the age 0 and ages 150 and 4999 are acceptable if you accept
>> only digits.
>>
>> What I typically do is place all my "validation" code in a single
>> function,
>> updateControls, and might do something of the form
>>
>> CString s;
>> c_Age.GetWindowText(s);
>> int age = _ttoi(s);
>>
>> ...typically lots of other stuff
>>
>> c_OK.EnableWindow(...usually other conditions here... && age > 0 && age <
>> 120);
>>
>> On OnChange handler simply calls updateControls() and if the control is
>> not valid, the OK
>> button is disabled (as far as I know, there are no documented records of
>> someone exceeding
>> the age of 120. OTOH, in Norway truant officers showed up to take someone
>> to school
>> because the school had no record he was attending, and he was 7 years old.
>> Actually, it
>> turned out he was 107, so you have to accept ages > 100.
>>
>> THe trick is that there is exactly one or two EnableWindow calls for each
>> window. If
>> there is a complex boolean expression as above, there is exactly one call;
>> otherwise, the
>> idiom is of the form
>> if(conditions)
>> ctl.EnableWindow(TRUE);
>> else
>> ctl.EnableWindow(FALSE);
>>
>> Another model is the "monotonically mutable" approach
>>
>> BOOL enableOK = TRUE;
>>
>> ...stuff
>>
>> enableOK &= condition
>>
>> ...stuff
>>
>> enableOK &= anothercondition
>>
>> ...stuff
>>
>> enableOK &= yetanothercondition;
>>
>> c_OK.EnableWindow(enableOK);
>>
>> I use these techniques interchangeably, depending on which one seems most
>> appropriate for
>> the task.
>>
>> The advantage is that there is NEVER a question about what enables or
>> disables a control;
>> it is always in exactly ONE function, which examines the dependencies from
>> first
>> principles (not little boolean flags set from random places). so you have
>> complete control
>> of what is going on.
>> joe
>>
>>>
>>>"Joseph M. Newcomer" <newcomer(a)flounder.com> wrote in message
>>>news:0gk8v51vln9ml0vhirgk01060qmov1kgjj(a)4ax.com...
>>>> One of the things I discovered the hard way was that doing
>>>> validation-on-focus-loss is not
>>>> the best way to handle validation. So about 20 years ago, I adopted the
>>>> idea of
>>>> "realtime" validation; for example, that the edit control contains code
>>>> to
>>>> validate the
>>>> age (whatever that means) and re-validates on every character typed; an
>>>> example of this is
>>>> my Validating Edit Control which is on my MVP Tips site, which validates
>>>> the format of a
>>>> floating-point number.
>>>>
>>>> But when you select a menu item, you don't actually lose (not loose)
>>>> focus, but when the
>>>> app comes up, you should lose focus when one of its controls gets focus.
>>>> Note, however,
>>>> that if the app doesn't actually do a SetFocus,then there is no
>>>> loss-of-focus.
>>>>
>>>> One particularly bad feature of validation-on-focus-loss is what do you
>>>> do
>>>> if the value is
>>>> "invalid" by whatever determines validity? If you pop up a MessageBox,
>>>> this is the wrong
>>>> approach, because it means you can't even hit the "cancel" button
>>>> because
>>>> it keeps popping
>>>> up an annoying messagebox.
>>>>
>>>> When I have complex dialogs, I tend to do things like have a CStatic
>>>> which
>>>> displays an
>>>> error message if any one control fails to validate; in extreme cases
>>>> I've
>>>> used a CListBox
>>>> to display ALL the reasons that validation has failed. A variant of
>>>> this
>>>> is to use a
>>>> ToolTip on the OK button, which I disable if any control fails
>>>> validation;
>>>> the tooltip
>>>> displays one of reasons for validation failure.
>>>>
>>>> There are lots of different approaches to validation; for example, if
>>>> you
>>>> only want
>>>> digits, you can use the ES_NUMBER property of the edit control
>>>> (Property:
>>>> Number=true) to
>>>> make sure that illegal characters cannot be typed. If there is other
>>>> validation (for
>>>> example, that the age is < 120), I prefer to do these with realtime
>>>> validation.
>>>> joe
>>>>
>>>> On Wed, 19 May 2010 13:52:21 -0500, "JCO" <someone(a)somewhere.com> wrote:
>>>>
>>>>>Using VS2008
>>>>>I have an app that has an edit box that contains the Clients Age. I'm
>>>>>doing
>>>>>the validity check when the edit box looses focus. This works great
>>>>>when
>>>>>the user clicks a button that runs the application. However, if the
>>>>>user
>>>>>clicks Run App from the menu, the edit box does not loose the focus...
>>>>>therefore the check is not made.
>>>>>
>>>>>I can tell you that the code for File>Run does nothing more that call
>>>>>the
>>>>>::OnFileRunapplication
>>>>>
>>>>>What's the easiest way to resolve this? Seems like I need to loose the
>>>>>focus of the edit box before making a call to ::OnFileRunapplication.
>>>>>
>>>>>Thanks
>>>> Joseph M. Newcomer [MVP]
>>>> email: newcomer(a)flounder.com
>>>> Web: http://www.flounder.com
>>>> MVP Tips: http://www.flounder.com/mvp_tips.htm
>> Joseph M. Newcomer [MVP]
>> email: newcomer(a)flounder.com
>> Web: http://www.flounder.com
>> MVP Tips: http://www.flounder.com/mvp_tips.htm
Joseph M. Newcomer [MVP]
email: newcomer(a)flounder.com
Web: http://www.flounder.com
MVP Tips: http://www.flounder.com/mvp_tips.htm
From: JCO on
Joseph,
When you say you put all of your Validation in one function, I assume this
does not include Controls that have a subclass? Because that validation
would be done in the subclass control...Right?


"Joseph M. Newcomer" <newcomer(a)flounder.com> wrote in message
news:u7s8v5tjksdq49gtfurg91dq1jg7f4ki9l(a)4ax.com...
> See below...
> On Wed, 19 May 2010 17:41:02 -0500, "JCO" <someone(a)somewhere.com> wrote:
>
>>Okay both of you agree that the Lose Focus is not a great way to do it and
>>I
>>agree.
>>
>>This is an EditBox that is set to accept only Integers because it is the
>>Clients Age. VS2008 gives me a property to set that forces it to be an
>>Integer only.
> ****
> If all you want to set is a simple integer, this should be sufficient. It
> doesn't allow
> you to check the range of the integer
> ****
>>Since this is the case, I should not have to SubClass CEdit
>>for my purpose. This is to simple. I changed the Handler from
>>OnFocusKill
>>to EN_CHANGE. This seems to work just fine.
> ****
> There are people who think "subclassing" is a heavy-duty concept. The
> last time someone
> asked "how do I do this without subclassing?" I pointed out that I had
> subclassed six
> controls before breakfast that day. It is a tiny amount of typing, plus
> adding the
> subclass functionality.
> ****
>>
>>This should be okay.... right? I think it should be okay because the
>>Property that sets it to Integers only already does all of the validation
>>I
>>need.
> ****
> But note that the age 0 and ages 150 and 4999 are acceptable if you accept
> only digits.
>
> What I typically do is place all my "validation" code in a single
> function,
> updateControls, and might do something of the form
>
> CString s;
> c_Age.GetWindowText(s);
> int age = _ttoi(s);
>
> ...typically lots of other stuff
>
> c_OK.EnableWindow(...usually other conditions here... && age > 0 && age <
> 120);
>
> On OnChange handler simply calls updateControls() and if the control is
> not valid, the OK
> button is disabled (as far as I know, there are no documented records of
> someone exceeding
> the age of 120. OTOH, in Norway truant officers showed up to take someone
> to school
> because the school had no record he was attending, and he was 7 years old.
> Actually, it
> turned out he was 107, so you have to accept ages > 100.
>
> THe trick is that there is exactly one or two EnableWindow calls for each
> window. If
> there is a complex boolean expression as above, there is exactly one call;
> otherwise, the
> idiom is of the form
> if(conditions)
> ctl.EnableWindow(TRUE);
> else
> ctl.EnableWindow(FALSE);
>
> Another model is the "monotonically mutable" approach
>
> BOOL enableOK = TRUE;
>
> ...stuff
>
> enableOK &= condition
>
> ...stuff
>
> enableOK &= anothercondition
>
> ...stuff
>
> enableOK &= yetanothercondition;
>
> c_OK.EnableWindow(enableOK);
>
> I use these techniques interchangeably, depending on which one seems most
> appropriate for
> the task.
>
> The advantage is that there is NEVER a question about what enables or
> disables a control;
> it is always in exactly ONE function, which examines the dependencies from
> first
> principles (not little boolean flags set from random places). so you have
> complete control
> of what is going on.
> joe
>
>>
>>"Joseph M. Newcomer" <newcomer(a)flounder.com> wrote in message
>>news:0gk8v51vln9ml0vhirgk01060qmov1kgjj(a)4ax.com...
>>> One of the things I discovered the hard way was that doing
>>> validation-on-focus-loss is not
>>> the best way to handle validation. So about 20 years ago, I adopted the
>>> idea of
>>> "realtime" validation; for example, that the edit control contains code
>>> to
>>> validate the
>>> age (whatever that means) and re-validates on every character typed; an
>>> example of this is
>>> my Validating Edit Control which is on my MVP Tips site, which validates
>>> the format of a
>>> floating-point number.
>>>
>>> But when you select a menu item, you don't actually lose (not loose)
>>> focus, but when the
>>> app comes up, you should lose focus when one of its controls gets focus.
>>> Note, however,
>>> that if the app doesn't actually do a SetFocus,then there is no
>>> loss-of-focus.
>>>
>>> One particularly bad feature of validation-on-focus-loss is what do you
>>> do
>>> if the value is
>>> "invalid" by whatever determines validity? If you pop up a MessageBox,
>>> this is the wrong
>>> approach, because it means you can't even hit the "cancel" button
>>> because
>>> it keeps popping
>>> up an annoying messagebox.
>>>
>>> When I have complex dialogs, I tend to do things like have a CStatic
>>> which
>>> displays an
>>> error message if any one control fails to validate; in extreme cases
>>> I've
>>> used a CListBox
>>> to display ALL the reasons that validation has failed. A variant of
>>> this
>>> is to use a
>>> ToolTip on the OK button, which I disable if any control fails
>>> validation;
>>> the tooltip
>>> displays one of reasons for validation failure.
>>>
>>> There are lots of different approaches to validation; for example, if
>>> you
>>> only want
>>> digits, you can use the ES_NUMBER property of the edit control
>>> (Property:
>>> Number=true) to
>>> make sure that illegal characters cannot be typed. If there is other
>>> validation (for
>>> example, that the age is < 120), I prefer to do these with realtime
>>> validation.
>>> joe
>>>
>>> On Wed, 19 May 2010 13:52:21 -0500, "JCO" <someone(a)somewhere.com> wrote:
>>>
>>>>Using VS2008
>>>>I have an app that has an edit box that contains the Clients Age. I'm
>>>>doing
>>>>the validity check when the edit box looses focus. This works great
>>>>when
>>>>the user clicks a button that runs the application. However, if the
>>>>user
>>>>clicks Run App from the menu, the edit box does not loose the focus...
>>>>therefore the check is not made.
>>>>
>>>>I can tell you that the code for File>Run does nothing more that call
>>>>the
>>>>::OnFileRunapplication
>>>>
>>>>What's the easiest way to resolve this? Seems like I need to loose the
>>>>focus of the edit box before making a call to ::OnFileRunapplication.
>>>>
>>>>Thanks
>>> Joseph M. Newcomer [MVP]
>>> email: newcomer(a)flounder.com
>>> Web: http://www.flounder.com
>>> MVP Tips: http://www.flounder.com/mvp_tips.htm
> Joseph M. Newcomer [MVP]
> email: newcomer(a)flounder.com
> Web: http://www.flounder.com
> MVP Tips: http://www.flounder.com/mvp_tips.htm

From: Joseph M. Newcomer on
If my controls do validation in subclass code, I usually have an IsValid method of the
control that tells me if the content is valid. See my Validating Edit Control, for
example. So I might write

BOOL EnableOK = TRUE;
.... lots of tests
EnableOK &= c_FloatingPointValue.IsValid();
.....maybe more tests

c_OK.EnableWindow(EnableOK);

where c_FloatingPointValue is an instance of my validating edit control.
joe

On Fri, 21 May 2010 14:34:50 -0500, "JCO" <someone(a)somewhere.com> wrote:

>Joseph,
>When you say you put all of your Validation in one function, I assume this
>does not include Controls that have a subclass? Because that validation
>would be done in the subclass control...Right?
>
>
>"Joseph M. Newcomer" <newcomer(a)flounder.com> wrote in message
>news:u7s8v5tjksdq49gtfurg91dq1jg7f4ki9l(a)4ax.com...
>> See below...
>> On Wed, 19 May 2010 17:41:02 -0500, "JCO" <someone(a)somewhere.com> wrote:
>>
>>>Okay both of you agree that the Lose Focus is not a great way to do it and
>>>I
>>>agree.
>>>
>>>This is an EditBox that is set to accept only Integers because it is the
>>>Clients Age. VS2008 gives me a property to set that forces it to be an
>>>Integer only.
>> ****
>> If all you want to set is a simple integer, this should be sufficient. It
>> doesn't allow
>> you to check the range of the integer
>> ****
>>>Since this is the case, I should not have to SubClass CEdit
>>>for my purpose. This is to simple. I changed the Handler from
>>>OnFocusKill
>>>to EN_CHANGE. This seems to work just fine.
>> ****
>> There are people who think "subclassing" is a heavy-duty concept. The
>> last time someone
>> asked "how do I do this without subclassing?" I pointed out that I had
>> subclassed six
>> controls before breakfast that day. It is a tiny amount of typing, plus
>> adding the
>> subclass functionality.
>> ****
>>>
>>>This should be okay.... right? I think it should be okay because the
>>>Property that sets it to Integers only already does all of the validation
>>>I
>>>need.
>> ****
>> But note that the age 0 and ages 150 and 4999 are acceptable if you accept
>> only digits.
>>
>> What I typically do is place all my "validation" code in a single
>> function,
>> updateControls, and might do something of the form
>>
>> CString s;
>> c_Age.GetWindowText(s);
>> int age = _ttoi(s);
>>
>> ...typically lots of other stuff
>>
>> c_OK.EnableWindow(...usually other conditions here... && age > 0 && age <
>> 120);
>>
>> On OnChange handler simply calls updateControls() and if the control is
>> not valid, the OK
>> button is disabled (as far as I know, there are no documented records of
>> someone exceeding
>> the age of 120. OTOH, in Norway truant officers showed up to take someone
>> to school
>> because the school had no record he was attending, and he was 7 years old.
>> Actually, it
>> turned out he was 107, so you have to accept ages > 100.
>>
>> THe trick is that there is exactly one or two EnableWindow calls for each
>> window. If
>> there is a complex boolean expression as above, there is exactly one call;
>> otherwise, the
>> idiom is of the form
>> if(conditions)
>> ctl.EnableWindow(TRUE);
>> else
>> ctl.EnableWindow(FALSE);
>>
>> Another model is the "monotonically mutable" approach
>>
>> BOOL enableOK = TRUE;
>>
>> ...stuff
>>
>> enableOK &= condition
>>
>> ...stuff
>>
>> enableOK &= anothercondition
>>
>> ...stuff
>>
>> enableOK &= yetanothercondition;
>>
>> c_OK.EnableWindow(enableOK);
>>
>> I use these techniques interchangeably, depending on which one seems most
>> appropriate for
>> the task.
>>
>> The advantage is that there is NEVER a question about what enables or
>> disables a control;
>> it is always in exactly ONE function, which examines the dependencies from
>> first
>> principles (not little boolean flags set from random places). so you have
>> complete control
>> of what is going on.
>> joe
>>
>>>
>>>"Joseph M. Newcomer" <newcomer(a)flounder.com> wrote in message
>>>news:0gk8v51vln9ml0vhirgk01060qmov1kgjj(a)4ax.com...
>>>> One of the things I discovered the hard way was that doing
>>>> validation-on-focus-loss is not
>>>> the best way to handle validation. So about 20 years ago, I adopted the
>>>> idea of
>>>> "realtime" validation; for example, that the edit control contains code
>>>> to
>>>> validate the
>>>> age (whatever that means) and re-validates on every character typed; an
>>>> example of this is
>>>> my Validating Edit Control which is on my MVP Tips site, which validates
>>>> the format of a
>>>> floating-point number.
>>>>
>>>> But when you select a menu item, you don't actually lose (not loose)
>>>> focus, but when the
>>>> app comes up, you should lose focus when one of its controls gets focus.
>>>> Note, however,
>>>> that if the app doesn't actually do a SetFocus,then there is no
>>>> loss-of-focus.
>>>>
>>>> One particularly bad feature of validation-on-focus-loss is what do you
>>>> do
>>>> if the value is
>>>> "invalid" by whatever determines validity? If you pop up a MessageBox,
>>>> this is the wrong
>>>> approach, because it means you can't even hit the "cancel" button
>>>> because
>>>> it keeps popping
>>>> up an annoying messagebox.
>>>>
>>>> When I have complex dialogs, I tend to do things like have a CStatic
>>>> which
>>>> displays an
>>>> error message if any one control fails to validate; in extreme cases
>>>> I've
>>>> used a CListBox
>>>> to display ALL the reasons that validation has failed. A variant of
>>>> this
>>>> is to use a
>>>> ToolTip on the OK button, which I disable if any control fails
>>>> validation;
>>>> the tooltip
>>>> displays one of reasons for validation failure.
>>>>
>>>> There are lots of different approaches to validation; for example, if
>>>> you
>>>> only want
>>>> digits, you can use the ES_NUMBER property of the edit control
>>>> (Property:
>>>> Number=true) to
>>>> make sure that illegal characters cannot be typed. If there is other
>>>> validation (for
>>>> example, that the age is < 120), I prefer to do these with realtime
>>>> validation.
>>>> joe
>>>>
>>>> On Wed, 19 May 2010 13:52:21 -0500, "JCO" <someone(a)somewhere.com> wrote:
>>>>
>>>>>Using VS2008
>>>>>I have an app that has an edit box that contains the Clients Age. I'm
>>>>>doing
>>>>>the validity check when the edit box looses focus. This works great
>>>>>when
>>>>>the user clicks a button that runs the application. However, if the
>>>>>user
>>>>>clicks Run App from the menu, the edit box does not loose the focus...
>>>>>therefore the check is not made.
>>>>>
>>>>>I can tell you that the code for File>Run does nothing more that call
>>>>>the
>>>>>::OnFileRunapplication
>>>>>
>>>>>What's the easiest way to resolve this? Seems like I need to loose the
>>>>>focus of the edit box before making a call to ::OnFileRunapplication.
>>>>>
>>>>>Thanks
>>>> Joseph M. Newcomer [MVP]
>>>> email: newcomer(a)flounder.com
>>>> Web: http://www.flounder.com
>>>> MVP Tips: http://www.flounder.com/mvp_tips.htm
>> Joseph M. Newcomer [MVP]
>> email: newcomer(a)flounder.com
>> Web: http://www.flounder.com
>> MVP Tips: http://www.flounder.com/mvp_tips.htm
Joseph M. Newcomer [MVP]
email: newcomer(a)flounder.com
Web: http://www.flounder.com
MVP Tips: http://www.flounder.com/mvp_tips.htm