Controlla se un elemento è figlio di un genitore


115

Ho il codice seguente.

<html>
<head>
    <script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.3.2/jquery.min.js"></script>
</head>

<div id="hello">Hello <div>Child-Of-Hello</div></div>
<br />
<div id="goodbye">Goodbye <div>Child-Of-Goodbye</div></div>

<script type="text/javascript">
<!--
function fun(evt) {
    var target = $(evt.target);    
    if ($('div#hello').parents(target).length) {
        alert('Your clicked element is having div#hello as parent');
    }
}
$(document).bind('click', fun);
-->
</script>

</html>

Mi aspetto che solo quando Child-Of-Helloviene cliccato, $('div#hello').parents(target).lengthrestituirà> 0.

Tuttavia, succede ogni volta che clicco su un punto qualsiasi.

C'è qualcosa che non va nel mio codice?

Risposte:


160

Se sei interessato solo al genitore diretto e non ad altri antenati, puoi semplicemente usarlo parent()e dargli il selettore, come in target.parent('div#hello').

Esempio: http://jsfiddle.net/6BX9n/

function fun(evt) {
    var target = $(evt.target);    
    if (target.parent('div#hello').length) {
        alert('Your clicked element is having div#hello as parent');
    }
}

Oppure, se vuoi controllare se ci sono antenati che corrispondono, usa .parents().

Esempio: http://jsfiddle.net/6BX9n/1/

function fun(evt) {
    var target = $(evt.target);    
    if (target.parents('div#hello').length) {
        alert('Your clicked element is having div#hello as parent');
    }
}

19
come farlo senza jquery?
SuperUberDuper

60

.has()sembra essere progettato per questo scopo. Poiché restituisce un oggetto jQuery, devi anche testare .length:

if ($('div#hello').has(target).length) {
   alert('Target is a child of #hello');
}

@redanimalwar Right; questo è ciò che fa. Trova l'elemento genitore, quindi controlla se targetè al suo interno.
Blazemonger

22

Vanilla 1-liner per IE8 +:

parent !== child && parent.contains(child);

Ecco come funziona:

function contains(parent, child) {
  return parent !== child && parent.contains(child);
}

var parentEl = document.querySelector('#parent'),
    childEl = document.querySelector('#child')
    
if (contains(parentEl, childEl)) {
  document.querySelector('#result').innerText = 'I confirm, that child is within parent el';
}

if (!contains(childEl, parentEl)) {
  document.querySelector('#result').innerText += ' and parent is not within child';
}
<div id="parent">
  <div>
    <table>
      <tr>
        <td><span id="child"></span></td>
      </tr>
    </table>
  </div>
</div>
<div id="result"></div>


Grazie, è davvero fantastico! La ricorsione è interessante. Mi chiedo come l'argomento della funzione diventa (all'interno) dell'oggetto su cui opera la funzione. Potresti avere un collegamento a ulteriori informazioni su questo?
JohnK,

20

Se hai un elemento che non ha un selettore specifico e vuoi comunque controllare se è un discendente di un altro elemento, puoi usare jQuery.contains ()

jQuery.contains (contenitore, contenuto)
Descrizione: controlla se un elemento DOM è un discendente di un altro elemento DOM.

Puoi passare l'elemento genitore e l'elemento che vuoi controllare a quella funzione e restituisce se quest'ultimo è un discendente del primo.


3
Presta particolare attenzione a $.containsprendere elementi DOM e non istanze jQuery, altrimenti restituirà sempre false.
aleclarson

Un altro dettaglio da ricordare: $.containsnon restituisce mai vero se i due argomenti sono lo stesso elemento. Se lo vuoi, usa domElement.contains(domElement).
aleclarson

9

Ho finito per usare .closest () invece.

$(document).on("click", function (event) {
    if($(event.target).closest(".CustomControllerMainDiv").length == 1)
    alert('element is a child of the custom controller')
});

3

Puoi far funzionare il tuo codice semplicemente scambiando i due termini:

if ($(target).parents('div#hello').length) {

Hai avuto il figlio e il genitore nella direzione sbagliata.


2
var target = $(evt.target);quindi il tuo codice dovrebbe leggere if (target.parents('div#hello').length) {e non...$(target)...
Peter Ajtai,

0

Oltre alle altre risposte, puoi utilizzare questo metodo meno noto per afferrare elementi di un determinato genitore in questo modo,

$('child', 'parent');

Nel tuo caso, sarebbe

if ($(event.target, 'div#hello')[0]) console.log(`${event.target.tagName} is an offspring of div#hello`);

Notare l'uso di virgole tra il figlio e il genitore e le loro virgolette separate. Se fossero circondati dalle stesse virgolette

$('child, parent');

avresti un oggetto contenente entrambi gli oggetti, indipendentemente dal fatto che esistano nei loro alberi dei documenti.


Questo è un trucco interessante, ma non funziona bene con elementi senza ID o classi
aln447
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.