最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - jQuery InnerText not including sub element - Stack Overflow

programmeradmin4浏览0评论

I'm wondering how I would get the text of a nested list item without getting the text of its children i.e.

<ul>
   <li id="node">
      I want this
    <ul>
       <li>
          I don't want this
        </li>
    </ul>
    </li>
</ul>

Now using jQuery with $('#node').text() gets me all text, where as I just want the "I want this" string.

I'm wondering how I would get the text of a nested list item without getting the text of its children i.e.

<ul>
   <li id="node">
      I want this
    <ul>
       <li>
          I don't want this
        </li>
    </ul>
    </li>
</ul>

Now using jQuery with $('#node').text() gets me all text, where as I just want the "I want this" string.

Share Improve this question edited Mar 21, 2023 at 0:44 halfer 20.4k19 gold badges108 silver badges201 bronze badges asked Sep 25, 2009 at 11:31 OwenOwen 7,0987 gold badges45 silver badges79 bronze badges
Add a comment  | 

4 Answers 4

Reset to default 10

Tim's solution will work. If your markup is always fixed in that format and you only need to read that first stretch of text up to the child element, you could even get away with simply:

node.firstChild.data

The following will get you a concatenated string of all the text nodes that are direct children of a node:

function getChildText(node) {
  var text = "";
  for (var child = node.firstChild; !!child; child = child.nextSibling) {
    if (child.nodeType === 3) {
      text += child.nodeValue;
    }
  }
  return text;
}

alert( getChildText(document.getElementById("node")) );

This example uses .contents() to get all the children nodes (including text nodes), then uses .map() to turn each child node into a string based on the nodeType. If the node is a text node (i.e. text not within the <li>), we return its nodeValue.

This returns a jQuery set containing strings, so we call .get() to get a 'standard' array object that we can call .join() on.

// our 'div' that contains your code:
var $html = $('<li id="node">I want this<ul><li>I dont want this</li></ul>    </li>');

// Map the contents() into strings
$html.contents().map(function() { 
  // if the node is a textNode, use its nodeValue, otherwise empty string
  return this.nodeType == 3 ? this.nodeValue : undefined; 
  // get the array, and join it together:
}).get().join('');

// "I want this    " -- note the extra whitespace from after the <ul>

And to make a simpler call:

$.fn.directText=function(delim) {
  if (!delim) delim = '';
  return this.contents().map(function() { return this.nodeType == 3 ? this.nodeValue : undefined}).get().join(delim);
};

$html.directText();
// "I want this    "

Or a slightly more robust version to allow trimming whitespace / changing the joining string:

$.fn.directText = function(settings) {
   settings = $.extend({},$.fn.directText.defaults, settings);
   return this.contents().map(function() {
     if (this.nodeType != 3) return undefined; // remove non-text nodes
     var value = this.nodeValue;
     if (settings.trim) value = $.trim(value);
     if (!value.length) return undefined; // remove zero-length text nodes
     return value;
   }).get().join(settings.joinText);
};

$.fn.directText.defaults = {
   trim: true,
   joinText: ''
};

There's a Text Children Plugin for this, if it's something you'll want to do often. It offers you a few options for the output too.

发布评论

评论列表(0)

  1. 暂无评论