使用JQuery在Div中包含多组元素

时间:2009-12-07 18:55:43

标签: jquery css-selectors wrapall

我正在开发一个下拉菜单,需要使用JQuery改变现有的html标记,使其适合设计。

这是一个简化的例子: 在div中包含所有包含多个“li”的“ul”(在同一个div中,每个UL不包含一个div)。

<ul>
    <li>foo</li>
</ul>
<ul>
    <li>foo</li>
    <li>foo</li>
</ul>
<ul>
    <li>foo</li>
    <li>foo</li>
</ul>

<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.3.2/jquery.min.js"></script>

<script>
my_selection = [];
i = 0;
// find all ul's that have more than one li
$("ul").each(function(){
    if($(this).find("li").length > 1){
        // add this to my_selection
        my_selection[i] = $(this);
        i++;
    } // if
}); // each

// wrap my_selection in div tags
$(my_selection).wrapAll(document.createElement("div"));
</script>

上面的代码给出了这个firebug错误:

“无法在层次结构中的指定点插入节点”代码:“3”

我怎样才能让它发挥作用?

6 个答案:

答案 0 :(得分:5)

这将是一个更清洁的方法:

$('ul:has(li)').wrap('<div></div>');

首先,您不需要创建节点,只需向jQuery提供包装字符串。 其次,在此实例中使用:has选择器来减少示例中的each功能。 最后,(这取决于您的预期功能)您可能希望使用wrap而不是wrapAll

编辑: 另一种选择是从相反的方向接近它。获取<li>代码,然后抓住<ul>父代:

$('li:not(:only-child)').parent().filter('ul').wrap('<div></div>');

答案 1 :(得分:1)

这有点像黑客。

<script>
jQuery( function() {
    my_selection = [];

    i = 0;
    n = 0;
    jQuery( 'ul' ).each( function() {
        var ul = jQuery( this );
        if ( ul.children().length > 1 ) {
            my_selection[n++] = 'ul:eq(' + i + ')';
        }
        ++i;
    } );

    jQuery( my_selection.join( ',' ) ).wrapAll( document.createElement( 'div' ) );
} );
</script>

答案 2 :(得分:0)

你的代码中有一个错误,试图通过DIV包装你的LI。

<script>
my_selection = [];
i = 0;
// find all ul's that have more than one li
$("ul").each(function() {
    var $ul = $(this);
    if ($ul.find("li").length > 1){
        // add this to my_selection
        my_selection[i] = $ul;
        i++;
    } // if
});

// wrap my_selection in div tags
$(my_selection).wrap(document.createElement("div"));
</script>

答案 3 :(得分:0)

我不确定jQuery是否可以将数组作为选择器。在$(my_selection)中,my_selection不是jQuery对象,而是对象数组。您可以尝试使用var my_selection = $(''); ... my_selection.add($(this));生成jQuery对象。

此外,使用.wrapAll()方法,您只需使用:.wrapAll('<div></div>');

答案 4 :(得分:0)

当我回答这个问题时,我有点忙,抱歉所有的问题。以下是正确解决问题的方法。

<script type="text/javascript">
jQuery( function() {
    jQuery( 'ul' ).find( 'li:eq(1)' ).parent().wrapAll( '<div></div>' );
} );
</script>

修改:我将 li:gt(0)更改为 li:eq(1),它们都有效,但有一个更多感。

这很简单,它经历了所有的ul和他们的孩子,它试图抓住第二个孩子。如果找到第二个子节点,则返回到它的父节点,将其添加到wrapAll方法。

编辑:如果您将帖子编辑的次数超过8次,就会变成社区Wiki,这很有趣。

答案 5 :(得分:0)

这些都是很好的答案。但我注意到你的脚本不在$(document).ready(function(){...})内,你似乎验证了这个错误仍然存​​在于未包含在就绪函数中的其他代码中。

我试过并发现威廉的代码有效(给他+1),但由于我的强迫症我把它清理了一下

$(document).ready(function(){
 my_selection = [];
 $('ul').each(function(i){
  if ($(this).find('li').length > 1 ){
   my_selection.push(['ul:eq(' + i + ')']);
  }
 });
 $( my_selection.join(',')).wrapAll('<div class="wrapper"></div>');
})