繁体   English   中英

如何正确捕获动态插入的“输入”文本元素的onchange或onkeyup事件?

[英]How do I properly capture an onchange or onkeyup event for a dynamically inserted 'input' text element?

我有一些JavaScript可以为我构建一些HTML并将其插入div 我正在为此测试使用jQuery 1.7.2

我对将自定义更改或input事件处理程序附加到名为gene_autocomplete_fieldinput文本字段gene_autocomplete_field

到目前为止,这是我尝试过的。

以下函数构建HTML,并将其插入到名为gene_containerdiv

function buildGeneContainerHTML(count, arr) {
    var html = "";
    // ...
    html += "<input type='text' size='20' value='' id='gene_autocomplete_field' name='gene_autocomplete_field' placeholder='Enter gene name...' /><br/>";
    // ...
    return html;
}

// ...
$('#gene_container').html( buildGeneContainerHTML(count, geneNameArr) );

在我的呼唤HTML,我抢gene_autocomplete_fieldgene_container元素,然后我重写keyup的事件处理程序gene_autocomplete_field

<script>
    $(document).ready(function() {
        $("#gene_container input:[name=gene_autocomplete_field]").live('keyup', function(event) {
            refreshGenePicker($("#gene_container input:[name=gene_autocomplete_field]").val());
        });
    });
</script>

当我更改gene_autocomplete_field的文本时, refreshGenePicker()函数只会发送警报:

function refreshGenePicker(val) {
    alert(val);
}

结果

如果我在gene_autocomplete_field元素中键入任何字母,事件处理程序似乎会无限次调用alert(val) 我收到一个又一个警报,浏览器被对话框接管。 返回的值是正确的,但是我担心一次又一次调用refreshGenePicker() 我不认为这是不正确的行为。

问题

  • 如何一次正确捕获keyup事件,以便一次只处理一次对自动完成字段的内容更改?
  • 为此,我应该使用其他事件吗?

更新

事实证明,不仅仅是13(返回/回车)的keyCode可能是一个问题-按Control,Alt,Esc或其他特殊字符将触发一个事件(但就无限循环问题而言,这是无症状的) 。 我正在筛选的基因名称中没有元字符。 因此,我使用了字母数字检测测试来从进一步的事件处理中过滤掉非字母数字字符,其中包括Return键:

if (!alphaNumericCheck(event.keyCode)) return;

alert被称为无限次,因为您使用“ Enter”键确认/关闭警报。 使用.on('change')代替。 当您在alert使用enter时,这将防止refreshGenePicker

但是,仅当输入元素失去焦点时才会触发'change'事件。 如果要在每个键上使用refreshGenePicker ,请改用以下方法:

$("#gene_container input:[name=gene_autocomplete_field]").live('keyup', function(event) {
    if(event.keyCode === 13) // filter ENTER
        return;
    refreshGenePicker($("#gene_container input:[name=gene_autocomplete_field]").val());
});

这将过滤所有传入的enter keyup事件( jsFiddle demo )。 同时切换到.on并放下.live

编辑 :请注意,还有更多可能性可以消除alert模式,例如escape键或space键。 您应该在refreshGenePicker内部添加一个检查,检查该值是否实际上已更改

如果您使用的是jQuery> 1.7,则应该真正使用.on()

检查出的perftest

还要检查我一些相关的问题

同样,当测试相等时,您应该在其周围添加引号

input:[name='gene_autocomplete_field']

要回答你真正的问题:)。 它不应像您提供的代码那样工作。 也许其他地方有问题。 您可以为此问题设置jsfiddle吗?

查看我的演示 ,也许您看到代码出什么问题:

function refreshGenePicker(value) {
    console.log('keyup! Value is now: ' + value);
}

(function($) {
    var someHtml = '<input type="text" name="gene_autocomplete_field">';
    $('body').append(someHtml);

    $('body').on('keyup', 'input[name="gene_autocomplete_field"]', function(e) {
        refreshGenePicker($(this).val());
    });
})(jQuery);​
$(document).ready(function() {
    $('#test').html('<input id="text" />');
    $('#text').keyup(function() {
        console.log($(this).val());
    });
});​

这样很好。 由于您的第二个代码块位于<script>标记中,因此您可能会多次运行它-这将导致它绑定多次,并在每次绑定时产生多个警报。 您当然可以在添加键之前在该输入上使用.unbind() ,但我认为更好的解决方案是将所有代码分组在一个$(document).ready(); 以确保您只绑定一次对象。

http://jsfiddle.net/Ka7Ty/2/

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM