繁体   English   中英

获取所选元素的外部 HTML

[英]Get selected element's outer HTML

我正在尝试使用 jQuery 获取所选对象的 HTML。 我知道.html()函数; 问题是我需要包含所选对象的 HTML(在本例中为表格行,其中.html()仅返回行内的单元格)。

我四处搜索,发现了一些非常“hackish”类型的克隆对象、将其添加到新创建的 div 等的方法,但这似乎很脏。 有没有更好的方法,或者新版本的 jQuery (1.4.2) 是否提供任何类型的outerHtml功能?

我相信目前(5/1/2012),所有主流浏览器都支持outerHTML功能。 在我看来,这个片段就足够了。 我个人会选择记住这一点:

// Gives you the DOM element without the outside wrapper you want
$('.classSelector').html()

// Gives you the outside wrapper as well only for the first element
$('.classSelector')[0].outerHTML

// Gives you the outer HTML for all the selected elements
var html = '';
$('.classSelector').each(function () {
    html += this.outerHTML;
});

//Or if you need a one liner for the previous code
$('.classSelector').get().map(function(v){return v.outerHTML}).join('');

编辑element.outerHTML 基本支持统计

无需为其生成函数。 只需这样做:

$('a').each(function(){
    var s = $(this).clone().wrap('<p>').parent().html();
    console.log(s);
});

(顺便说一下,您浏览器的控制台将显示记录的内容。自 2009 年左右以来的大多数最新浏览器都具有此功能。)

最后的魔法是这样的:

.clone().wrap('<p>').parent().html();

克隆意味着您实际上并没有干扰 DOM。 在没有它的情况下运行它,您将看到在所有超链接之前/之后插入了p标签(在本例中),这是不可取的。 所以,是的,使用.clone()

它的工作方式是,它需要每a标签,使得它的一个克隆的RAM,与包装p标签,获取它的父(指p标签),然后得到innerHTML它的财产。

编辑:接受建议并将div标签更改为p标签,因为它的输入较少并且工作方式相同。

2014 年编辑:问题和此回复来自 2010 年。当时,没有更好的解决方案可以广泛使用。 现在,许多其他回复都更好:例如 Eric Hu 或 Re Capcha 的回复。

该站点似乎为您提供了一个解决方案: jQuery:outerHTML | 油豆腐

jQuery.fn.outerHTML = function(s) {
    return s
        ? this.before(s).remove()
        : jQuery("<p>").append(this.eq(0).clone()).html();
};

怎么样: prop('outerHTML')

var outerHTML_text = $('#item-to-be-selected').prop('outerHTML');

并设置:

$('#item-to-be-selected').prop('outerHTML', outerHTML_text);

它对我有用。

PS :这是在jQuery 1.6 中添加的。

扩展jQuery:

(function($) {
  $.fn.outerHTML = function() {
    return $(this).clone().wrap('<div></div>').parent().html();
  };
})(jQuery);

并像这样使用它: $("#myTableRow").outerHTML();

我同意 Arpan(2010 年 12 月 13 日 5:59)。

他的做法实际上是一种更好的做法,因为您不使用克隆。 clone 方法非常耗时,如果您有子元素,并且似乎没有其他人关心 IE 是否真的拥有outerHTML属性(是的,IE 确实有一些有用的技巧)。

但我可能会创建他的脚本有点不同:

$.fn.outerHTML = function() {
    var $t = $(this);
    if ($t[0].outerHTML !== undefined) {
        return $t[0].outerHTML;
    } else {
        var content = $t.wrap('<div/>').parent().html();
        $t.unwrap();
        return content;
    }
};

要成为真正的 jQuery 风格,您可能希望outerHTML()成为一个 getter一个 setter,并使其行为尽可能类似于html()

$.fn.outerHTML = function (arg) {
    var ret;

    // If no items in the collection, return
    if (!this.length)
        return typeof arg == "undefined" ? this : null;
    // Getter overload (no argument passed)
    if (!arg) {
        return this[0].outerHTML || 
            (ret = this.wrap('<div>').parent().html(), this.unwrap(), ret);
    }
    // Setter overload
    $.each(this, function (i, el) {
        var fnRet, 
            pass = el,
            inOrOut = el.outerHTML ? "outerHTML" : "innerHTML";

        if (!el.outerHTML)
            el = $(el).wrap('<div>').parent()[0];

        if (jQuery.isFunction(arg)) { 
            if ((fnRet = arg.call(pass, i, el[inOrOut])) !== false)
                el[inOrOut] = fnRet;
        }
        else
            el[inOrOut] = arg;

        if (!el.outerHTML)
            $(el).children().unwrap();
    });

    return this;
}

工作演示: http : //jsfiddle.net/AndyE/WLKAa/

这允许我们将一个参数传递给outerHTML ,它可以是

  • 一个可取消的函数 — function (index, oldOuterHTML) { } — 返回值将成为元素的新 HTML(除非返回false )。
  • 一个字符串,它将被设置来代替每个元素的 HTML。

有关更多信息,请参阅html()的 jQuery 文档。

您还可以使用get (检索与 jQuery 对象匹配的 DOM 元素。)。

例如:

$('div').get(0).outerHTML;//return "<div></div>"

作为扩展方法:

jQuery.fn.outerHTML = function () {
  return this.get().map(function (v) {
    return v.outerHTML
  }).join()
};

或者

jQuery.fn.outerHTML = function () {
  return $.map(this.get(), function (v) {
    return v.outerHTML
  }).join()
};

多选并返回所有匹配元素的外部 html。

$('input').outerHTML()

返回:

'<input id="input1" type="text"><input id="input2" type="text">'

要将完整的 jQuery 插件制作为.outerHTML ,请将以下脚本添加到任何 js 文件并在标题中包含 jQuery 之后:

更新新版本具有更好的控制以及更 jQuery Selector 友好的服务! :)

;(function($) {
    $.extend({
        outerHTML: function() {
            var $ele = arguments[0],
                args = Array.prototype.slice.call(arguments, 1)
            if ($ele && !($ele instanceof jQuery) && (typeof $ele == 'string' || $ele instanceof HTMLCollection || $ele instanceof Array)) $ele = $($ele);
            if ($ele.length) {
                if ($ele.length == 1) return $ele[0].outerHTML;
                else return $.map($("div"), function(ele,i) { return ele.outerHTML; });
            }
            throw new Error("Invalid Selector");
        }
    })
    $.fn.extend({
        outerHTML: function() {
            var args = [this];
            if (arguments.length) for (x in arguments) args.push(arguments[x]);
            return $.outerHTML.apply($, args);
        }
    });
})(jQuery);

这将使您不仅可以获取一个元素的外层HTML,还可以一次获取多个元素的 Array 返回值! 并且可以在两种 jQuery 标准样式中使用,例如:

$.outerHTML($("#eleID")); // will return outerHTML of that element and is 
// same as
$("#eleID").outerHTML();
// or
$.outerHTML("#eleID");
// or
$.outerHTML(document.getElementById("eleID"));

对于多个元素

$("#firstEle, .someElesByClassname, tag").outerHTML();

片段示例:

 console.log('$.outerHTML($("#eleID"))'+"\\t", $.outerHTML($("#eleID"))); console.log('$("#eleID").outerHTML()'+"\\t\\t", $("#eleID").outerHTML()); console.log('$("#firstEle, .someElesByClassname, tag").outerHTML()'+"\\t", $("#firstEle, .someElesByClassname, tag").outerHTML()); var checkThisOut = $("div").outerHTML(); console.log('var checkThisOut = $("div").outerHTML();'+"\\t\\t", checkThisOut); $.each(checkThisOut, function(i, str){ $("div").eq(i).text("My outerHTML Was: " + str); });
 <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script> <script src="https://rawgit.com/JDMcKinstry/ce699e82c7e07d02bae82e642fb4275f/raw/deabd0663adf0d12f389ddc03786468af4033ad2/jQuery.outerHTML.js"></script> <div id="eleID">This will</div> <div id="firstEle">be Replaced</div> <div class="someElesByClassname">At RunTime</div> <h3><tag>Open Console to see results</tag></h3>

你也可以这样做

document.getElementById(id).outerHTML

