javascript - Obtener el índice de un elemento como hijo en relación con el padre
Digamos que tengo este marcado:
<ul id="wizard">
<li>Step 1</li>
<li>Step 2</li>
</ul>
Y tengo este jQuery:
$("#wizard li").click(function () {
// alert index of li relative to ul parent
});
¿Cómo puedo obtener el índice del hijo li relativo a su padre, al hacer clic en ese li?
Por ejemplo, cuando haces clic en "Paso 1", debería aparecer un alert con "0".
Respuesta #1
$("#wizard li").click(function () {
console.log( $(this).index() );
});
Sin embargo, en lugar de adjuntar un controlador de clic a cada elemento de la lista, es mejor (en términos de rendimiento) usar delegate, que se vería así:
$("#wizard").delegate('li', 'click', function () {
console.log( $(this).index() );
});
En jQuery 1.7+, deberías usar on. El siguiente ejemplo enlaza el evento al elemento #wizard, funcionando como un evento delegado:
$("#wizard").on("click", "li", function() {
console.log( $(this).index() );
});
Respuesta #2
algo como:
$("ul#wizard li").click(function () {
var index = $("ul#wizard li").index(this);
alert("index is: " + index)
});
Respuesta #3
No es necesario requerir una gran biblioteca como jQuery para lograr esto, si no quieres. Para lograr esto con la manipulación del DOM incorporada, obtén una colección de los elementos li hermanos en un arreglo, y al hacer clic, verifica el indexOf del elemento clicado en ese arreglo.
const lis = [...document.querySelectorAll('#wizard > li')];
lis.forEach((li) => {
li.addEventListener('click', () => {
const index = lis.indexOf(li);
console.log(index);
});
});<ul id="wizard">
<li>Step 1</li>
<li>Step 2</li>
</ul>O, con delegación de eventos:
const lis = [...document.querySelectorAll('#wizard li')];
document.querySelector('#wizard').addEventListener('click', ({ target }) => {
// Make sure the clicked element is a <li> which is a child of wizard:
if (!target.matches('#wizard > li')) return;
const index = lis.indexOf(target);
console.log(index);
});<ul id="wizard">
<li>Step 1</li>
<li>Step 2</li>
</ul>O, si los elementos hijos pueden cambiar dinámicamente (como con una lista de tareas), entonces tendrás que construir el arreglo de lis en cada clic, en lugar de hacerlo de antemano:
const wizard = document.querySelector('#wizard');
wizard.addEventListener('click', ({ target }) => {
// Make sure the clicked element is a <li>
if (!target.matches('li')) return;
const lis = [...wizard.children];
const index = lis.indexOf(target);
console.log(index);
});<ul id="wizard">
<li>Step 1</li>
<li>Step 2</li>
</ul>