Re: Delphi: Edit box, Listbox, calculations (math)

Posted by webmaster Guido on August 22, 2002 at 04:42:09:

In Reply to: Delphi: Edit box, Listbox, calculations (math) posted by Lesley on August 12, 2002 at 02:16:43:

: I want to have an edit box, which actives code when the enter key is pressed. The edit box must have a numerical entry, preceded by either + = * /. I need to check that the entry is valid and if it is, copy the entry to a listbox. If not then display an error message. The next part requires looping through the listbox entries keeping a running total e.g. if the entries in the listbox are +60, -20, *3 then the running total box/label will display 120.

Well ;-) that's an entire application you're asking for, not some simple tip... ;-)
Anyway, since this is not too complicated, and it might be interesting for other readers as well, ...let's give it a try ;-)

1. Let's enter the numbers in an edit-box called edEntry. In order to evaluate the keystrokes, we need the OnKeyPress event handler of edEntry. Each time a key is pressed when edEntry has the focus, we check if it is the ENTER key (ENTER is code #13). If it is the ENTER key:

A. Check the length of the text entered in edEntry. It should be at least 2: an operator + - / or * followed by at least one digit. If not: give an error message.
B. If check (A) is OK, check if the first character is an operator. If not: give an error message.
C. If (B) is OK, extract the numerical part of the text. That's the part starting from the second character, with a length equal to the total length minus one.
D. Convert this to a floating point number. We do this only to see if the number is valid, the real computation comes later...
Here's the nice part: if the conversion doesn't work because maybe the text doesn't represent a valid number, Delphi will show an error message and jump out of the event handler. In that case, the next step is skipped automatically, so nothing is added to the listbox.
E. Add the text of edEntry to the listbox.

2. Say that there is a button to start the calculation, btnCalculate. In its OnClick event handler, we first check if there is something in the listbox. If not, display an error. Otherwise, loop through all the items of the listbox, in each loop doing 2 things:

A. Convert the *text* of the item, minus the first character, to a *number* (floating point number).
B. Depending on the operator (first character of the item), add to RunTotal, or subtract, or multiply, or divide.

3. When all the items of the listbox have been processed, convert RunTotal to text and display it, for example in a label called lblTotal.

Below is some code to get started:

procedure TForm1.edEntryKeyPress(Sender: TObject; var Key: Char);
  S: string;
  Op: char;
  Num: real;
  if Key <> #13 then
  if Length(edEntry.Text) < 2 then
    ShowMessage('Enter an OPERATOR and a NUMBER')
  else begin
    Op := edEntry.Text[1];
    if not (Op in ['+', '-', '*', '/']) then
      ShowMessage('First character must be an OPERATOR')
    else begin
      S := copy(edEntry.Text, 2, Length(edEntry.Text) - 1);
      Num := StrToFloat(S);
      // If the previous line results in an error, 
      // Delphi shows an error message and the procedure
      // is aborted... thus skipping the next line

procedure TForm1.btnCalculateClick(Sender: TObject);
  i: integer;
  S: string;
  Total, Num: real;
  if Listbox1.Items.Count = 0 then begin
    ShowMessage('Enter some operators and numbers');
  Total := 0;
  for i := 0 to Listbox1.Items.Count - 1 do begin
    S := copy(Listbox1.Items[i], 2, Length(Listbox1.Items[i]) - 1);
    Num := StrToFloat(S);
    case Listbox1.Items[i][1] of
      '+': Total := Total + Num;
      '-': Total := Total - Num;
      '*': Total := Total * Num;
      '/': Total := Total / Num;
  lblResult.Caption := FloatToStr(Total);

Note that for a better program, we need to do some error checking when doing the calculations. Because when there is a divide by 0 somewhere, or the numbers get to big, Delphi will show an error message and the loop will be terminated before reaching the end.

Of course, steps (2) and (3) could be done also each time when ENTER is pressed, so you really don't need the button. But it's a lot easier to debug it this way, and only when it works, try omitting the button.

[ DelphiLand Discussion Forum ]