2010-09-24 33 views
23

Gibt es eine billige Methode, um das tiefste Kind eines Elements auszuwählen?Wählen Sie das tiefste Kind in jQuery

Beispiel:

<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

nicht als Kritik gemeint, aber ich bin fasziniert von warum Sie wollen würde? –

+1

Für all jene, die dies über die Suchmaschinen finden, habe ich den Hauptteil von Jonathan mit der verbesserten Version von patrick dw aktualisiert. Erweitert auch die Anweisungen ein wenig. Sie können es hier finden: [jQuery tiefsten Plugin-Gist] (https://gist.github.com/1014671 "jQuery tiefsten Plugin-Gist") –

Antwort

27

EDIT: Dies ist wahrscheinlich ein besserer Ansatz als meine ursprüngliche Antwort:

Beispiel: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')); 

oder das was noch ein etwas kürzer:

Beispiel: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 

Ursprüngliche Antwort:

Beispiel:

Diese scheinen würde arbeitenhttp://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); 

Wenn Sie wissen, dass das tiefste ein bestimmtes Tag (oder etwas anderes) sein wird, könnten Sie es beschleunigen, indem Sie zum Beispiel .find('*') durch .find('div') ersetzen.

EDIT: aktualisiert, um nur die Länge zu prüfen, ob das aktuelle Element nicht tut ein firstChild oder wenn doch, daß der first ist kein Typ-1-Knoten.

+1

Super! Funktioniert perfekt! Ich habe dies auch in einem jQuery-Plugin gekapselt. Hier: https://gist.github.com/714851 – Jonathan

+0

@jonathanconway - Meine Antwort wurde mit einer wahrscheinlich effizienteren Version aktualisiert. – user113716

+2

@ user113716 Ich habe sogar eine kürzere Version http://jsfiddle.net/xN6d5/44/ :) – EaterOfCode

3

Ich glaube nicht, dass Sie es direkt tun können, aber Sie können

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

Hier ist eine leichte Verbesserung auf die Antwort von @ user113716, diese Version behandelt den Fall versuchen, wenn es keine Kinder gibt und gibt das Ziel selbst.

+0

+1, weil ich nur kopieren/Vergangenheit, um genau das zu bekommen, was ich brauche, verschachtelte Objekt oder nur anfängliche Objekt. Danken! – Georgio

1

Diese verkettbare Einzeiler funktionierte für mich, aber es nimmt an, dass es nur einen Blattknoten in der Hierarchie unten gibt.

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

Version, die für jedes Blatt am tiefsten wird.

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]); 
     } 
    } 
}