Peter Perháč
Peter Perháč

Reputation: 20782

How to avoid the ding sound when Escape is pressed while a TEdit is focused?

In code I have developed some years ago I have been using this a lot to close the current form on pressing the Escape key at any moment:

procedure TSomeForm.FormKeyPress(Sender: TObject; var Key: Char);
begin
    if key = #27 then close;
end;

This behaviour is defined for the TForm. The form's KeyPreview property is be set to True to let the form react to key presses before any other components. It all works perfectly well for the best part of the program, however, when the Escape key is pressed while a TEdit component is focused a sound (a ding sound used by Windows to signify invalid operation) is issued. It still works fine but I have never quite managed to get rid of the sound.

What's the problem with this?


Steps to recreate:

Upvotes: 8

Views: 4933

Answers (4)

TobyOne
TobyOne

Reputation: 11

Using the menu items and setting them to invisible, and using the shortcut, is a quick workaround that I've just stumbled across, but won't work if you need a shortcut that uses a character that is used in the first letter of an existing shortcut: For example for Alt+ENTER, you need to add something like this to the form create procedure:

MainMenu1.Items[0].ShortCut:=TextToShortCut('Alt+e');

However it's probably easier to use TActionList instead, and even though something like Alt+E is not listed you can add it.

Upvotes: 1

user3268424
user3268424

Reputation: 1

Starting from Jim's answer (thanks Jim) I had to make it work for me. What I needed was to make a dropped down combobox close keeping the selected item and move to the next/previous control when TAB/shift+TAB was pressed. Everytime I did press TAB the annoying sound filled the room. My work arroud was using onKeyDown event to catch the shiftstate, declaring var aShift: boolean; in form's interface and use the following code:

procedure TForm2.StComboKeyDown(Sender: TObject; var Key: Word; Shift: TShiftState);
begin
  if ssShift in Shift then aShift := true else aShift := false;
end;

procedure TForm2.StComboKeyPress(Sender: TObject; var Key: Char);
begin
 if Key=char(VK_TAB) then
   begin
     Key := #0;
     StCombo.DroppedDown := false;
     if aShift
       then previousControl.SetFocus
       else nextControl.SetFocus;
   end;
end;

Upvotes: 0

user1920453
user1920453

Reputation: 19

It's an old thread... but anyway, here's a far better one: catching Alt-C!

Unlike ESC, Alt-C isn't serviced by KeyPress, so setting Key to #0 in KeyPress doesn't work, and the horrendous "ding!" is issued every time. After hours of trying, here's the workaround I found: - create a main menu option to service the request - set its ShortCut to Alt+C - yes indeed, that is NOT one of the available ShortCut choices(!!)... but it does work anyway! - do the processing in that menu option's OnClick - you may even make in "in the background": you may set the menu option's Visible to false - as long as its Enabled stays true, it will be activated by Alt-C even though it will not be visible in the menu.

Hope that may help! And if you have something more elegant, please advise.

Upvotes: -1

Jim McKeeth
Jim McKeeth

Reputation: 38703

You get the ding because you left the ESC in the input. See how Key is a var? Set it to #0 and you eliminate the ding. That removes it from further processing.

procedure TSomeForm.FormKeyPress(Sender: TObject; var Key: Char);
begin
    if key = #27 then 
    begin
      key := #0;
      close;
    end;
end;

KeyPreview is just that, a preview of what will be passed to the controls unless you stop it.

Upvotes: 28

Related Questions