其中 id 是您要查找的元素的 id

我使用 Jessica 的解决方案(由 Josh 编辑)让 outerHTML 在 Firefox 上工作。 然而,问题是我的代码被破坏了,因为她的解决方案将元素包装到一个 DIV 中。 再添加一行代码就解决了这个问题。

以下代码为您提供了使 DOM 树保持不变的外层 HTML。

$jq.fn.outerHTML = function() {
    if ($jq(this).attr('outerHTML'))
        return $jq(this).attr('outerHTML');
    else
    {
    var content = $jq(this).wrap('<div></div>').parent().html();
        $jq(this).unwrap();
        return content;
    }
}

并像这样使用它: $("#myDiv").outerHTML();

希望有人觉得它有用!

// no cloning necessary    
var x = $('#xxx').wrapAll('<div></div>').parent().html(); 
alert(x);

在这里小提琴: http : //jsfiddle.net/ezmilhouse/Mv76a/

如果场景是动态添加新行,则可以使用以下命令:

var row = $(".myRow").last().clone();
$(".myRow").last().after(row);

.myrow<tr>的类名。 它复制最后一行并将其作为新的最后一行插入。 这也适用于IE7 ,而[0].outerHTML方法不允许在ie7 中赋值

我使用了由 Jessica 更新的 Volomike 的解决方案。 刚刚添加了一个检查以查看元素是否存在,并使其返回空白以防它不存在。

jQuery.fn.outerHTML = function() {
return $(this).length > 0 ? $(this).clone().wrap('<div />').parent().html() : '';
};

当然,像这样使用它:

$('table#buttons').outerHTML();

node.cloneNode() 几乎不像是一个黑客。 您可以克隆节点并将其附加到任何所需的父元素,还可以通过操作单个属性来操作它,而不必例如在其上运行正则表达式,或将其添加到 DOM,然后在后面操作。

也就是说,您还可以遍历元素的属性以构造它的 HTML 字符串表示形式。 如果 jQuery 添加一个,这似乎是任何外层 HTML 函数的实现方式。

这对于 vanilla JavaScript 来说非常简单......

document.querySelector('#selector')

你可以在这里找到一个很好的 .outerHTML() 选项https://github.com/darlesson/jquery-outerhtml

与仅返回元素的 HTML 内容的 .html() 不同,此版本的 .outerHTML() 返回所选元素及其 HTML 内容或将其替换为 .replaceWith() 方法,但不同之处在于允许替换 HTML 由链接。

示例也可以在上面的 URL 中看到。

我做了这个简单的测试,outerHTML 是 tokimon 解决方案(没有克隆),outerHTML2 是 jessica 解决方案(克隆)

console.time("outerHTML");
for(i=0;i<1000;i++)
 {                 
  var html = $("<span style='padding:50px; margin:50px; display:block'><input type='text' title='test' /></span>").outerHTML();
 }                 
console.timeEnd("outerHTML");

console.time("outerHTML2");

 for(i=0;i<1000;i++)
 {                 
   var html = $("<span style='padding:50px; margin:50px; display:block'><input type='text' title='test' /></span>").outerHTML2();
  }                 
  console.timeEnd("outerHTML2");

我的 Chrome (Version 20.0.1132.57 (0)) 浏览器的结果是

外部HTML:81ms
外部HTML2:439ms

但是如果我们使用没有原生outerHTML函数的tokimon解决方案(现在几乎每个浏览器都支持)

我们得到

外部HTML:594ms
外部HTML2:332ms

在现实世界的例子中会有更多的循环和元素,所以完美的组合是

$.fn.outerHTML = function() 
{
  $t = $(this);
  if( "outerHTML" in $t[0] ) return $t[0].outerHTML; 
  else return $t.clone().wrap('<p>').parent().html(); 
}

所以 clone 方法实际上比 wrap/unwrap 方法快
(jQuery 1.7.2)

