1

我构建了这个非常令人兴奋的 jQuery 插件,它可以将元素变为蓝色。 http://jsfiddle.net/LpCav/

我希望将其应用于当前不在页面上的元素。

我知道一种选择是在我将新元素添加到页面后立即应用它。另一种选择是克隆一个现有元素并将其添加到页面而不是创建新元素。我不想做这些选择中的任何一个。

相反,我可以使用 on() 将其应用于<li>内部的任何当前或未来元素<ul id="myNewList">吗?

如果没有,我可以修改插件以使其执行此行为吗?

谢谢

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> 
<html xmlns="http://www.w3.org/1999/xhtml"> 
    <head> 
        <meta http-equiv="content-type" content="text/html; charset=ISO-8859-1" /> 
        <title>Future</title>  
        <script src="http://code.jquery.com/jquery-latest.js" type="text/javascript"></script> 
        <script type="text/javascript">
            (function( $ ){
                $.fn.makeBlue = function() {  
                    return this.each(function() {
                        $(this).css('color','blue');
                    });
                };
            })( jQuery );

            $(function(){
                $('.myElement').makeBlue();
                $('#add').click(function(){
                    $('#myNewList').html('<li class="myElement">hello</li>')
                });
            });
        </script>
    </head>

    <body>
        <button id="add">Add</button>
        <ul id="myList">
            <li class="myElement">hello</li>
            <li class="myElement">hello</li>
        </ul>
        <ul id="myNewList">
        </ul>
    </body> 
</html> 
4

3 回答 3

1

由于您放弃了最简单(可能也是最常见的解决方案),因此您只能捕获一些“DOM 已更改”事件并绑定到该事件。根据我的发现,有一些事件,但支持很差。长话短说:这是一个库,可以为您提供所需的内容:

https://github.com/joelpurra/jquery-mutation-summary

于 2013-03-20T13:22:17.853 回答
0

我通常使用$(document).ready(...)块来确保在每个页面加载时调用代码(甚至是 ajax 回调)。但是,您应该将您的插件实现为一个幂等的插件 - 对同一元素的多次调用应该产生相同的结果。

根据我对现有 jquery 插件和内置插件的经验,我观察到以下内容:

  • 如果多次使用相同的配置对相同的元素调用相同的插件,则后续调用不会产生任何可见的差异

  • 如果在同一元素上使用不同的配置调用相同的插件,则效果是将配置与先前的调用之一合并。

也许如果你在你的插件中坚持这种行为,你俩都会与现有插件的行为保持一致,并让它们在场景中工作$(document).ready

使用.on(...)可能会更好,因为它会<ul>在需要时更新相应的元素。尽管如此,如果已经有列表项,插件应该以幂等方式处理它们。


编辑:

关于代码中的幂等性问题,它看起来像这样:

$.fn.makeBlue = function() {  
    return this.each(function() {
        var elem = $(this);
        if (elem.css('color') != 'blue') {
            // it is likely for the element not to have been processed yet.
            elem.css('color','blue');
        }
    });
};

更好的解决方案是将自定义 css 类添加到已处理的元素中 - 只是将它们标记为您的插件已访问。然后你可以$(this).hasClass('?')改为检查。这看起来像:

$.fn.makeBlue = function() {  
    return this.each(function() {
        var elem = $(this);
        if (!elem.hasClass('makeBlueCalled')) {
            elem.css('color','blue');
            elem.addClass('makeBlueCalled');
        }
    });
};

在您的插件中,如果唯一的目的是为文本着色,我最好使用 css 定义

ul.myList > li.myElement.makeBlueCalled { color: blue !important; }

并完全删除该elem.css('color','blue');行。

于 2013-03-20T13:15:40.307 回答
0

有 DOM2 “突变事件”来捕捉对 DOM 树的更改,但它们没有得到很好的支持,实际上已被 W3C 弃用。有新的“突变观察者”事件,但它们在 DOM4 中,也没有完全支持。有关这些的更多详细信息,请参阅此问题

无论如何(没有双关语),事实是 JS 是一种单线程语言,除非把它放在那里,否则页面上不会出现任何元素,因此在插入时进行所需的更改通常是微不足道的。

否则,此特定示例的正确答案是将其放入您的 CSS 样式表中:

.myElement {
    color: blue;
}

如果您真的在做比应用样式更复杂的事情,唯一可移植的选择是在知道元素存在后调用插件。

于 2013-03-20T13:16:31.810 回答