Pregunta

Necesito poder seleccionar el elemento raíz de un fragmento sin conocer los tipos de nodo, clase, id o jerarquía.

<div id="0">
    <div id="0a">
        <div id="a01"></div>
    </div>
    <div id="0b">
    </div>
    <div id="0c">
    </div>
</div>

Quiero poder hacer algo como $ (': root') y tener 0 seleccionado en el ejemplo anterior.

Mejor aún, preferiría $ (': level (0)') que significaría lo mismo que arriba, $ (': level (1)') seleccionaría 0a, 0b y 0c y $ (': level (1) > div') seleccionaría a01.

¿Alguna idea sobre cómo hacerlo bien?

¿Fue útil?

Solución

Si bien esta pregunta fue respondida hace un tiempo perfectamente, solo estaba tratando de intentarlo yo mismo y no estaba muy interesado en usar un selector como *: not (* *) - principalmente por los probables gastos generales. No sé si esta es una adición reciente a la capacidad de jQuery (estoy usando 1.8) pero puede usar:

$(':eq(0)');

Esto seleccionará el primer elemento no textnode encontrado, por lo que, a menos que el dom que está atravesando sea ilegal en su formación, siempre debe obtener el elemento raíz. También es muy óptimo porque jQuery debería saber detenerse después del primer elemento encontrado.

Entonces, aquí hay algo para todos los fanáticos de WSOD:

$(':eq(0)').remove();

Ah, y en caso de que no sea obvio que los fragmentos de código anteriores solo ilustran el selector, y te encuentras trabajando con un fragmento parcial (en lugar del documento completo), entonces debes usar este selector con el filtro de jQuery método:

$(fragment).filter(':eq(0)');

Sin embargo, cuando trabaje con fragmentos, puede hacer lo siguiente:

$(fragment).get(0);

Aunque tenga en cuenta que .get (0) puede seleccionar nodos de texto / comentario si son el primer elemento en su documento, mientras que el enfoque de filtro siempre encontrará el primer elemento real.

Otros consejos

OK, entonces lo que debe hacer es lo siguiente (suponiendo que está usando la muestra que tiene), si desea encontrar el nodo de nivel superior usando jquery es lo siguiente:

 $('*:not(* *)');  

Lo que literalmente está pidiendo aquí es para todos los nodos que no son hijos de otros nodos. El problema es que para un documento html, esto siempre le dará solo el elemento html, que no es particularmente útil. Entonces, si desea encontrar el elemento de nivel superior dentro del cuerpo de un documento html, usaría algo mucho más simple:

 $('body > *');

si quisieras el segundo nivel, simplemente irías

 $('body > * > *');

Pero, suponiendo que tenga algún tipo de estructura de documento arbitraria (como la que menciona), lo que puede hacer es usar el primer ejemplo para encontrar el primer nivel:

 $('*:not(* *)');

y luego para el segundo nivel

 $('*:not(* *)').find('> *');

y para el tercer nivel

 $('*:not(* *)').find('> * > *');

y así sucesivamente. Si está buscando un elemento div raíz (suponiendo que su muestra es como la pregunta), puede hacer esto:

 $('div:not(div div)');

y así sucesivamente, reemplazando * con div. No estoy seguro de por qué querrías hacer esto, pero funcionará. El problema es que la pregunta realmente no proporciona suficiente contexto para que podamos ofrecerle una mejor alternativa.

Soy más un prototipo, pero creo que podrías obtener todos los nodos y luego obtener el primer nodo en la matriz:

$('*')[0]

Luego obtenga los elementos secundarios de eso (para 0a, 0b y 0c)

$('*')[0].children()

Si tienes tus elementos como un fragmento jQuery como:

var myElements = $('<div id="0">
<div id="0a">
    <div id="a01"></div>
</div>
<div id="0b">
</div>
<div id="0c">
</div>
</div>');

entonces puedes encontrar el primer elemento:

myElements.filter(":first")

La función de filtro se ve desde el elemento raíz del fragmento.

jQuery no es necesario ...

var root = document.firstChild;

Puedo estar malinterpretando la pregunta, pero suponiendo que por raíz te refieres al punto en el que el padre es una etiqueta diferente al niño, entonces lo siguiente debería funcionar.

function GetRoot(element) {
    while(element.parent().attr("tagName") == element.attr("tagName")) {
        element = element.parent();
    }

    return element;
}

Esto básicamente sube por el árbol hasta que encuentra un padre que es una etiqueta diferente y luego devuelve el elemento. Para su ejemplo, eso significaría que si su elemento estuviera en a, o lo que sea, lo detectaría como la raíz y lo devolvería.

También debería ser posible hacer un selector de jquery personalizado con esto, pero obviamente es más complicado.

También debería ser bastante fácil extender esto para tomar un número entero que defina el nivel. Todo lo que necesita hacer es caminar por el árbol hasta la profundidad especificada una vez que haya encontrado la raíz y devuelva esos elementos.

podría considerar el uso de las funciones parent () y children (). si necesita ir a varios niveles, puede encadenarlos así.

$("#a01").parent().parent()  //returns <div id="0">

por favor vea mi comentario, e intentaré darle una mejor solución.

Obtengo el fragmento html de la llamada ajax, y también necesito obtener el div de raíz. Lo que hice fue simplemente llamar a $ (data) , y jQuery analizará el texto de retorno como HTML y le dará la raíz.

$.ajax path,
  type: 'GET'
  contentType: 'application/x-www-form-urlencoded;charset=UTF-8'
  success: (data) ->
    $(data)

Si desea seleccionar el nivel superior primario de un elemento pero aún debajo del cuerpo, iría

$(obj).parents().filter('body > *')
Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top