Запретить пользователям отправлять форму, нажав Enter


У меня есть опрос на веб-сайте, и, похоже, есть некоторые проблемы с пользователями, которые нажимают enter (я не знаю, почему) и случайно отправляют опрос (форму), не нажимая кнопку отправки. Есть ли способ предотвратить это?

Я использую HTML, PHP 5.2.9 и jQuery в опросе.

27   624   2009-05-22 01:09:25

27 ответов:

Вы можете использовать такой метод, как

$(document).ready(function() {
  $(window).keydown(function(event){
    if(event.keyCode == 13) {
      event.preventDefault();
      return false;
    }
  });
});

при чтении комментариев к исходному сообщению, чтобы сделать его более удобным и позволить людям нажимать введите если они заполнили все поля:

function validationFunction() {
  $('input').each(function() {
    ...

  }
  if(good) {
    return true;
  }
  return false;
}

$(document).ready(function() {
  $(window).keydown(function(event){
    if( (event.keyCode == 13) && (validationFunction() == false) ) {
      event.preventDefault();
      return false;
    }
  });
});

запретить ввод ключа в любом месте

если у вас нет <textarea> в вашей форме, а затем просто добавьте следующее к вашему <form>:

<form ... onkeypress="return event.keyCode != 13;">

или с помощью jQuery:

$(document).on("keypress", "form", function(event) { 
    return event.keyCode != 13;
});

это приведет к тому, что каждое нажатие клавиши внутри формы будет проверяться на код ключа. Если это не 13 (ключ Enter), то он вернет true и все будет идти так, как ожидалось. Если он равен 13 (клавиша Enter), то он вернет false и все сразу остановится, поэтому форма не будет отправлена.

The keypress событие является предпочтительным по сравнению с keydown так как это срабатывает только тогда, когда символ фактически вставляется. Элемент keydownkeyup) увольняют, когда любой клавиша нажата, включая клавиши управления. И,keyCode на keypress представляет вставляемый фактический символ, а не используемый физический ключ. Таким образом, вам не нужно явно проверять, нажата ли клавиша ввода Numpad (108). Элемент keyup слишком поздно, чтобы заблокировать форма представить.

отметим, что $(window) как было предложено в некоторых других ответах вместо $(document) не работает keydown/keypress/keyup в IE

разрешить ввод ключа только в текстовых областях

если у вас <textarea> в вашей форме (которая конечно должны принять клавишу Enter), а затем добавить обработчик нажатия клавиши для каждого отдельного элемента ввода, который не является <textarea>.

<input ... onkeypress="return event.keyCode != 13;">
<select ... onkeypress="return event.keyCode != 13;">
...

чтобы уменьшить шаблон, это лучше сделать с помощью jQuery:

$(document).on("keypress", ":input:not(textarea)", function(event) {
    return event.keyCode != 13;
});

если у вас есть другие функции обработчика событий, прикрепленные к этим элементам ввода, которые вы также хотите вызвать по какой-либо причине, то только предотвратите поведение события по умолчанию вместо возврата false, чтобы оно могло правильно распространяться на другие обработчики.

$(document).on("keypress", ":input:not(textarea)", function(event) {
    if (event.keyCode == 13) {
        event.preventDefault();
    }
});

разрешить ввод ключа на textareas и отправить кнопки только

если вы хотите разрешить ввод ключа на кнопках отправки <input|button type="submit"> тоже, то вы всегда можете уточнить селектор, как показано ниже.

$(document).on("keypress", ":input:not(textarea):not([type=submit])", function(event) {
    // ...
});

отметим, что input[type=text] как было предложено в некоторых других ответах, не охватывает эти нетекстовые входы HTML5, так что это не хороший селектор.

мне пришлось поймать все три события, связанные с нажатием клавиш, чтобы предотвратить отправку формы:

    var preventSubmit = function(event) {
        if(event.keyCode == 13) {
            console.log("caught ya!");
            event.preventDefault();
            //event.stopPropagation();
            return false;
        }
    }
    $("#search").keypress(preventSubmit);
    $("#search").keydown(preventSubmit);
    $("#search").keyup(preventSubmit);

вы можете объединить все вышеперечисленное в красивую компактную версию:

    $('#search').bind('keypress keydown keyup', function(e){
       if(e.keyCode == 13) { e.preventDefault(); }
    });

Если вы используете скрипт для выполнения фактического отправки, то вы можете добавить строку "return false" в обработчик onsubmit следующим образом:

<form onsubmit="return false;">

вызов submit () в форме из JavaScript не вызовет событие.

использование:

$(document).on('keyup keypress', 'form input[type="text"]', function(e) {
  if(e.keyCode == 13) {
    e.preventDefault();
    return false;
  }
});

Это решение работает на всех формах на веб-сайте (также на формах, вставленных с Ajax), предотвращая только введитеs во входных текстах. Поместите его в функцию готовности документа и забудьте об этой проблеме на всю жизнь.

вместо того, чтобы запретить пользователям нажимать введите, что может показаться неестественным, вы можете оставить форму как есть и добавить дополнительную проверку на стороне клиента: когда опрос не завершен, результат не отправляется на сервер, и пользователь получает приятное сообщение о том, что нужно закончить, чтобы заполнить форму. Если вы используете jQuery, попробуйте плагин проверки:

http://docs.jquery.com/Plugins/Validation

для этого потребуется больше работа, чем ловить введите кнопка, но, конечно, это обеспечит более богатый пользовательский опыт.

хороший простой маленький jQuery решение:

$("form").bind("keypress", function (e) {
    if (e.keyCode == 13) {
        return false;
    }
});

Я пока не могу комментировать, поэтому я опубликую новый ответ

принятый ответ в порядке, но он не останавливал submit На numpad enter. По крайней мере, в текущей версии Chrome. Мне пришлось изменить условие кода ключа на это, тогда он работает.

if(event.keyCode == 13 || event.keyCode == 169) {...}

Это мое решение, чтобы достичь цели, он чист и эффективен.

$('form').submit(function () {
  if ($(document.activeElement).attr('type') == 'submit')
     return true;
  else return false;
});

совершенно другой подход:

  1. первый <button type="submit"> в форме активируется при нажатии введите.
  2. это верно, даже если кнопка спрятана с style="display:none;
  3. скрипт для этой кнопки можно вернуться false, что прерывает процесс подачи.
  4. вы все еще можете иметь другое <button type=submit> чтобы отправить форму. Просто верните true в каскаде подчинение.
  5. клавишей введите в то время как реальная кнопка отправки фокусируется активирует реальную кнопку отправки.
  6. клавишей введите внутри <textarea> или другие элементы управления формы будут вести себя как обычно.
  7. клавишей введите внутри <input> элементы управления формой вызовут первый <button type=submit>, который возвращает false, и таким образом ничего не происходит.

таким образом:

<form action="...">
  <!-- insert this next line immediately after the <form> opening tag -->
  <button type=submit onclick="return false;" style="display:none;"></button>

  <!-- everything else follows as normal -->
  <!-- ... -->
  <button type=submit>Submit</button>
</form>

придание форме действия " javascript: void (0);", похоже, делает трюк

<form action="javascript:void(0);">
<input type="text" />
</form>
<script>
$(document).ready(function() {
    $(window).keydown(function(event){
        if(event.keyCode == 13) {
    alert('Hello');
        }
    });
});
</script>

раздел 4.10.22.2 неявное представление спецификации W3C HTML5 говорит:

A form элемент по умолчанию первый отправить кнопку на дерево чей владелец форма это form элемент.

Если пользовательский агент поддерживает разрешение пользователю неявно отправлять форму (например, на некоторых платформах нажатие клавиши "enter" во время текстовое поле фокусируется неявно отправляет форму), а затем делает это для формы, у которой по умолчанию определен поведение активации!--5--> должен заставить агента пользователя выполнить шаги активации синтетического щелчка на по умолчанию.

Примечание: следовательно, если по умолчанию отключена, форма не отправляется при использовании такого неявного механизма представления. (Ля кнопка не имеет поведение активации!--5--> когда отключен.)

таким образом, совместимый со стандартами способ отключить любое неявное представление формы заключается в размещении отключенной кнопки отправки в качестве первой кнопки отправки в форме:

<form action="...">
  <!-- Prevent implicit submission of the form -->
  <button type="submit" disabled style="display: none" aria-hidden="true"></button>

  <!-- ... -->

  <button type="submit">Submit</button>
</form>

одной из приятных особенностей этого подхода является то, что он работает без JavaScript; независимо от того, включен ли JavaScript, требуется соответствующий стандартам веб-браузер для предотвращения неявной формы подчинение.

мне нужно было предотвратить отправку только определенных входов, поэтому я использовал селектор классов, чтобы это была "глобальная" функция везде, где мне это нужно.

<input id="txtEmail" name="txtEmail" class="idNoEnter" .... />

и этот код jQuery:

$('.idNoEnter').keydown(function (e) {
  if (e.keyCode == 13) {
    e.preventDefault();
  }
});

альтернативно, если keydown недостаточно:

$('.idNoEnter').on('keypress keydown keyup', function (e) {
   if (e.keyCode == 13) {
     e.preventDefault();
   }
});

некоторые замечания:

изменение различных хороших ответов здесь,введите ключ, кажется, работает для keydown во всех браузерах. Для альтернативы, я обновил bind() до on() метод.

Я большой поклонник селекторов классов, взвешивая все плюсы и минусы и обсуждения производительности. Мое соглашение об именах-это "idSomething", чтобы указать, что jQuery использует его в качестве идентификатора, чтобы отделить его от стиля CSS.

  1. Не используйте type= "submit" для входов или кнопок.
  2. использовать type= "button" и использовать js [Jquery / angular / etc] для отправки формы на сервер.

вы можете сделать метод JavaScript, чтобы проверить, если введите клавиша была нажата, и если это так, чтобы остановить отправку.

<script type="text/javascript">
  function noenter() {
  return !(window.event && window.event.keyCode == 13); }
</script>

просто вызовите это в методе submit.

не ставя кнопку Отправить может сделать. Просто поместите скрипт на вход (type=button) или добавьте eventListener, если вы хотите, чтобы он отправлял данные в форме.

лучше использовать

<input type="button">

чем с помощью этого

<input type="submit">

у меня была аналогичная проблема, где у меня была сетка с "ajax textfields" (Yii CGridView) и только одна кнопка отправки. Каждый раз, когда я делал поиск по текстовому полю и нажимал enter в отправленной форме. Я должен был что-то сделать с кнопкой, потому что это была единственная общая кнопка между представлениями (шаблон MVC). Все, что мне нужно было сделать, это удалить type="submit" и поставить onclick="document.forms[0].submit()

Я думаю, что он хорошо покрыт всеми ответами, но если вы используете кнопку с некоторым кодом проверки JavaScript, вы можете просто установить onkeypress формы для ввода, чтобы вызвать ваш submit как ожидалось:

<form method="POST" action="..." onkeypress="if(event.keyCode == 13) mySubmitFunction(this); return false;">

onkeypress JS может быть все, что вам нужно сделать. Нет необходимости в более масштабных, глобальных изменениях. Это особенно верно, если вы не тот, кто кодирует приложение с нуля, и Вы были привлечены к исправлению чужого веб-сайта, не разрывая его на части и повторное тестирование.

в моем конкретном случае мне пришлось остановить ввод от отправки формы, а также имитировать нажатие кнопки отправки. Это связано с тем, что кнопка отправки имела обработчик щелчка, потому что мы были в модальном окне (унаследованный старый код). В любом случае вот мои комбинированные решения для этого случая.

    $('input,select').keypress(function(event) {
        // detect ENTER key
        if (event.keyCode == 13) {
            // simulate submit button click
            $("#btn-submit").click();
            // stop form from submitting via ENTER key press
            event.preventDefault ? event.preventDefault() : event.returnValue = false;
        }
    });

этот вариант использования особенно полезен для людей, работающих с IE8.

это работает для меня

jQuery.each($("#your_form_id").find('input'), function(){
    $(this).bind('keypress keydown keyup', function(e){
       if(e.keyCode == 13) { e.preventDefault(); }
    });
});

что-то я не увидел ответа на: при переходе через элементы на странице, нажав введите когда вы доберетесь до кнопки Отправить вызовет обработчик onsubmit на форме, но он будет записывать событие как MouseEvent. Вот мое короткое решение для покрытия большинства оснований:

это не ответ, связанный с jQuery

HTML

<form onsubmit="return false;" method=post>
  <input type="text" /><br />
  <input type="button" onclick="this.form.submit()" value="submit via mouse or keyboard" />
  <input type="button" onclick="submitMouseOnly(event)" value="submit via mouse only" />
</form>

JavaScript

window.submitMouseOnly=function(evt){
    let allow=(evt instanceof MouseEvent) && evt.x>0 && evt.y>0 && evt.screenX > 0 && evt.screenY > 0;
    if(allow)(evt.tagName=='FORM'?evt.target:evt.target.form).submit();
}

чтобы найти работу пример: https://jsfiddle.net/nemesarial/6rhogva2/

Я хотел бы добавить немного кода CoffeeScript (не проверено в полевых условиях):

$ ->
    $(window).bind 'keypress', (event) ->
        if event.keyCode == 13
            unless {'TEXTAREA', 'SELECT'}[event.originalEvent.srcElement.tagName]
                event.preventDefault()

(Я надеюсь, вам понравится хороший трюк в предложении unless.)

здесь уже есть много хороших ответов, я просто хочу внести свой вклад с точки зрения UX. Элементы управления клавиатуры в формах очень важно.

вопрос в том, как отключить от подачи на нажатие клавиши Enter. Не как игнорировать Enter в приложение. Поэтому рассмотрите возможность присоединения обработчика к элементу формы, а не к окну.

отключение Enter для отправки формы все равно следует разрешить следующее:

  1. отправка формы с помощью Enter когда кнопку "Отправить" ориентирована.
  2. форма представления, когда все поля заполнены.
  3. взаимодействие с кнопками без отправки через Enter.

это просто шаблон, но он следует всем трем условиям.

$('form').on('keypress', function(e) {
  // Register keypress on buttons.
  $attr = $(e.target).attr('type);
  if ($attr === 'button' || $attr === 'submit') {
    return true;
  }

  // Ignore keypress if all fields are not populated.
  if (e.which === 13 && !fieldsArePopulated(this)) {
    return false;
  }
});

только блок SUBMIT но не другие, важные функции клавиши enter, такие как создание нового абзаца в <textarea>:

window.addEventListener('keydown', function(e){
    //set default value for variable that will hold the status of keypress
    pressedEnter = false;

    //if user pressed enter, set the variable to true
    if(event.keyCode == 13)
        pressedEnter = true;

    //we want forms to disable submit for a tenth of a second only
    setTimeout(function(){
        pressedEnter = false;
    },100)

})

//find all forms
var forms = document.getElementsByTagName('form')

//loop through forms
for(i = 0; i < forms.length; i++){
    //listen to submit event
    forms[i].addEventListener('submit', function(e){
        //if user just pressed enter, stop the submit event
        if(pressedEnter == true) {
            e.preventDefault();
            return false;
        }
    })
}

это сработало для меня во всех браузерах после большого разочарования в других решениях. Внешняя функция name_space - это просто держаться подальше от объявления глобалов, что я также рекомендую.

$(function() {window.name_space = new name_space();}); //jquery doc ready
function name_space() {
    this.is_ie = (navigator.userAgent.indexOf("MSIE") !== -1);

    this.stifle = function(event) {
        event.cancelBubble;
        event.returnValue = false;
        if(this.is_ie === false) {
            event.preventDefault();
        }
        return false;
    }

    this.on_enter = function(func) {
        function catch_key(e) {
            var enter = 13;
            if(!e) {
                var e = event;
            }
            keynum = GetKeyNum(e);
            if (keynum === enter) {
                if(func !== undefined && func !== null) {
                    func();
                }
                return name_space.stifle(e);
            }
            return true; // submit
        }

        if (window.Event) {
            window.captureEvents(Event.KEYDOWN);
            window.onkeydown = catch_key;
        }
        else {
            document.onkeydown = catch_key;
        }

        if(name_space.is_ie === false) {
            document.onkeypress = catch_key;    
        }
    }
}

пример использования:

$(function() {
    name_space.on_enter(
        function () {alert('hola!');}
    );
});

в моем случае у меня было несколько jQuery UI автозаполнение полей и текстовых областей в форме, поэтому я определенно хотел, чтобы они приняли введите. Поэтому я удалил type="submit" ввод из формы и добавил якорь <a href="" id="btn">Ok</a> вместо. Затем я стилизовал его как кнопку и добавил следующий код:

$( '#btn' ).click( function( event ){
    event.preventDefault();
    if ( validateData() ){
        $( 'form#frm' ).append( '<input type="submit" id="frm-submit" style="display:none;"></input>' );
        setTimeout( function(){ $( '#frm-submit' ).click(); }, 500 );
    }
    return false;
});

если пользователь заполняет все необходимые поля, validateData() успешно и форма отправляется.

использование:

// Validate your form using the jQuery onsubmit function... It'll really work...

$(document).ready(function(){
   $(#form).submit(e){
       e.preventDefault();
       if(validation())
          document.form1.submit();
   });
});

function validation()
{
   // Your form checking goes here.
}

<form id='form1' method='POST' action=''>
    // Your form data
</form>