【问题标题】:jQuery clone chained selectsjQuery 克隆链式选择
【发布时间】:2026-01-07 21:10:01
【问题描述】:

我刚从:http://jsfiddle.net/FJFFJ/1/Chain dynamically created dropdowns with JQuery)开始

真的很好,但现在我需要做一点改变:克隆最后一组选择。

即:

+-
Argentina | San Juan | Rawson
Chile     | Santiago | Chiñihue

然后,如果我点击“+”,它将克隆

Chile | Santiago | Chiñihue

而不是第一个。

【问题讨论】:

    标签: jquery select clone chained


    【解决方案1】:

    这实际上是一个比我想象的更难的问题。显然,当您克隆 SELECT 元素集时,它无法更改为未显示的内容。我花了大约一个小时左右才弄清楚到底发生了什么,很好的挑战,谢谢!

    我最终做的是克隆您的模板并手动更改值并手动调用“更改”事件,以便在二级和三元 SELECT 元素中可以使用正确的选项。

    版本 1:http://jsfiddle.net/m4JTQ/2/

    版本 2(这是一个去掉 i 迭代器的修改版本:http://jsfiddle.net/Zf7xb/1/

    这是 jsfiddle 最终消失的代码。

    // Version 1
    $(function() {
    
        // Iterator for the dupe ids
        var i = 0;
    
        $('#clone').click(function() {
            // put the clone() into cloned
            var cloned = $('#template').clone();
    
            // Add .dupe class to cloned
            $(cloned).addClass('dupe');
    
            // Set the id of cloned, use i++ instead of incrementing it elsewhere.
            $(cloned).attr('id', 'duplicate'+ i++);
    
            // Append cloned to #filter
            $(cloned).appendTo('#filter');
    
            // Passing selector rather than iteration                   
            chainItWithId($(cloned));
    
            // If this is NOT the first addition, do some kludge
            if ($('#filter div.dupe').length!==1) {
                // Set the previous clone to lastClone
                var lastClone = $(cloned).siblings('div.dupe:last');
    
                // Set the value of .pais to the value of the previous .pais
                $(cloned).find('.pais').val($(lastClone).find('.pais').val());
                // Do the "change" event manually.
                $(cloned).find('.pais').change();
    
                // Set the value of .provincia to the value of the previous .provincia
                $(cloned).find('.provincia').val($(lastClone).find('.provincia').val());
                // Do the "change" event manually
                $(cloned).find('.provincia').change();
    
                // Set the value of .ciudad to the value of the previous .cudad
                $(cloned).find('.ciudad').val($(lastClone).find('.ciudad').val());
    
            }
    
            // Show the hidden div
            $('#filter div:hidden').show();
    
        });
        $('#remove').click(function() {
            // Remove all but the very last set of options
            if ($('#filter > div').length > 1) {
                $('#filter > div').last().remove();
            }
        });
    
        // Manually do the "click" event
        $('#clone').click();
    });
    
    // Here I'm getting the cloned full selector
    function chainItWithId(cloned) {
        // Chain .provincia to .pais in the current clone
        $(cloned).find('.provincia').chained($(cloned).find('.pais'));
        // Chain .ciudad to .provincia in the current clone
        $(cloned).find('.ciudad').chained($(cloned).find('.provincia'));
    }
    

    这个版本没有i迭代器,它更干净一些。

    // Version 2
    $(function() {
    
        $('#clone').click(function() {
            // put the clone() into cloned
            var cloned = $('#template').clone();
    
            // Add .dupe class to cloned
            $(cloned).addClass('dupe');
    
            // Set the id to the count of div.dupe elements in #filter
            // This will increment 0,1,2,3 as you add elements.
            $(cloned).attr('id', 'duplicate'+ $('#filter div.dupe').length);
    
            // Append cloned to #filter
            $(cloned).appendTo('#filter');
    
            // Passing selector rather than iteration                    
            chainItWithId($(cloned));
    
            // If this is NOT the first addition, do some kludge
            if ($('#filter div.dupe').length!==1) {
                // Set the previous clone to lastClone
                var lastClone = $(cloned).siblings('div.dupe:last');
    
                // Set the value of .pais to the value of the previous .pais
                $(cloned).find('.pais').val($(lastClone).find('.pais').val());
                // Do the "change" event manually.
                $(cloned).find('.pais').change();
    
                // Set the value of .provincia to the value of the previous .provincia
                $(cloned).find('.provincia').val($(lastClone).find('.provincia').val());
                // Do the "change" event manually
                $(cloned).find('.provincia').change();
    
                // Set the value of .ciudad to the value of the previous .cudad
                $(cloned).find('.ciudad').val($(lastClone).find('.ciudad').val());
    
            }
    
            // Show the hidden div
            $('#filter div:hidden').show();
    
        });
        $('#remove').click(function() {
            // Remove all but the very last set of options
            if ($('#filter > div').length > 1) {
                $('#filter > div').last().remove();
            }
        });
    
        // Manually do the "click" event
        $('#clone').click();
    });
    
    // Here I'm getting the cloned full selector
    function chainItWithId(cloned) {
        // Chain .provincia to .pais in the current clone
        $(cloned).find('.provincia').chained($(cloned).find('.pais'));
        // Chain .ciudad to .provincia in the current clone
        $(cloned).find('.ciudad').chained($(cloned).find('.provincia'));
    }
    

    【讨论】: