Вернуть дерево предков блока, на который был произведен клик
Суть задачи в том, чтобы когда я нажимал на любой блок на странице сайта, мне выдавало полный путь от body до этого элемента. То бишь функция, которая возвращает дерево предков блока, на который нажали, вплоть до body, и в случае если таких элементов несколько, то возвращался еще и индекс блока, на который нажали. Пробовал через parent() и parents(), но до точки так и не дошел
Ответы (2 шт):
Автор решения: reznikovkg
→ Ссылка
// Переменная для хранения крайнего полученного пути (дерева)
var t = null;
// Создаем событие для клика на странице
document.addEventListener('click', function (e) {
t = e.path; // Сам путь (готовое свойство события)
console.log(t); // Выводим путь при клике
})
Вывод до body
// Переменная для хранения крайнего полученного пути (дерева)
var t = null;
// Создаем событие для клика на странице
document.addEventListener('click', function (e) {
t = e.path; // Сам путь (готовое свойство события)
const index = t.findIndex(item => (item.tagName.toLowerCase() === 'body'))
console.log(t.slice(0, index + 1)); // Выводим путь при клике до body
})
Автор решения: DiD
→ Ссылка
/**
* Функция, которая возвращает селектор передаваемого аргументом тега
*/
const expose = tag => {
/* Селектор формируется именем тега плюс
если есть id, то #id,
иначе прибавляем классы */
let sel = `${tag.tagName.toLowerCase()}`+
( tag.id?`#${tag.id}`:
tag.className?`.${tag.className.replace(/ /g,'.')}`:
''), col;
/* Если у элемента нет id,
и с таким селектором в родителе находит не один элемент,
то можно прибавить к селектору индекс элемента */
if(!tag.id&&(col=tag.parentNode.querySelectorAll(sel)).length>1)
sel+=`:nth-child(${[...col].findIndex(el=>tag==el)+1})`;
/* возвращаем селектор */
return sel;
}
/* событие onclick */
document.body.onclick = e =>
/* собираем общий селектор до тега, куда кликнули */
alert(e.path.reverse().splice(3).map(expose).join('>'));
/* Дальнейший код к задаче не относится, но может помочь в отладке */
let selected;
document.body.onmousemove = e => {
let { x, y } = e;
if(selected) selected.style.outline = '';
selected = document.elementFromPoint(x,y);
if(selected) selected.style.outline='1px solid red';
};