2010-09-24 2 views
23

есть ли метод cheep для выбора самого глубокого ребенка элемента?выбрать самый глубокий ребенок в jQuery

Пример:

<div id="SearchHere"> 
    <div> 
    <div> 
     <div></div> 
    </div> 
    </div> 
    <div></div> 
    <div> 
    <div> 
     <div> 
     <div id="selectThis"></div> 
     </div> 
    </div> 
    </div> 
    <div> 
    <div></div> 
    </div> 
</div> 
+0

не имел в виду как критику, но я очарован, почему вы хотите? –

+1

Для всех тех, кто находит это через поисковые системы, я обновил суть из jonathan с улучшенной версией от patrick dw. Также немного расширились инструкции. Вы можете найти его здесь: [jQuery deepest plugin gist] (https://gist.github.com/1014671 "jQuery deepest plugin gist") – 2011-06-08 15:54:54

ответ

27

EDIT: Это, вероятно, лучший подход, чем мой оригинальный ответ:

Пример:http://jsfiddle.net/patrick_dw/xN6d5/5/

var $target = $('#SearchHere').children(), 
    $next = $target; 

while($next.length) { 
    $target = $next; 
    $next = $next.children(); 
} 

alert($target.attr('id')); 

или это что даже немного короче:

Пример:http://jsfiddle.net/patrick_dw/xN6d5/6/

var $target = $('#SearchHere').children(); 

while($target.length) { 
    $target = $target.children(); 
} 

alert($target.end().attr('id')); // You need .end() to get to the last matched set 

Оригинальный ответ:

Это, казалось бы работать:

Пример:http://jsfiddle.net/xN6d5/4/

var levels = 0; 
var deepest; 

$('#SearchHere').find('*').each(function() { 
    if(!this.firstChild || this.firstChild.nodeType !== 1 ) { 
     var levelsFromThis = $(this).parentsUntil('#SearchHere').length; 
     if(levelsFromThis > levels) { 
      levels = levelsFromThis; 
      deepest = this; 
     } 
    } 
}); 

alert(deepest.id); 

Если вы знаете, что самым глубоким будет определенный тег (или что-то еще), вы можете ускорить его, заменив .find('*') на .find('div').

EDIT: обновление только проверить длину, если текущий элемент делает не имеют firstChild или, если это делает, что FirstChild не является типом узла 1.

+1

Удивительный! Работает отлично! Я также инкапсулировал это в плагин jQuery. Здесь: https://gist.github.com/714851 – Jonathan

+0

@jonathanconway - Обновлен мой ответ с вероятной более эффективной версией. – user113716

+2

@ user113716 Я сделал еще более короткую версию http://jsfiddle.net/xN6d5/44/ :) – EaterOfCode

3

Я не думаю, что вы можете сделать это прямо, но вы можете попробовать

var s = "#SearchHere"; 
while($(s + " >div ").size() > 0) 
    s += " > div"; 
alert($(s).attr('id')); 
5

Вот небольшое улучшение на ответ от @ user113716, эта версия обрабатывает случай, когда нет никаких детей и возвращает цель сам.

(function($) { 

    $.fn.deepestChild = function() { 
     if ($(this).children().length==0) 
      return $(this); 

     var $target = $(this).children(), 
     $next = $target; 

     while($next.length) { 
      $target = $next; 
      $next = $next.children(); 
     } 

     return $target; 
    }; 

}(jQuery)); 
+0

+1, потому что мне просто пришлось копировать/прош ть, чтобы получить именно то, что мне нужно, получить вложенный объект или только начальный объект. Спасибо! – Georgio

1

Этот цельный однострочный вкладыш работал для меня, но предполагает, что в иерархии ниже всего один листовой узел.

jQuery("#searchBeginsHere") 
    .filter(function(i,e){ return jQuery(e).children().size() === 0; }) 
0

Версия, чтобы получить самую глубокую для каждого листа.

http://jsfiddle.net/ncppk0zw/14/

var found = $('#SearchHere *'); 

for (var i = 0; i < found.length; i++) { 
    if (i > 1) { 
     if (found[i].parentNode !== found[i-1]) { 
      // Deepest. Next element is other leaf 
      console.log(found[i-1]); 
      continue; 
     } 
     if (i == found.length-1) { 
      // Deepest. Last element in DOM tree 
      console.log(found[i]); 
     } 
    } 
} 
Смежные вопросы