Zatrzymaj „Ding” po naciśnięciu Enter

124

Mam bardzo prostą aplikację Windows Forms. A w systemie Windows (lub przynajmniej w aplikacjach Windows Forms) po naciśnięciu klawisza Enter w jednowierszowej kontrolce TextBox usłyszysz dźwięk Ding. To nieprzyjemny dźwięk, który wskazywał, że nie można wprowadzić nowej linii, ponieważ jest to jednowierszowy TextBox.

To wszystko jest w porządku. Jednak w moim formularzu mam 1 pole tekstowe i przycisk wyszukiwania. Pozwalam użytkownikowi przeprowadzić wyszukiwanie, naciskając klawisz Enter po zakończeniu pisania, aby nie musiał używać myszy do klikania przycisku wyszukiwania.

Ale pojawia się ten dźwięk Ding. To jest bardzo irytujące.

Jak możemy sprawić, by dźwięk w ogóle nie był odtwarzany w mojej formie?

@David H - Oto jak wykrywam naciśnięcie klawisza Enter:

private void textBox1_KeyUp(object sender, KeyEventArgs e)
{
    if (e.KeyCode == Keys.Enter)
    {
        // Perform search now.
    }
}
bendr
źródło
Jak rozpoznajesz, że klawisz Enter został naciśnięty, gdy fokus znajduje się w polu tekstowym?
David Heffernan,
W okienku Właściwości kliknij dwukrotnie zdarzenie KeyDown lub KeyUp. Następnie w widoku kodu wpisujesz kod, który mam zamiar umieścić w moim pytaniu.
bendr
2
KeyPress jest prawdopodobnie właściwym zdarzeniem i chcesz ustawić e.Handled = true
David Heffernan
Dziękuję @David, nie wiedziałem tego :)
bendr
7
Żałuję, że nie ma sposobu na stłumienie irytującego buczenia, ale pozwól, aby naciśnięcie klawisza wybuchło. Czasami naciśnięcie klawisza jest po prostu naciśnięciem klawisza, nie ma potrzeby włączania alarmu.
flipdoubt

Odpowiedzi:

56

Zapoznaj się z właściwością Form.AcceptButton . Możesz go użyć do określenia domyślnego przycisku dla formularza, w tym przypadku do naciśnięcia klawisza Enter.

Z dokumentów:

Ta właściwość umożliwia wyznaczenie domyślnej akcji, która ma wystąpić, gdy użytkownik naciśnie klawisz ENTER w aplikacji. Przycisk przypisany do tej właściwości musi być IButtonControl, który znajduje się w bieżącym formularzu lub znajduje się w kontenerze w bieżącym formularzu.

Istnieje również właściwość CancelButton, gdy użytkownik naciśnie klawisz Escape.

mdm
źródło
1
Dziękuję @mdm, to działało najlepiej dla mnie. :) Wrócę do głosowania za, gdy będę miał więcej rep.
bendr
1
@bendr Mam ten sam problem .. ale używam UserControl .. nie ma Form.AcceptButton .. jak to naprawić?
Murhaf Sousli
1
Wydaje się, że program Visual Studio nie ma odpowiedniego pola w okienku Właściwości. Najwyraźniej trzeba to zrobić w kodzie. this.AcceptButton = buttonOK; this.CancelButton = buttonCancel;
Chris,
5
To nie zadziała w przypadku ToolStripButtons lub jeśli chcesz użyć klawisza ENTER do sprawdzenia poprawności TextBox lub ToolStripTextBox. Lepszym podejściem byłaby odpowiedź Lucio Fonseca, który pracował dla mnie z ToolStripTextBox.
Robert S.
Nie widzę twojego rozwiązania: nie masz praktycznego ćwiczenia, aby być bardziej oświeconym
Pedro Ávila
198

Mi to pasuje:

