获取单击的<a>的DOM路径

Tom*_*kay 24 html javascript jquery dom css-selectors

HTML

<body>
<div class="lol">
<a class="rightArrow" href="javascriptVoid:(0);" title"Next image">
</div>
</body>
Run Code Online (Sandbox Code Playgroud)

伪代码

$(".rightArrow").click(function() {
rightArrowParents = this.dom(); //.dom(); is the pseudo function ... it should show the whole
alert(rightArrowParents);
});
Run Code Online (Sandbox Code Playgroud)

提醒信息将是:

身体div.lol a.rightArrow

我如何使用javascript/jquery获取此信息?

Mic*_*nor 40

这是一个返回jQuery路径的本机JS版本.如果有元素,我也会为元素添加ID.如果您在数组中看到id,这将使您有机会执行最短路径.

var path = getDomPath(element);
console.log(path.join(' > '));
Run Code Online (Sandbox Code Playgroud)

输出

body > section:eq(0) > div:eq(3) > section#content > section#firehose > div#firehoselist > article#firehose-46813651 > header > h2 > span#title-46813651
Run Code Online (Sandbox Code Playgroud)

这是功能.

function getDomPath(el) {
  var stack = [];
  while ( el.parentNode != null ) {
    console.log(el.nodeName);
    var sibCount = 0;
    var sibIndex = 0;
    for ( var i = 0; i < el.parentNode.childNodes.length; i++ ) {
      var sib = el.parentNode.childNodes[i];
      if ( sib.nodeName == el.nodeName ) {
        if ( sib === el ) {
          sibIndex = sibCount;
        }
        sibCount++;
      }
    }
    if ( el.hasAttribute('id') && el.id != '' ) {
      stack.unshift(el.nodeName.toLowerCase() + '#' + el.id);
    } else if ( sibCount > 1 ) {
      stack.unshift(el.nodeName.toLowerCase() + ':eq(' + sibIndex + ')');
    } else {
      stack.unshift(el.nodeName.toLowerCase());
    }
    el = el.parentNode;
  }

  return stack.slice(1); // removes the html element
}
Run Code Online (Sandbox Code Playgroud)


T.J*_*der 32

使用jQuery,就像这样(后面是一个不使用jQuery的解决方案,除了事件;更少的函数调用,如果这很重要):

$(".rightArrow").click(function() {
  var rightArrowParents = [];
  $(this).parents().addBack().not('html').each(function() {
    var entry = this.tagName.toLowerCase();
    if (this.className) {
      entry += "." + this.className.replace(/ /g, '.');
    }
    rightArrowParents.push(entry);
  });
  alert(rightArrowParents.join(" "));
  return false;
});
Run Code Online (Sandbox Code Playgroud)

实例:

$(".rightArrow").click(function() {
  var rightArrowParents = [];
  $(this).parents().addBack().not('html').each(function() {
    var entry = this.tagName.toLowerCase();
    if (this.className) {
      entry += "." + this.className.replace(/ /g, '.');
    }
    rightArrowParents.push(entry);
  });
  alert(rightArrowParents.join(" "));
  return false;
});
Run Code Online (Sandbox Code Playgroud)
<div class="lol multi">
  <a href="#" class="rightArrow" title="Next image">Click here</a>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
Run Code Online (Sandbox Code Playgroud)

(在活生生的实例,我已经更新了class该属性divlol multi证明处理多类.)

这用于parents获取被单击的元素的祖先,html从该通道移除元素not(自从您开始body),然后循环创建每个父项的条目并将它们推送到数组上.然后我们使用addBacka后面添加到集合中,这也将集合的顺序更改为您想要的(parents特殊情况,它会按照您想要的顺序反向提供父级,但是然后addBAck将其按照DOM顺序重新设置) .然后它用于Array#join创建以空格分隔的字符串.

在创建条目时,如果有任何内容,className我们将空格替换.为支持具有多个类的元素(<p class='foo bar'>has className= "foo bar",以便条目最终成为p.foo.bar).

只是为了完整性,这是jQuery可能过度杀伤的地方之一,你可以通过走DOM来做到这一点:

$(".rightArrow").click(function() {
  var rightArrowParents = [],
    elm,
    entry;

  for (elm = this; elm; elm = elm.parentNode) {
    entry = elm.tagName.toLowerCase();
    if (entry === "html") {
      break;
    }
    if (elm.className) {
      entry += "." + elm.className.replace(/ /g, '.');
    }
    rightArrowParents.push(entry);
  }
  rightArrowParents.reverse();
  alert(rightArrowParents.join(" "));
  return false;
});
Run Code Online (Sandbox Code Playgroud)

实例:

$(".rightArrow").click(function() {
  var rightArrowParents = [],
    elm,
    entry;

  for (elm = this; elm; elm = elm.parentNode) {
    entry = elm.tagName.toLowerCase();
    if (entry === "html") {
      break;
    }
    if (elm.className) {
      entry += "." + elm.className.replace(/ /g, '.');
    }
    rightArrowParents.push(entry);
  }
  rightArrowParents.reverse();
  alert(rightArrowParents.join(" "));
  return false;
});
Run Code Online (Sandbox Code Playgroud)
<div class="lol multi">
  <a href="#" class="rightArrow" title="Next image">Click here</a>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
Run Code Online (Sandbox Code Playgroud)

在那里我们只是重复使用元素的标准parentNode属性来走向树,直到我们用完父母或者我们看到html元素.然后我们反转我们的数组(因为它向后移动到你想要的输出),并加入它,我们很高兴去.

  • 我想你已经知道你是个坏人.谢啦!:) (4认同)

Ale*_*tic 10

我需要一个本机JS版本,它返回CSS标准路径(不是jQuery),并处理ShadowDOM.此代码是Michael Connor答案的一个小更新,以防万一其他人需要它:

function getDomPath(el) {
  if (!el) {
    return;
  }
  var stack = [];
  var isShadow = false;
  while (el.parentNode != null) {
    // console.log(el.nodeName);
    var sibCount = 0;
    var sibIndex = 0;
    // get sibling indexes
    for ( var i = 0; i < el.parentNode.childNodes.length; i++ ) {
      var sib = el.parentNode.childNodes[i];
      if ( sib.nodeName == el.nodeName ) {
        if ( sib === el ) {
          sibIndex = sibCount;
        }
        sibCount++;
      }
    }
    // if ( el.hasAttribute('id') && el.id != '' ) { no id shortcuts, ids are not unique in shadowDom
    //   stack.unshift(el.nodeName.toLowerCase() + '#' + el.id);
    // } else
    var nodeName = el.nodeName.toLowerCase();
    if (isShadow) {
      nodeName += "::shadow";
      isShadow = false;
    }
    if ( sibCount > 1 ) {
      stack.unshift(nodeName + ':nth-of-type(' + (sibIndex + 1) + ')');
    } else {
      stack.unshift(nodeName);
    }
    el = el.parentNode;
    if (el.nodeType === 11) { // for shadow dom, we
      isShadow = true;
      el = el.host;
    }
  }
  stack.splice(0,1); // removes the html element
  return stack.join(' > ');
}
Run Code Online (Sandbox Code Playgroud)