Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/batch-file/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何将javascript事件处理程序附加到在javascript中创建的这些元素 背景_Javascript_Jquery - Fatal编程技术网

如何将javascript事件处理程序附加到在javascript中创建的这些元素 背景

如何将javascript事件处理程序附加到在javascript中创建的这些元素 背景,javascript,jquery,Javascript,Jquery,从长远来看,我并不是最炙手可热的jQuery家伙,我正试图去掉下面代码中重复的工作。虽然性能开销可能很小,而且可以忽略不计,但这更像是不想编写多次执行相同操作的蹩脚代码 基本上我有一个简单的发票表单,用户也可以添加多个项目 表单最初有4个输入:项目名称、项目价格、项目数量和总额 每当“价格”或“数量”字段触发更改事件时,都会计算总数 问题-部分解决(请参阅更新) 用户可以为第二项(或第三项、第四项、第五项等)添加额外的输入行 将事件处理程序附加到price和quantity字段的现有jav

从长远来看,我并不是最炙手可热的jQuery家伙,我正试图去掉下面代码中重复的工作。虽然性能开销可能很小,而且可以忽略不计,但这更像是不想编写多次执行相同操作的蹩脚代码

基本上我有一个简单的发票表单,用户也可以添加多个项目

表单最初有4个输入:项目名称、项目价格、项目数量和总额

  • 每当“价格”或“数量”字段触发更改事件时,都会计算总数
问题-部分解决(请参阅更新) 用户可以为第二项(或第三项、第四项、第五项等)添加额外的输入行

  • 将事件处理程序附加到
    price
    quantity
    字段的现有javascript已经运行,因此不会将侦听器附加到新添加的输入行
解决方案 目前,我已经解决了一些可怕的问题,即在添加新行输入后,我将事件侦听器重新附加到所有输入字段

我想这很酷,如果你对你的工作质量不感到自豪,但是如果发票是20个项目,我真的需要在已经附加了侦听器的19行上添加第20个项目行循环,再次附加它们,然后将侦听器附加到新行。我希望不会

我已经设法将新添加的输入行作为目标,以擦除克隆输入中的值——因此我认为只需将新输入字段作为目标并附加侦听器——但我得到了正确的2和8,因为理想情况下我希望这样做

  • 克隆输入行
  • 清除值
  • 附加侦听器
  • 添加到DOM
  • 我现在所做的让人觉得奇怪的事情是

  • 克隆行
  • 将该行添加到DOM中
  • 选择新添加的行并擦除值
  • 选择新添加的数量字段并附加侦听器
  • 选择新添加的价格字段并附加侦听器
  • 选择新添加的合计字段并附加侦听器(以更新发票合计)
  • 下面的代码,供你嘲笑,然后希望同情我,并提供一个更简洁的解决方案,或者至少是一个关于如何着手编写我自己的更好版本的建议

    /** Add additional item lines */
    $('#add-item').click(function(e){
        e.preventDefault();
        /** clone first line and insert it */
        $('.input-row:first').clone().insertAfter('.input-row:last');
        /** clear the newly inserted inputs of values */
        $(':input', '.input-row:last').val("");
        /** ensure all item price and qty inputs have events attached to their change value */
        $('input[name="item_qty[]"],input[name="item_price[]"]').on("change",function () {
            var $container = $(this).closest('.form-group');
            qty = Number($('input[name="item_qty[]"]',$container).val())||0,
            price = Number($('input[name="item_price[]"]',$container).val())||0;
            $('input[name="item_total[]"]',$container).val(qty * price);
            $('input[name="item_total[]"]',$container).change();
        });
        /** Sum inputs for invoice total */
        $('input[name="item_total[]"').change(function() {
            var total = 0;
            $.each($("[name='item_total[]']"), function(index, value) {
                total += parseFloat($(this).val());
            });
            $("#total").val(total);
        });
    });
    
    更新 因此,通过利用事件委托,事件可以传播(或冒泡)dom-谢谢大家!每当新父div中的一个输入发生变化时,我都会重新计算发票总额

    <div id="invoice-items">
        <input name /> <input quantity /> <input price /> <input total />
        <input name /> <input quantity /> <input price /> <input total />
        <input name /> <input quantity /> <input price /> <input total />
        ...
    </div>
    
    /** if any input rows change update the invoice total */
    $('#invoice-items').on('change', 'input', function(event){
        var total = 0;
        $.each($("[name='item_total[]']"), function(index, value) {
            total += parseFloat($(this).val());
        });
        $("#total").val(total);
    });
    
    我想我仍然需要的是在添加一行之后运行此代码的一些方法,或者遵循更干净的事件委派路线-某种方式只针对发生更改事件的行的
    item_total[]
    ?也许我可以捕获触发更改事件的元素的特定索引,并仅更新该索引处的
    项\u total[]

    在这里大声想一想,我想如果我捕获事件并循环所有输入,直到找到与触发事件的元素匹配的元素,我就可以抓取下一个表单输入,名称为
    invoice\u total[]
    ,并对其进行更新我们去看看

    更新 因此,我可以捕捉事件-快乐的日子:)

    因此,我仍然不知道我更新了哪些
    item\u qty[]
    元素,因此我不知道要更新哪些
    item\u total[]
    元素


    有什么建议吗 您要获取包装元素吗

    <div>
        <input />
        <input />
    </div>
    
    $('div').on('change', 'input', function(){
        // your magic here
    });
    
    
    $('div')。在('change','input',function()上{
    //你的魔法在这里
    });
    
    这将对现在在场的两个人以及新元素起作用。为什么?简而言之:
    将事件绑定到存在的元素。您创建了一个新的事件,并对其进行了更改,但从未将事件绑定到新元素。这件事在树上冒着气泡,没有什么能抓住它

    我的代码没有绑定到元素本身,您告诉它在
    input
    上监听其中的更改。新的元素进来了,你改变了它们,什么都没有发生,所以它会在树上冒泡。

    这就是最大的区别:这次我们告诉现有元素现在就做些什么。

    您希望将事件处理程序附加到克隆行。重点是什么?你在寻找更好的方式是对的,它是以活动授权的形式出现的。在它上面–它允许您将事件处理程序仅附加到一个父元素,该父元素将处理每个子
    input
    元素的
    change
    事件(无论它们始终存在还是新添加).我刚刚对
    事件委派回答发表了评论-如果我可以将侦听器附加到div中的所有输入-很好,但是我如何针对特定输入来填充值。这种方式对我的发票总额非常有效,因为如果有任何需要更新的更改,那么单个行项目又如何呢?我是否将每一行包装在一个div中,并针对该div进行更改?好的,因此每一行输入现在都包含在一个父div中,我已将侦听器附加到该父div。好极了!我将首先尝试一下,只是为了确定-但我怀疑我会遇到问题-例如,
    当数量[0]发生变化时,如何使总数[0]==数量[0]*价格[0]
    Ok,所以当任何一行发生变化时,观察所有输入并更新发票总额非常有效-我更新了我的问题,希望有人能提出一种方法,在该行发生变化时更新每一行。
    event.currentTarget.attributes.name.nodeValue == 'item_qty[]'
    
    <div>
        <input />
        <input />
    </div>
    
    $('div').on('change', 'input', function(){
        // your magic here
    });