private void textBox1_KeyDown(object sender, KeyEventArgs e)
{

    //Se apertou o enter
    if (e.KeyCode == Keys.Enter)
    {
        //enter key is down

        this.doSomething();

        e.Handled = true;
        e.SuppressKeyPress = true;

     }

 }

SuppressKeyPress to prawdziwa sztuczka. Mam nadzieję, że to pomoże.

Lucio Fonseca
źródło
30
Moim zdaniem to jedyna ważna odpowiedź. e.Handled = true;był niewystarczający; to właśnie SuppressKeyPresszałatwiło sprawę .
Jonathon Reinhart
12
textBox1_KeyUp będzie działał w tej sytuacji niezależnie od Handled lub SuppressKeyPress
stackuser83
4
Działa dla mnie z ToolStripTextBox.KeyDown. Nie było innego rozwiązania. Dzięki!
Robert S.
1
To nie zadziałało na moim textboxi KeyDownwydarzeniu
Alex Jolig
7
To powinna być akceptowana odpowiedź. Aktualnie zaakceptowana odpowiedź wymaga umieszczenia standardowego przycisku na formularzu, co jest nieprzyjemne.
Javid
56

Próbować

textBox.KeyPress += new KeyPressEventHandler(keypressed);

private void keypressed(Object o, KeyPressEventArgs e)
{
    if (e.KeyCode == Keys.Enter)
    {
        e.Handled = true; //this line will do the trick
    }
}
FIre Panda
źródło
Dobrze, ale będzie działać tylko wtedy, gdy fokus jest nadal na TextBox. A co jeśli użytkownik naciśnie Tabpierwszy?
mdm,
4
@mdm Zależy od projektu interfejsu użytkownika. Być może OP chce tego działania tylko wtedy, gdy fokus znajduje się w polu tekstowym. To dość powszechne.
David Heffernan
2
Jeśli użytkownik nacisnął klawisz Tab, fokus nie będzie już znajdował się na TextBox, następny Contorl, który zostanie skupiony, to kontrolka przycisku, która nie wydaje tego dźwięku po naciśnięciu klawisza Enter. :-)
bendr
@David, dzięki za przykład. Właśnie tego spróbowałem. I za każdym razem, gdy umieszczam e.Handled = true w zdarzeniu .KeyPress, żaden inny kod nie jest wykonywany. Jedyną rzeczą, która się dzieje, cały tekst w polu tekstowym zostanie wybrany (a ja nawet nie mam kodu, który wybiera dowolny tekst)
bendr
1
Odpowiedź Lucio Fonseca była jedyną, jaką znalazłem, która rozwiązała problem.
Jonathon Reinhart
15

Po prostu dodaj e.SuppressKeyPress = true;oświadczenie „jeśli”.

private void textBox1_KeyUp(object sender, KeyEventArgs e)
{
    if (e.KeyCode == Keys.Enter)
    {
        //If true, do not pass the key event to the underlying control.
        e.SuppressKeyPress = true;  //This will suppress the "ding" sound.*/

        // Perform search now.
    }
}
brandonstrong
źródło
13

Możesz użyć KeyPress zamiast KeyUp lub KeyDown, co jest bardziej wydajne i oto jak sobie z tym poradzić

  private void textBox1_KeyPress(object sender, KeyPressEventArgs e)
    {
        if (e.KeyChar == (char)Keys.Enter)
        {
            e.Handled = true;
            button1.PerformClick();
        }
    }

i powiedz pokój „Ding”

Mawardy
źródło
2
To zadziałało idealnie dla mnie. e) Handled najwyraźniej wyłącza 'Ding'. Ustawienie przycisku „Prześlij” (w moim przypadku) jako domyślnego nie zadziałałoby, ponieważ chciałem inaczej obsługiwać klawisz „Enter” dla innych pól tekstowych w formularzu. <br/> <br/> Przy okazji : W tym projekcie używam VB. więc zamiast rzucać e.KeyChar, konwertuję to: if e.KeyChar = ChrW (Keys.Enter Then ....
Mark Ainsworth
1
W ramach KeyDown, używam e.Handledi e.SuppressKeyPressnie działało dla mnie - nadal dinging. Ale zmiana tego, jak zasugerowano tutaj, aby użyć KeyPress' event and e.Handled` zrobiła to ładnie.
Jinlye
To powinna być poprawna odpowiedź, dzięki
Firas Shrourou
7

Służy SuppressKeyPressdo zatrzymywania dalszego przetwarzania naciśnięcia klawisza po jego obsłudze.

public class EntryForm: Form
{
   public EntryForm()
   {
   }

   private void EntryTextBox_KeyDown(object sender, KeyEventArgs e)
   {
      if(e.KeyCode == Keys.Enter)
      {
         e.Handled = true;
         e.SuppressKeyPress = true;
         // do some stuff

      }
      else if(e.KeyCode == Keys.Escape)
      {
          e.Handled = true;
          e.SuppressKeyPress = true;
          // do some stuff

      }
   }

   private void EntryTextBox_KeyUp(object sender, KeyEventArgs e)
   {
      if(e.KeyCode == Keys.Enter)
      {
         // do some stuff

      }
      else if(e.KeyCode == Keys.Escape)
      {
         // do some stuff

      }
   }
}
Snehasish
źródło
2

Natknąłem się na ten post, próbując obsłużyć KeyDown, który zadziałał dla mnie.

If e.KeyCode = Keys.Enter Then
   e.SuppressKeyPress = True
   btnLogIn.PerformClick()
End If

Pomijanie naciśnięcia klawisza zatrzymuje wysyłanie zdarzenia do kontrolki podstawowej. Powinno to działać, jeśli ręcznie obsługujesz wszystko, co będzie robił klawisz Enter w tym polu tekstowym. Przepraszamy za Visual Basic.

Colin
źródło
2

Jest bardzo mała szansa, że ​​ktokolwiek dostanie tę odpowiedź, ale inne odpowiedzi są naprawdę przerażające. Tłumienie wydarzenia przy KeyDownzabijaniu 2 dodatkowych wydarzeń w jednym uderzeniu. Ustawienie e.Handledwłaściwości na truejest w tym kontekście bezużyteczne.
Najlepszym sposobem jest ustawienie Form.AcceptButtonwłaściwości na rzeczywisty przycisk wyszukiwania.
Jest też inny sposób wykorzystania Enterklucza - niektórzy mogą chcieć, aby działał jak TABprzycisk. Aby to zrobić, dodaj nowy Button, ustaw jego Locationwłaściwość poza Formobszarem (tj. (-100, -100)) - ustawienie Visiblewłaściwości na falsemoże Buttonw niektórych przypadkach wyłączyć moduły obsługi. Ustaw Form.AcceptButtonwłaściwość na nowy przycisk. W programie Clickobsługi zdarzeń dodaj następujący kod
this.SelectNextControl(ActiveControl, true, true, true, true)

Teraz możesz chcieć przenieść focustylko wtedy focus, gdy jest włączony TextBox, możesz chcieć przetestować ActiveControltyp lub użyć e.Supresswłaściwości w programach obsługi zdarzeń kontrolek, które nie są przeznaczone do użycia, Enterponieważ TAB to wszystko. Nie musisz nawet biće.KeyCode

ArtK
źródło
1
$("#txtSomething").keypress(function (e) {
        if (e.which == 13) {

            e.Handled = true; //This will prevent the "ding" sound

            //Write the rest of your code
        }
    });
Kod Miasto
źródło
To jest to, czego szukam.
Sid
1

W WinForms klawisz Enter powoduje dźwięk Ding, ponieważ nie określono właściwości formularza AcceptButton. Jeśli nie potrzebujesz przycisku AcceptButton, dźwięk dzwonka można wyciszyć, ustawiając w formularzu KeyPreview wartość true i wprowadzając następujące zdarzenie KeyPress:

private void Form_KeyPress(object sender, KeyPressEventArgs e)
{
    if (e.KeyChar == '\r')
        e.Handled = true;
}

Bez względu na to, która kontrola jest aktywna, po naciśnięciu klawisza Enter nie będzie więcej dźwięku. Ponieważ kolejność przetwarzania kluczowych zdarzeń to KeyDown, KeyPress i KeyUp, klawisz Enter będzie nadal działał dla zdarzeń KeyDown dla formantów.

Berry Jansen
źródło
0

Ustaw właściwość IsDefault przycisku wyszukiwania na true. Spowoduje to, że będzie to przycisk domyślny i zostanie automatycznie kliknięty po naciśnięciu klawisza Enter.

Zruty
źródło
Z dokumentów, do których To specify the default button of a form, set the AcceptButton property of the form to the desired button.
utworzyłeś łącze
Tak, sam to zbadałem. Wydaje się, że oba podejścia są wymienne. AcceptButtonwydaje się bardziej stylowy, ale jestem przyzwyczajony do IsDefaultsiebie.
Zruty
0

Cóż, żyłem z tym problemem wystarczająco długo i szukałem go tutaj.

Po zastanowieniu się nad tym od dłuższego czasu i szukaniu najprostszego sposobu, aby to naprawić, wymyśliłem najłatwiejszy, ale nie tak elegancki sposób, aby to naprawić.

Oto co zrobiłem.

  1. Umieść w formularzu 2 niewidoczne przyciski „OK” i „Cancel”.
  2. Ustaw właściwość AcceptButton i CancelButton w formularzu na niewidoczne przyciski.
  3. Nie dodano kodu do przycisków!

To rozwiązało wszystkie drugorzędne problemy wymienione w tym wątku, w tym ToolStripMenu. Moją największą skargą był BindingNavigator, kiedy wprowadzałem numer rekordu w bieżącą pozycję, aby nawigować i naciskać Enter.

Zgodnie z pierwotnym pytaniem, w którym programista chciał funkcji wyszukiwania po naciśnięciu przycisku Enter, po prostu umieściłem kod wyszukiwania w niewidocznym przycisku OK!

Jak dotąd wydaje się, że rozwiązuje to wszystkie problemy, ale jak wszyscy wiemy z Visual Studio, prawdopodobnie coś się pojawi.

Jedynym innym możliwym eleganckim sposobem, jaki mógłbym wymyślić, byłoby napisanie nowej klasy obsługi naciśnięć klawiszy, co w przypadku większości moich projektów wymaga dużo pracy.

user2793447
źródło
0

Możesz ustawić wieloliniowy tekst w polu tekstowym na wartość true, a następnie naciśnij klawisz Enter.

private void yourForm_Load(object sender, EventArgs e)
    {
        textBox1.Multiline = true;
    }

//then write your TextBox codes
private void textBox1_KeyUp(object sender, KeyEventArgs e)
{
    if (e.KeyCode == Keys.Enter)
    {
        // doSomething();
    }
}
Shedrack Ikwabe
źródło
0

Zmieniłem właściwości pola tekstowego dla wielowierszowego pola tekstowego i to działa dla mnie.

Christian Fontaine
źródło
Odpowiedź została już udzielona poniżej 22 lutego. O [wejdź] też trzeba się zająć;)
Goodies
-2
void RTextBox_KeyDown(object sender, KeyEventArgs e)
{
    if (e.KeyData == Keys.Enter)
    {
        //do ...
        bool temp = Multiline;
        Multiline = true;
        e.Handled = true;
        Multiline = temp;
    }
}
mahdi
źródło
1
To jest nadmiarowa odpowiedź z samym kodem, bez wyjaśnienia. Ponadto cały Multilinekod jest całkowicie nieistotny.
Jonathon Reinhart