JQuery: клонировать элементы и события - PullRequest
16 голосов
/ 03 ноября 2011

Всякий раз, когда я использую ajax для динамического создания нового контента, .clone (), append () и т. Д., Новый элемент теряет все триггеры и события, которые я запрограммировал = (

После копирования, простые вещи, которые РАБОТАЮТ надругие элементы, такие как добавление класса в, на скопированных элементах больше не работают. Любое новое содержимое ajax не работает. Командные кнопки больше не работают. Что я могу сделать?

Я клонирую этот HTML и командукнопки больше не работают. Стилизация элементов span больше не работает с элементами CLONED:

<div name="shows" id="x"><br/> <!-- The ID depends on the database-->
    <div name="shows" id="x">
        ID: <input disabled="disabled" size="7" value="x" name="id" />
        Status: 
        <select name="status" >
          <option selected="selected" >Display</option>
          <option >Hide</option>
        </select>
        <br/><br/>
        <span class="required" id="date_txt">*Date: </span><input type="text" value="" name="date" />
        &nbsp;&nbsp;
        <span class="required" id="title_txt">*Title: </span><input type="text" size="65" value="" name="title" />
        <br/>
        <span class="required" id="venue_txt">*Venue: </span><input type="text" size="45" value="" name="venue" />
        Telephone: <input type="text" value="" name="tel" />
        <br/>
        URL: <input type="text" size="100" value="" name="url" />
        <br/><br/>
        Address: <input type="text" size="45" value="" name="address" />
        &nbsp;&nbsp;
        <span class="required" id="city_txt">*City: </span><input type="text" value="" name="city" />
        <br/>
        State: <input type="text" value="" name="state" />
        ZIP: <input type="text" value="" name="zip" />
        <span id="country_txt">*Country: </span><input type="text" value="United States" name="country" />
        <br/>
        <br/>Comments: <br/>
        <textarea cols="80" rows="8" name="comments" ></textarea>
    </div>
    <!-- START OF:commands  -->
    <div id="commands" >
        <button name="edit" id="edit" >Edit</button> 
        <button name="delete" id="delete" >Delete</button>
    <br />
    <hr />
    <br />
    </div>
    <!-- END OF:commands  -->
</div>
<!-- END OF:new -->

Добавлены новые комментарии, 03.03.2011:

ОК, я разобрался с проблемой, и у меня возникла ошибка на моем jQuery.Теперь, когда я добавляю .clone (true) ПОЧТИ все работает.

Моя новая проблема - пользовательский интерфейс выбора даты.После клонирования HTML, когда я щелкаю по недавно клонированному полю даты, фокус переходит к (старому) полю даты, из которого были клонированы данные.Более того, если я выберу дату, значение переходит к старому полю даты. -Не клонированное поле даты.

Вот мой код ajax (после успешной отправки):

Код пользовательского интерфейса DatePicker:

$("input[name='date']").datepicker({ dateFormat: 'yy-mm-dd', changeMonth: true, changeYear: true, numberOfMonths: 3, showButtonPanel: true});

Ajax:

    ...ajax code...
function(data)
{
var $msg = eval(data);
if( $msg[0] == 1 )
    {
    //#var.new
        $id = '#'+$msg[1];
        $data = $("#new");
    $new = $data.clone(true);
    $new.find('input.datefield').datepicker();


        $new.attr("id", $id);
        $new.children('[name="id"]').val($id);
        $new.children('[name="id"]').attr("value", $id);
        $new.children(":input").each(function() { var $value = $(this).val(); $(this).attr("value", $value); });
        $new.prepend( "<br/>" );

        $commands = $("#blank").children("#commands").clone(true);
        $commands.children("#add").text("Update");
        $commands.children("#add").attr("pk", $id);
        $commands.children("#add").attr("name", "update");
        $commands.children("#add").attr("id", "update");

        $commands.children("#reset").text("Delete");
        $commands.children("#reset").attr("pk", $id);
        $commands.children("#reset").attr("name", "delete");
        $commands.children("#reset").attr("id", "delete");

        $new.append( $commands );

        //#animation
        //blank.slideUp
        $("#blank").slideUp(2500, function(){
        $("#ADDNEW").html("&#9658; New:");
        //$("#blank").clone().prependTo( $("#active") );
        //$("#blank").prependTo( "#active" );

        //active.slideUp
        $("#active").slideUp("slow", function(){
        $("#ON").html("&#9658; Active:");
        $("#active").prepend( $new );
        $('#reset').trigger('click');

        //active.slideDown
        $("#active").slideDown(8500, function(){
        $("#ON").html("&#9660; Active:");

        //blank.slideDown
        $("#blank").slideDown(3500, function(){
        $("#ADDNEW").html("&#9660; New:");
        load_bar(0);

        }); //end: anumation.#blank.slideDown
        }); //end: anumation.#active.slideDown
        }); //end: anumation.#blank.slideUp
        }); //end: anumation.#active.slideUp

        //$("#new").fadeOut(2000, function(){
        //START: blank
        //alert( $("#blank").html() );
        //$dad = $("#new");
        //$dad.children('input[name!="id"][name!="country"], textarea').val('');
        //$dad.children('[name="country"]').val("United States");
        //$dad.children('[name="date"]').focus();
        //END: blank
        //$("#new").fadeIn(2000, function(){
        //alert( $msg );
        //}); //end: anumation.fadeIn
        //}); //end: anumation.fadeOut
        } //end: if
    else
        {
        //var varMSG = data;
        //alert( "Hello" );
        alert( $msg );

        //$("#add").attr("disabled", false);
        //$("#reset").attr("disabled", false);
        load_bar(0);
        } //end: if.else
    }//end: $.post.function
); //END:$.post
}); 
//END:ajax

Ответы [ 4 ]

38 голосов
/ 03 ноября 2011

.clone( true ) делает свое дело.

Документация: http://api.jquery.com/clone/

1 голос
/ 13 ноября 2014

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

$('.someclass').on('click', function() {

но я решил мою проблему, заменив on live следующим образом:

$('.someclass').live('click', function() {
0 голосов
/ 04 ноября 2011

Я наконец-то заставил работать с датчиком интерфейса. Мне пришлось полностью удалить DatePicker ДО клонирования и добавить его ПОСЛЕ клонирования элементов. Ребята из UI должны облегчить нам задачу. Иди разберись!

Непосредственно перед клонированием:

//#datepicker
$("input[name='date']").datepicker( "destroy" );
$("input[name='date']").removeClass("hasDatepicker").removeAttr('id');

После клонирования:

$("input[name='date']").datepicker({ dateFormat: 'yy-mm-dd', changeMonth: true, changeYear: true, numberOfMonths: 3, showButtonPanel: true});
0 голосов
/ 04 ноября 2011

Если ваши обработчики настроены с использованием чего-то вроде $ ('. class'). click (...)

Попробуйте что-то вроде этого: $ ('. class'). live ('click', ...)

Live применяется к элементам с классом, которые могут еще не существовать.

...