【问题标题】:jquery tree traversaljquery树遍历
【发布时间】:2011-05-06 05:28:59
【问题描述】:

我有一个任务需要遍历一棵树(检查/取消检查单个项目)。我已经编写了代码,它可以正常工作,但有时速度很慢。请帮我改进它。

这是它的工作原理:

  1. 取消选中父级取消选中 该父母的所有孩子
  2. 取消选中(一个或多个) 子节点取消选中父节点
  3. 自动检查父级 检查所有的孩子
  4. 检查所有子项时 父母也被检查 自动地
    • 这也适用于任何深度树。所以如果有 3 级深度节点,取消选中最内层的子节点将取消选中每个节点的第一个父节点。

其他一些注意事项: CSS类:

  • "checked" - 黑色字体,删除后字体为灰色
  • “标记” - 灰色背景

所以:

  • 当父级没有选择子级时,它的 css 类“已选中”被删除(变为灰色)
  • 当一个项目未选中时,它的 css 类“选中”和“标记”被删除(黑色字体变为灰色且没有灰色背景)
  • 当所有子级都未选中时,父级的“标记”类被删除(灰色背景被删除)。

我希望这个插图会有所帮助:

以及部分HTML源代码:

<ul class='treeList2b'><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:30px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Aparatura elektryczna, elektroenergetyka   </span></div>

<ul class='treeList2b'><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:60px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Silniki, napędy, automatyka napęd&#243;w </span></div>
<ul class='treeList2b'><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:90px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Silniki i napędy przemysłowe </span></div>
<ul class='treeList2b'><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:120px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Prądu stałego   </span></div>
</li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:120px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Prądu przemiennego </span></div>
<ul class='treeList2b'><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:150px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>synchroniczne   </span></div>
</li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:150px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>asynchroniczne </span></div>

</li></ul></li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:120px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Silniki krokowe   </span></div>
</li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:120px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Siłowniki elektryczne   </span></div>
<ul class='treeList2b'><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:150px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Liniowe </span></div>
</li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:150px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Obrotowe </span></div>
</li></ul></li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:120px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Serwosilniki, serwonapędy </span></div>
</li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:120px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Inne </span></div>

</li></ul></li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:90px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Układy zabezpieczeń silnik&#243;w   </span></div>
</li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:90px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Elektroniczne układy sterowania napęd&#243;w   </span></div>
<ul class='treeList2b'><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:120px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Przemienniki prądu stałego   </span></div>
</li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:120px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Przemienniki częstotliwości (falowniki)   </span></div>
</li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:120px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Układy łagodnego rozruchu (softstarty)   </span></div>

</li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:120px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Sterowniki silnik&#243;w DC </span></div>
</li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:120px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Sterowniki silnik&#243;w krokowych </span></div>
<ul class='treeList2b'><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:150px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Jednoosiowe   </span></div>
</li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:150px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Wieloosiowe   </span></div>
</li><li class='open'>                        <div class="tlWrap clearfix marked checked" style="padding-left:150px;"><input type="checkbox" checked="checked" class="checkbox" name="SelectedBranch" id="SelectedBranch"><span>Wieloosiowe z interpolacją   </span></div>

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

...

还有我的脚本:

<script type="text/javascript">
/*<![CDATA[*/
    $(function(){           
        $('ul.treeList2b .checkbox').click(function(e){
            e.stopPropagation();
            var obj = $(this).closest('li').find(':checkbox'); 
            obj.attr('checked', this.checked);
            var childCnt=obj.size();  // get childrent count - when parent was clicked
            var checkedCnt=obj.filter(':checked').length; // out of those get those that are checked
            if (childCnt==checkedCnt){
                obj.parents('li').each(function (index, element) {
                    var objSub = $(element).find('li');
                    childCnt = objSub.size();
                    checkedCnt = objSub.find(':checkbox:checked').length;
                    if (childCnt==checkedCnt) { 
                        $(element).find(':checkbox:first').attr("checked", true);
                        $(element).children('div.tlWrap').addClass('checked');
                    }
                    $(element).children('div.tlWrap').addClass('marked');
                });
            }else{ 
                var objParent = obj.parents('li').find(':checkbox:first');
                objParent.attr("checked", false);
                objParent.parent('div.tlWrap').removeClass('checked');
            }
            refleshCheckbox(this);
        });
    });
    function refleshCheckbox(obj){
        if(!$(obj).attr('checked')){
            $(obj).closest('li').find('div.tlWrap').removeClass('marked');
        } 
        if ($(obj).closest('ul').find(':checkbox:checked').length==0){
            $(obj).closest('ul').parent().find('div.tlWrap').removeClass('marked');
        }
    }
/*]]>*/
</script>

【问题讨论】:

    标签: javascript jquery jquery-selectors


    【解决方案1】:

    我不会在此答案中添加所有功能,因为您将通过自己实现它们来了解更多信息。但我做了一个test case on jsFiddle,如图所示:

    $(".option-tree > li > label > input:checkbox").each(function(){
        var $this = $(this),
            options = $this.closest("li").find("> ul > li > label > input:checkbox");
    
        $this.change(function(){
            options.prop("checked", $this[0].checked);
        });
    
        options.change(function(){
            var  all = options.length,
               checked = options.filter(":checked").length;
            $this[0].checked = all === checked;
        });
    
    });
    

    请注意,上面的示例使用jQuery 1.6,您必须使用.prop 而不是.attr.removeAttr

    对于早期版本的 jQuery(1.6 之前),它看起来像这样:

    $(".option-tree > li > label > input:checkbox").each(function(){
        var $this = $(this),
            options = $this.closest("li").find("> ul > li > label > input:checkbox");
    
        $this.change(function(){
            if ($this[0].checked) {
                options.attr("checked", "checked");
            } else {
                options.removeAttr("checked");
            }
        });
    
        options.change(function(){
            var  all = options.length,
               checked = options.filter(":checked").length;
            $this[0].checked = all === checked;
        });
    
    });
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多