开发者

jQuery clone : should it clone DOM Level 0 Events?

开发者 https://www.devze.com 2022-12-16 07:08 出处:网络
While reading the book jQuery in Action and playing with the first events handling example, I discovered that jQuery doesn\'t consistently clone DOM Level 0 events. It clones the inline events, but no

While reading the book jQuery in Action and playing with the first events handling example, I discovered that jQuery doesn't consistently clone DOM Level 0 events. It clones the inline events, but not those defined as a property. It could be a good thing to discourage the use of inline event handlers, but is is by design? What is one wants to clone something from a legacy page ?

Here is an alteration of the example given in the book, to demonstrate the behavior.

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">
<html>
  <head>
    <title>DOM Level 0 Events Example</title>
    <script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.3/jquery.min.js">
    </script>
<script type="text/javascript">
  $(function(){
    $('#testElement')[0].onclick = function(event) {
      say(this.id + ' Click ASSIGN [DOM 0]');
    }
            $('#testElement').click(function() { say(this.id + ' Click JQUERY [DOM 2]');});
            $('#testElement').clone(true).attr('id',"clonedElement").insertAfter($('#testElement'));
  });

  function say(text) {
    $('#console').append('&l开发者_运维技巧t;div>'+text+'</div>');
  }
  </script>
  </head>

  <body>
    <div id="testElement" style="border: solid brown 1px; margin: 10px; width : 100px; height: 100px;" onclick="say(this.id + ' Click INLINE [DOM 0]')">&nbsp;</div>
<div id="console"></div>
 </body>
</html>


Line 305 to 312 in "jQuery-1.3.2.js

"IE" copies events bound via "attachEvent" when using "cloneNode". Calling "detachEvent" on the clone will also remove the events from the orignal. In order to get around this, we use "innerHTML". Unfortunately, this means some modifications to attributes in "IE" that are actually only stored as properties will not be copied (such as the the name attribute on an input).

The example to pasate not work in IE for the reason explained. We should make a modification to the method "clone" of jQuery to have this functionality in IE

EDIT:

ok, I'm sorry, now I understand the problem, but from what I see and what you can view in "clonedElement_2" is a limitation of "cloneNode". The only thing I can think of is to change the method "clone" of "jQuery"

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">
<html>
<head>
    <script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.3/jquery.min.js"></script>
    <script language="JavaScript">

        (function($){

            $.fn.__extendClone = $.fn.clone;
            $.fn.clone = function(events){

                var ret = $(this).__extendClone(events);

                if (events){

                    var listEvents = ["onabort", "onblur", "onchange", "onclick", "ondblclick", "onerror", "onfocus", 
                        "onkeydown", "onkeypress", "onkeyup", "onload",  "onmousedown", "onmousemove", "onmouseout", 
                        "onmouseover", "onmouseup", "onreset", "onresize", "onselect", "onsubmit", "onunload"];

                    for (var inde in listEvents){
                        if ($.isFunction($(this)[0][listEvents[inde]])){
                            $(ret)[0][listEvents[inde]] = $(this)[0][listEvents[inde]];
                        }
                    }
                }

                return ret;

            };

        })(jQuery);     

        $(function()
        {
            //work
            var mytestElement = document.getElementById("testElement")
            mytestElement.setAttribute("style", "border: solid green 2px; margin: 10px; width : 100px; height: 100px;");

            //don't twork
            $('#testElement')[0].onclick = function(event) {
                say(this.id + ' Click ASSIGN [DOM 0]');
            }

            $('#testElement').click(function() { say(this.id + ' Click JQUERY [DOM 2]');});

            //clone jquery
            $('#testElement').clone(true).attr('id',"clonedElement").insertAfter($('#testElement'));

            //clone js
            var myNode = document.getElementById("testElement").cloneNode(true);
            myNode.setAttribute("id", "clonedElement_2");
            myNode.setAttribute("style", "border: solid blue 2px; margin: 10px; width : 100px; height: 100px;");
            document.getElementById("container").appendChild(myNode);

        });

        function say(text) {
            $('#console').append('<div>'+text+'</div>');
        }

    </script>
</head>
<body>
    <div id="testElement" style="border: solid brown 2px; margin: 10px; width : 100px; height: 100px;" onclick="say(this.id + ' Click INLINE [DOM 0]')">&nbsp;</div>
    <div id="container"></div>
    <div id="console"></div>
</body>
</html>
0

精彩评论

暂无评论...
验证码 换一张
取 消