输入触发器按钮单击

我有一个有两个按钮的页面。一个是<button>元素,另一个是<input type="submit">元素。按钮按此顺序出现在页面上。如果我在窗体中的任何一个文本字段中并按下<Enter>,则会触发button元素的click事件。我认为这是因为button元素放在前面。

我找不到任何看起来可靠的方法来设置默认按钮,我也不想在这一点上。在没有更好的东西的情况下,我已经捕获了窗体上任何地方的一个按键,如果它是被按下的<Enter>键,我只是对它求反:

$('form').keypress( function( e ) {
var code = e.keyCode || e.which;


if( code === 13 ) {
e.preventDefault();
return false;
}
})

据我所知,到目前为止,它似乎是有效的,但感觉难以置信的笨拙。

有人知道更复杂的方法吗?

同样,这个解决方案是否存在我没有意识到的陷阱?

谢谢。

121641 次浏览

默认情况下,在表单的文本字段中按enter键将提交表单。如果您不希望它以这种方式工作,您必须捕获回车键并像您所做的那样使用它。这是没有办法的。即使表单中没有按钮,它也会以这种方式工作。

我会像下面这样做:在处理按钮的onclick事件(不提交)检查事件对象的键码。如果是回车,我会返回false。

您可以使用javascript阻止表单提交,直到适当的时间。举个简单的例子:

<form onsubmit='return false;' id='frmNoEnterSubmit' action="index.html">


<input type='text' name='txtTest' />


<input type='button' value='Submit'
onclick='document.forms["frmNoEnterSubmit"].onsubmit=""; document.forms["frmNoEnterSubmit"].submit();' />


</form>

按enter键仍然会触发表单提交,但javascript会阻止它实际提交,直到您实际按下按钮。

阅读HTML规范以真正理解预期的行为是很重要的:

HTML5规范明确说明了implicit submissions中发生的事情:

表单元素的默认按钮是按树顺序排列的第一个提交按钮,其表单所有者就是该表单元素。

如果用户代理支持让用户隐式提交表单(例如,在某些平台上,当文本字段被聚焦时,点击“enter”键隐式提交表单),那么对于默认按钮具有定义的激活行为的表单,这样做必须导致用户代理在默认按钮上运行合成的单击激活步骤。

这在HTML4规范中没有明确规定,但是浏览器已经实现了HTML5规范中描述的内容(这就是为什么显式包含它)。

编辑添加:

我能想到的最简单的答案是把你的提交按钮作为表单中的第一个[type="submit"]项,用css在表单底部添加填充,并绝对将提交按钮放置在你想要它的底部。

通过在聚焦的<input type="text">上按“Enter”,你会在第一个定位的元素<button><input type="submit">上触发“click”事件。如果你在<textarea>中按“Enter”,你只是创建了一个新的文本行。

参见示例在这里

你的代码阻止在<textarea>中创建新的文本行,所以你必须只捕捉<input type="text">的按键。

但是为什么你需要在文本字段中按Enter呢?如果你想通过按“Enter”来提交表单,但<button>必须保持在布局中的第一个,只需使用标记:将<input type="submit">代码放在<button>之前,并使用CSS保存所需的布局。

捕获'Enter'并保存标记:

$('input[type="text"]').keypress(function (e) {
var code = e.keyCode || e.which;
if (code === 13) {
e.preventDefault();
// also submit by pressing Enter:
$("form").submit();
}
});

我不认为你需要javascript或CSS来解决这个问题。

根据HTML 5按钮规范,没有类型属性的按钮与类型设置为“submit”的按钮被视为相同的,即作为提交包含其表单的按钮。将按钮类型设置为“button”应该可以防止您所看到的行为。

我不确定浏览器对此的支持,但在HTML 4.01按钮规范中指定了相同的行为,所以我希望它很好。

使用

<button type="button">Whatever</button>

应该能行。

原因是表单中的按钮的类型隐式设置为submit。正如zzzzBoz所说,Spec说在这种情况下触发的是第一个buttoninputtype="submit"。如果你特别设置了type="button",那么它将被浏览器从考虑中删除。

我添加了一个类型为“submit”的按钮作为表单的第一个元素,并使其不可见(width:0;height:0;padding:0;margin:0;border-style:none;font-size:0;)。工作类似于站点的刷新,即当按钮被按下时,我不做任何事情,除了站点再次加载。对我来说很好……

我的情况在表单元素中有两个Submit按钮:UpdateDeleteDelete按钮删除图像,Update按钮用表单中的文本字段更新数据库。

因为Delete按钮是表单中的第一个按钮,所以它是Enter键上的默认按钮。这不是我想要的。用户希望在更改一些文本字段后能够命中Enter

我找到了设置默认按钮在这里的答案:

<form action="/action_page.php" method="get" id="form1">
First name: <input type="text" name="fname"><br>
Last name: <input type="text" name="lname"><br>
</form>
<button type="submit" form="form1" value="Submit">Submit</button>

在没有使用任何脚本的情况下,我使用<button> form="bla"属性定义了每个按钮所属的表单。我将Delete按钮设置为一个不存在的表单,并将我想在Enter键上触发的Update按钮设置为用户在输入文本时将处于的表单。

这是迄今为止唯一对我有效的方法。

Dom示例

  <button onclick="anotherFoo()"> Add new row</button>
<input type="text" name="xxx" onclick="foo(event)">

javascript

function foo(event){
if(event.which == 13 || event.keyCode == 13) // for crossbrowser
{
event.preventDefault(); // this code prevents other buttons triggers use this
// do stuff
}
}


function anotherFoo(){
// stuffs.
}

如果你不使用preventDefault(),其他按钮将被触发。

无论你在哪里使用<button>元素,默认情况下,它都认为按钮type="submit",所以如果你定义按钮type="button",那么它不会认为<button>是提交按钮。

你可以这样做。

将您的事件绑定到一个公共函数中,并通过按键或按钮单击调用该事件。

为例。

function callME(event){
alert('Hi');
}






$('button').on("click",callME);
$('input ').keypress(function(event){
if (event.which == 13) {
callME(event);
}
});