9

Might it is very simple question but I never touched delphi. I have a edit box and that can accept character. But on some special condition I have to verify the edit box character are only numbers.

How can we do that?

Note: user can enter any char but at the time of validation I have to verify above one.

David Heffernan
  • 601,492
  • 42
  • 1,072
  • 1,490
PawanS
  • 7,033
  • 14
  • 43
  • 71
  • 4
    please clarify why you don't want to block the user from entering invalid data. Users getting stuck with invalid data in an entry field is considered a "user trap" and is considered bad user interface design by many developers. – Warren P Jun 23 '11 at 15:30
  • @Warren Please clarify why you want to block users entering values at source and thus robbing them of the feedback of seeing key presses resulting in characters appearing on screen. – David Heffernan Jun 23 '11 at 16:35
  • 1
    Not allowing the user to enter invalid values into the control does not mean not giving him feedback. You can still pop up some message saying "you entered a wrong value, etc..." like when Capslock is on at windows login. – Stefan Glienke Jun 23 '11 at 20:06
  • @David: No response to keystroke may in fact confuse some users also. Perhaps an ideal response would be to flash a large red light on the screen, and beep. If they persist in typing non-digits, we may have to give them an eNoogie. :-) – Warren P Jun 23 '11 at 21:12
  • @Warrent It's you that is proposing "no response to keystroke". And yes it would be confusing. – David Heffernan Jun 23 '11 at 21:19
  • @Stefan - that's exactly what I would prefer. Why should users fill the invalid data (e.g. chars into number box) and get the error message they did something wrong. IMHO it saves the time. –  Jun 23 '11 at 21:39
  • So david, confused user, or stuck user? You would rather have them stuck? Either way, it's a trap. – Warren P Jun 23 '11 at 22:35
  • @warren why would they be stuck? I'm assuming the user is capable of deleting text. – David Heffernan Jun 24 '11 at 06:27
  • @Warren, @Stefan: Blocking my input is like having my hands beaten, I'd prefer just being told or hinted that my input is wrong, so I could fix it myself. It doesn't necessarily mean I must be informed about the mistake only when I press Enter. You can employ such things like changing the text colour or the textbox's background colour. You can even pop up a message informing you something might be amiss *without blocking the input*, yes, like Windows does when Caps Lock is on at the login screen. – Andriy M Jun 24 '11 at 06:58
  • the user might be less likely to get stuck if we show a red X beside an invalid entry at least. – Warren P Jun 27 '11 at 12:11

4 Answers4

12

I don't know what event you intend to use to invoke validation, but the validation can be done like this:

if TryStrToInt(Edit1.Text, Value) then
  DoSomethingWithTheNumber(Value)
else
  HandleNotANumberError(Edit1.Text);
David Heffernan
  • 601,492
  • 42
  • 1,072
  • 1,490
  • 2
    Shouldn't there be an 'else' before the call to DoSomethingWithTheNumber? – awmross Jun 24 '11 at 00:02
  • @awmross good point. In my head the error handler raised an exception but that's too strong and assumption. – David Heffernan Jun 24 '11 at 06:23
  • Oh thanks! I was converting edit box text to char and comparing each char is in set or [0..9] exist or not. Based on that I tried, but this looks shorter. – PawanS Jun 27 '11 at 05:23
  • 1
    @GAPS If you want to restrict the answers to 12 year old versions of the software you really should say so when you ask the question. – David Heffernan Jun 27 '11 at 08:02
8

I don't understand why you would want to allow a user to enter a character, and later not allow it to pass validation.

If you really do need to block entry, then a control that does this for you is better than hacking this up yourself. If your version of delphi is really old, then try out the JVCL: TJvValidateEdit in the JVCL component library, for example, in all versions of delphi. However, in regular recent delphi versions (2009 and later), there is already built in several possible solutions including TMaskEdit and TSpinEdit.

If you really only need to write a validation method, then consider using a regex or hand-coded validation function, and keep that code separate from the control.

// Taking OP question obsessively literally, this 
// function doesn't allow negative sign, decimals, or anything
// but digits
function IsValidEntry(s:String):Boolean;
var
  n:Integer;
begin
  result := true;
  for n := 1 to Length(s) do begin
    if (s[n] < '0') or (s[n] > '9') then
    begin
       result := false;
       exit;
    end;
  end;
end;
Warren P
  • 65,725
  • 40
  • 181
  • 316
  • +1 My thoughts exactly, I fail to understand the code though, David code does that in one line: `TryStrToInt()` – Johan Jun 23 '11 at 15:36
  • 3
    @Warren, he said, "But on some special condition I have to verify the edit box character are only numbers." So he needs to verify this only in certain circumstances, not all the time. BTW, plz add NumbersOnly property in Edit controls in the recent versions of Delphi to the list of your built-in solution. Setting NumbersOnly property to True will make the edit control to reject any non-numeric character. – vcldeveloper Jun 23 '11 at 15:36
  • 1
    NumbersOnly is not a valid option imo nor is setting it by WinAPI (ES_NUMBER) since even then you can paste invalid text. – Stefan Glienke Jun 23 '11 at 20:03
  • Oh interesting find @vcldeveloper! Sounds problematic though? – Warren P Jun 23 '11 at 21:11
  • @Stefan, I cannot reproduce the issue you mentioned in Windows 7, using Delphi 2010. An Edit control which its NumbersOnly propert is set to True does not accept any alphabetic character getting paste in it. – vcldeveloper Jun 24 '11 at 06:48
  • I just tested it on Windows XP and you can paste non number characters into the edit according to http://msdn.microsoft.com/en-us/library/bb775464.aspx Although it seems they changed it for Vista and higher (also see comments on the msdn article) – Stefan Glienke Jun 24 '11 at 13:19