这是一个非常优化的 jquery 外部 HTML 插件:( http://jsperf.com/outerhtml-vs-jquery-clone-hack/5 => 其他 2 个快速代码片段与某些浏览器(如 FF < 11)不兼容)

(function($) {

  var DIV = document.createElement("div"),
      outerHTML;

  if ('outerHTML' in DIV) {
    outerHTML = function(node) {
      return node.outerHTML;
    };
  } else {
    outerHTML = function(node) {
      var div = DIV.cloneNode();
      div.appendChild(node.cloneNode(true));
      return div.innerHTML;
    };
  }

  $.fn.outerHTML = function() {
    return this.length ? outerHTML(this[0]) : void(0);
  };

})(jQuery);

@Andy E => 我不同意你的看法。 externalHMTL 不需要 getter 和 setter:jQuery 已经给了我们 'replaceWith'...

@mindplay => 你为什么要加入所有的outerHTML? jquery.html 只返回第一个元素的 HTML 内容。

(对不起,没有足够的声望来写评论)

简短而甜蜜。

[].reduce($('.x'), function(i,v) {return i+v.outerHTML}, '')

或者在箭头函数的帮助下更甜蜜的事件

[].reduce.call($('.x'), (i,v) => i+v.outerHTML, '')

或者根本没有 jQuery

[].reduce.call(document.querySelectorAll('.x'), (i,v) => i+v.outerHTML, '')

或者如果您不喜欢这种方法,请检查

$('.x').get().reduce((i,v) => i+v.outerHTML, '')

请注意,Josh 的解决方案仅适用于单个元素。

可以说,“外部”HTML 只有当您只有一个元素时才真正有意义,但在某些情况下,将 HTML 元素列表转换为标记是有意义的。

扩展 Josh 的解决方案,这个解决方案将处理多个元素:

(function($) {
  $.fn.outerHTML = function() {
    var $this = $(this);
    if ($this.length>1)
      return $.map($this, function(el){ return $(el).outerHTML(); }).join('');
    return $this.clone().wrap('<div/>').parent().html();
  }
})(jQuery);

编辑:Josh 解决方案的另一个问题已修复,请参阅上面的评论。

另一个类似的解决方案,添加了临时 DOM 对象的remove()

这对于更改 dom 上的元素非常有用,但不适用于 ie 将 html 字符串传入 jquery 时,如下所示:

$('<div id="foo">Some <span id="blog">content</span></div>').find('#blog').outerHTML();

经过一些操作后,我创建了一个函数,该函数允许上述内容在 ie 中用于 html 字符串:

$.fn.htmlStringOuterHTML = function() {     
    this.parent().find(this).wrap('<div/>');        
    return this.parent().html();
};

$.html = el => $("<div>"+el+"</div>").html().trim();

我在寻找我的问题的答案时遇到了这个问题,即我试图删除一个表格行,然后将其添加回表格的底部(因为我正在动态创建数据行,但想显示一个“添加新记录'底部的类型行)。

我有同样的问题,因为它返回了innerHtml,所以缺少TR标签,它保存了该行的ID,意味着不可能重复这个过程。

我发现的答案是 jquery remove()函数实际上将它删除的元素作为对象返回。 所以,删除并重新添加一行就像这样简单......

var a = $("#trRowToRemove").remove();            
$('#tblMyTable').append(a);  

如果您不是删除对象而是想将其复制到其他地方,请改用clone()函数。

jQuery 插件作为直接获取整个元素 HTML 的速记:

jQuery.fn.outerHTML = function () {
    return jQuery('<div />').append(this.eq(0).clone()).html();
};

并像这样使用它: $(".element").outerHTML();

纯 JavaScript:

var outerHTML = function(node) {
  var div = document.createElement("div");
  div.appendChild(node.cloneNode(true));
  return div.innerHTML;
};
$("#myNode").parent(x).html(); 

其中 'x' 是节点号,从 0 开始作为第一个,如果你想获得一个特定的节点,应该得到你想要的正确节点。 如果你有子节点,你真的应该在你想要的节点上放一个 ID,但是,在那个节点上只是零。 使用这种方法并且没有 'x' 对我来说效果很好。

简单的解决方案。

var myself = $('#div').children().parent();
$("#myTable").parent().html();

也许我没有正确理解您的问题,但这将获得所选元素的父元素的 html。

这就是你追求的吗?

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM