Есть ли способ выбрать узлы-братья?
По некоторым причинам производительности я пытаюсь найти способ выбрать только узлы-братья выбранного узла. Например,
<div id="outer">
<div id="inner1"> </div>
<div id="inner2"> </div>
<div id="inner3"> </div>
<div id="inner4"> </div>
</div>
Если я выбрал узел inner1, есть ли способ получить доступ к его inner2-4
узлам inner2-4
?
Ответы
Ответ 1
Ну... конечно... просто получить доступ к родительскому, а затем к детям.
node.parentNode.childNodes[]
или... с помощью jQuery:
$('#innerId').siblings()
Изменить: Клетус, как всегда, вдохновляет. Я потянулся дальше. Вот как jQuery получает братьев и сестер по существу:
function getChildren(n, skipMe){
var r = [];
for ( ; n; n = n.nextSibling )
if ( n.nodeType == 1 && n != skipMe)
r.push( n );
return r;
};
function getSiblings(n) {
return getChildren(n.parentNode.firstChild, n);
}
Ответ 2
var sibling = node.nextSibling;
Это приведет к возвращению брата сразу после него, или null больше не будет братьев и сестер. Аналогично, вы можете использовать previousSibling
.
[Изменить]. С другой стороны, это не даст следующий тег div
, но пробел после node. Лучше, кажется,
var sibling = node.nextElementSibling;
Существует также previousElementSibling
.
Ответ 3
Быстрый:
var siblings = n => [...n.parentElement.children].filter(c=>c!=n)
https://codepen.io/anon/pen/LLoyrP?editors=1011
Получить родительские дочерние элементы как массив, отфильтровать этот элемент.
Изменить:
И чтобы отфильтровать текстовые узлы (спасибо pmrotule):
var siblings = n => [...n.parentElement.children].filter(c=>c.nodeType == 1 && c!=n)
Ответ 4
С 2017 года:
простой ответ: element.nextElementSibling
для получения правильного элемента. также у вас есть element.previousElementSibling
для предыдущего
отсюда довольно просто получить все следующие sibiling
var n = element, ret = [];
while (n = n.nextElementSibling){
ret.push(n)
}
return ret;
Ответ 5
Вы проверили метод "Sibling" в jQuery?
sibling: function( n, elem ) {
var r = [];
for ( ; n; n = n.nextSibling ) {
if ( n.nodeType === 1 && n !== elem ) {
r.push( n );
}
}
return r;
}
n.nodeType == 1 проверить, является ли элемент html node и n! == исключать текущий элемент.
Я думаю, вы можете использовать одну и ту же функцию, весь этот код, похоже, ванильный javascript.
Ответ 6
Есть несколько способов сделать это.
Любой из следующих должен сделать трюк.
// METHOD A (ARRAY.FILTER, STRING.INDEXOF)
var siblings = function(node, children) {
siblingList = children.filter(function(val) {
return [node].indexOf(val) != -1;
});
return siblingList;
}
// METHOD B (FOR LOOP, IF STATEMENT, ARRAY.PUSH)
var siblings = function(node, children) {
var siblingList = [];
for (var n = children.length - 1; n >= 0; n--) {
if (children[n] != node) {
siblingList.push(children[n]);
}
}
return siblingList;
}
// METHOD C (STRING.INDEXOF, ARRAY.SPLICE)
var siblings = function(node, children) {
siblingList = children;
index = siblingList.indexOf(node);
if(index != -1) {
siblingList.splice(index, 1);
}
return siblingList;
}
К вашему сведению: кодовая база jQuery - отличный ресурс для изучения Javascript класса A.
Вот отличный инструмент, который раскрывает кодовую базу jQuery в очень обтекаемой форме. http://james.padolsey.com/jquery/
Ответ 7
Здесь вы можете получить предыдущие, следующие и все братья и сестры (обе стороны):
function prevSiblings(target) {
var siblings = [], n = target;
while(n = n.previousElementSibling) siblings.push(n);
return siblings;
}
function nextSiblings(target) {
var siblings = [], n = target;
while(n = n.nextElementSibling) siblings.push(n);
return siblings;
}
function siblings(target) {
var prev = prevSiblings(target) || [],
next = nexSiblings(target) || [];
return prev.concat(next);
}
Ответ 8
Используйте document.querySelectorAll() и Циклы и итерация
function sibblingOf(children,targetChild){
var children = document.querySelectorAll(children);
for(var i=0; i< children.length; i++){
children[i].addEventListener("click", function(){
for(var y=0; y<children.length;y++){children[y].classList.remove("target")}
this.classList.add("target")
}, false)
}
}
sibblingOf("#outer >div","#inner2");
#outer >div:not(.target){color:red}
<div id="outer">
<div id="inner1">Div 1 </div>
<div id="inner2">Div 2 </div>
<div id="inner3">Div 3 </div>
<div id="inner4">Div 4 </div>
</div>
Ответ 9
var childNodeArray = document.getElementById('somethingOtherThanid').childNodes;
Ответ 10
1) Добавить выбранный класс в целевой элемент
2) Найти все дочерние элементы родительского элемента, исключая целевой элемент
3) Удалить класс из целевого элемента
<div id = "outer">
<div class="item" id="inner1">Div 1 </div>
<div class="item" id="inner2">Div 2 </div>
<div class="item" id="inner3">Div 3 </div>
<div class="item" id="inner4">Div 4 </div>
</div>
function getSiblings(target) {
target.classList.add('selected');
let siblings = document.querySelecttorAll('#outer .item:not(.currentlySelected)')
target.classList.remove('selected');
return siblings
}
Ответ 11
JQuery
$el.siblings();
Родной - последний, Edge13+
[...el.parentNode.children].filter((child) =>
child !== el
);
Родной (альтернатива) - последний, Edge13+
Array.from(el.parentNode.children).filter((child) =>
child !== el
);
Родной - IE10+
Array.prototype.filter.call(el.parentNode.children, (child) =>
child !== el
);
Ответ 12
Следующая функция вернет массив, содержащий все элементы данного элемента.
function getSiblings(elem) {
return [...elem.parentNode.children].filter(item => item !== elem);
}
Просто передайте выбранный элемент в функцию getSiblings()
как единственный параметр.
Ответ 13
x1 = document.getElementById('outer')[0]
.getElementsByTagName('ul')[1]
.getElementsByTagName('li')[2];
x1.setAttribute("id", "buyOnlineLocationFix");