4

I know you said user can enter any char but at the time of validation.
However I would like to offer an alternative, because it seems very silly to allow a user to enter values, only to complain to the user 1 minute later; that just smells well... not nice.

I would disallow entry of anything but numbers.
If you have integers thats particularly easy:

Fill in the OnKeyPress event for the editbox.

procedure TForm1.Edit1KeyPress(Sender: TObject; var Key: Char) ;
begin
  if not(Key IN ['0'..'9', #8, #9, #13, #27, #127]) then key:= #0;
end;

This will drop anything that's not a number.

If you allow negative numbers you'll need to extra checking to see if the - has not been entered before.

procedure TForm1.Edit1KeyPress(Sender: TObject; var Key: Char) ;
var
  Edit1Text: string;
begin
  if (Key = '-') and Pos('-',Edit1.Text) = 0 then begin
    Edit1.Text:= '-' + Edit1.Text;  //Force the '-' to be in the front.
  end
  else if (Key = '-') and Pos('-',Edit1.Text) <> 0 then begin  //else flip the sign
    Edit1Text:= Edit1.Text;
    Edit1.Text:= StringReplace(Edit1Text, '-', '',[]);
  end;
  if not(Key IN ['0'..'9', #8, #9, #13, #27, #127]) then key:= #0;
end;

Because the user can also paste data into an edit box, you'll still have to check the data upon change of the text in the edit.
Because this gets rather fiddly in the ONKeyPress event I use a custom edit component that does this kind of checking and prevents the user from entering foot-in-mouth input into an edit box.

Personally I don't believe in ever issuing an error message, you should always strive to not allow the user to enter invalid data in the first place.

Johan
  • 74,508
  • 24
  • 191
  • 319
  • You might want to change that set into `['0'..'9', #8, #9, #13, #27, #127, '-']`. Especially backspace and delete are handy for entering input. ;) (And for floats, you might like to include DecimalSeparator also.) – NGLN Jun 23 '11 at 14:31
  • -1 For not paying attention to OP's note. Sorry. Validating numbers on the fly could be the exception, but validation on exit or on submitting is good common practice. – NGLN Jun 23 '11 at 14:35
  • @NGLN, I refuse to write programs that issue error messages, you I'll ignore your comment. It's just a strong believe I have, the user is always right. – Johan Jun 23 '11 at 14:44
  • @Johan David doesn't explicitly issue an error message: `HandleNotANumberError` e.g. might set the focus to that edit control and give it a red background. – NGLN Jun 23 '11 at 14:47
  • 1
    @Johan: Careful. Not all errors come from the user, and if you don't inform the user of what's going wrong this can lead to frustration on their part. – Mason Wheeler Jun 23 '11 at 14:48
  • @Mason, NGLN, I'm very aware of that I just try to go the extra mile to avoid issuing errors and NGLN's option of displaying in red I sometimes use as well when the input validation gets too complex. I just believe in giving feedback other than though modal dialogboxes with a single button. 99% of the cases I succeed, 1% I'm deeply ashamed and issue a would you like to yes/no dialog. I have never programmed a error dialog though. **Feedback is very important of course (modeless feedback that is)** – Johan Jun 23 '11 at 14:54
  • Virtually downvoted. Question states "user can enter any char but at the time of validation I have to verify above one". Still your answer is worth taking into account, – Kromster Jun 23 '11 at 14:57
  • 4
    You still have to validate the text on exit/change since there are more ways to put data into an edit box than pressing keys. Pasting text for example. – PetriW Jun 23 '11 at 15:18
  • "Personally I don't believe in ever issuing an error message, you should always strive to not allow the user to enter invalid data in the first place." That's OK up to a point, but you must let the user discover why their input is not being accepted. – David Heffernan Jun 23 '11 at 15:23
  • @PertiW, yes, it's been a long time since I wrote my TValidEdit class, but IIRC I did end up doing the checking in the change event. – Johan Jun 23 '11 at 15:24
  • @David, I use a blue colored hint box for that, that displays the allowed values when the user enters a wrong char *(or invalid combination of chars)*, combined with some message in the statusbar. – Johan Jun 23 '11 at 15:25
  • @johan I did same, but client don't like that. Forcefully I had to move to silly behave but both seems good at some point – PawanS Jun 27 '11 at 05:31
4

But on some special condition I have to verify the edit box character are only numbers.

You need two edit-controls. One for the numbers-only value and one for the allow-all value. Enable or disable the control which match the condition. If the two controls have good captions (and perhaps hints, why a control is enabled or disabled) so the user knows what he has to enter and why.

  • I don't like blocking the user. A scenario:
  • I enter "abc123"
  • on leaving the edit control I get an error message "only numbers allowed"
  • I realize that I have forgotten to reach the special condition
  • I want to do something to reach the special condition
  • but I can't because I always get the error message "only numbers allowed"
  • so I have to correct the value to "123"
  • do the things to reach the special condition
  • retype my old "abc123" value again

aarrgghh :-)

For simple data entry forms I do the following: I allow wrong input but switch the font color to red for each edit control with an invalid input (red font color is not enough when an empty value is not allow). If the user try to post the data I give one error message which inform the user about all invalid input fields and abort the post.

Heinz Z.
  • 1,537
  • 3
  • 14
  • 29
  • yeah!! even i do the same. but 1 thing i want to mention about that condition. That condition is simply based on a check box value, nothing more than that – PawanS Jun 27 '11 at 05:28