jQuery:如何更改标签名称?

jQuery:如何更改标签名称?

例如:

<tr> $1 </tr> 

我需要

 <div> $1 </div> 

我可以

  1. 创buildDOM元素<div>
  2. 将tr内容复制到div
  3. 从dom中删除tr

但是,我可以直接吗?

PS:

  $(tr).get(0).tagName = "div"; 

导致DOMException

您可以使用jQuery的.replaceWith()方法replace任何HTML标记。

例如: http : //jsfiddle.net/JHmaV/

Ref .:。 用。。。来代替

如果你想保留现有的标记,你可以使用这样的代码:

 $('#target').replaceWith('<newTag>' + $('target').html() +'</newTag>') 

不,根据W3C规范是不可能的:“DOMStringtypes的tagName,只读”

http://www.w3.org/TR/DOM-Level-2-Core/core.html

DOM的renameNode()方法在哪里?

今天(2014)没有浏览器了解新的DOM3 renameNode方法 (请参阅W3C )检查是否运行在您的bowser: http : //jsfiddle.net/k2jSm/1/

所以,一个DOM解决scheme是丑陋的,我不明白为什么(?)jQuery没有实施一个解决方法?

纯DOMalgorithm

  1. createElement(new_name)
  2. 将所有内容复制到新元素;
  3. replaceChild()replace旧的新的

是这样的,

 function rename_element(node,name) { var renamed = document.createElement(name); foreach (node.attributes as a) { renamed.setAttribute(a.nodeName, a.nodeValue); } while (node.firstChild) { renamed.appendChild(node.firstChild); } return node.parentNode.replaceChild(renamed, node); } 

…等待审查和jsfiddle …

jQueryalgorithm

@ilpoldoalgorithm是一个很好的起点,

  $from.replaceWith($('<'+newname+'/>').html($from.html())); 

正如其他人评论,它需要一个属性副本…等待通用…

特定于class保留属性 ,请参阅http://jsfiddle.net/cDgpS/

另见https://stackoverflow.com/a/9468280/287948

要保留标签的内部内容,您可以使用访问器.html().replaceWith()

分叉的例子: http : //jsfiddle.net/WVb2Q/1/

上述解决scheme将现有元素从头开始重新创build,并销毁进程中的任何事件绑定。

简短的回答:(失去的属性)

 $("p").wrapInner("<div/>").children(0).unwrap(); 

更长的回答:(副本的属性)

 $("p").each(function (o, elt) { var newElt = $("<div class='p'/>"); Array.prototype.slice.call(elt.attributes).forEach(function(a) { newElt.attr(a.name, a.value); }); $(elt).wrapInner(newElt).children(0).unwrap(); }); 

摆弄嵌套的绑定

从同一时间复制任何绑定将是一件很酷的事情,但获取当前的绑定对我来说并不适用。

你可以去一点基本的。 为我工作。

 var oNode = document.getElementsByTagName('tr')[0]; var inHTML = oNode.innerHTML; oNode.innerHTML = ''; var outHTML = oNode.outerHTML; outHTML = outHTML.replace(/tr/g, 'div'); oNode.outerHTML = outHTML; oNode.innerHTML = inHTML; 

要replace多个标签的内部内容,每个标签都有自己的原始内容,则必须以不同的方式使用.replaceWith().html()

http://jsfiddle.net/kcrca/VYxxG/

JS改变标签名称

 /** * This function replaces the DOM elements's tag name with you desire * Example: * replaceElem('header','ram'); * replaceElem('div.header-one','ram'); */ function replaceElem(targetId, replaceWith){ $(targetId).each(function(){ var attributes = concatHashToString(this.attributes); var replacingStartTag = '<' + replaceWith + attributes +'>'; var replacingEndTag = '</' + replaceWith + '>'; $(this).replaceWith(replacingStartTag + $(this).html() + replacingEndTag); }); } replaceElem('div','span'); /** * This function concats the attributes of old elements */ function concatHashToString(hash){ var emptyStr = ''; $.each(hash, function(index){ emptyStr += ' ' + hash[index].name + '="' + hash[index].value + '"'; }); return emptyStr; } 

相关小提琴在这个链接

简单地改变属性值就不会这样做(正如其他人所说的,一些HTMLElement属性是只读的;也有一些将原型上下文保持为更原始的元素)。 模拟DOM API最接近的是模仿JavaScript中原型inheritance的过程。

通过__proto__对象的原型的“设置”通常是不被接受的。 另外,您可能会考虑为什么您认为您需要首先复制整个DOM元素。 但是在这里:

 // Define this at whatever scope you'll need to access it // Most of these kinds of constructors are attached to the `window` object window.HTMLBookElement = function() { function HTMLBookElement() { var book = document.createElement('book'); book.__proto__ = document.createElement('audio'); return book; } return new HTMLBookElement(); } // Test your new element in a console (I'm assuming you have Chrome) var harryPotter = new HTMLBookElement(); // You should have access to your new `HTMLBookElement` API as well as that // of its prototype chain; since I prototyped `HTMLAudioElement`, you have // some default properties like `volume` and `preload`: console.log(harryPotter); // should log "<book></book>" console.log(harryPotter.volume); // should log "1" console.log(harryPotter.preload); // should log "auto" 

所有DOM元素都以这种方式工作。 例如: <div></div>是由HTMLDivElement生成的,它扩展了HTMLElement ,而HTMLElement又扩展了Element ,后者又扩展了Object

由于replaceWith()不适用于我的元素(可能是因为我在map()使用它),我通过创build一个新元素并根据需要复制属性来完成此操作。

 $items = $('select option').map(function(){ var $source = $(this), $copy = $('<li></li>'), title = $source.text().replace( /this/, 'that' ); $copy .data( 'additional_info' , $source.val() ) .text(title); return $copy; }); $('ul').append($items); 

拿他的话

用Word“如何更改标签名称”的问题? 我会build议这个解决scheme:
如果有意义的话必须逐案决定。

我的例子将“重新命名”所有具有超链接的a-Tags,带有span标签的SMS。 维护所有属性和内容:

 $('a[href^="sms:"]').each(function(){ var $t=$(this); var $new=$($t.wrap('<div>') .parent() .html() .replace(/^\s*<\s*a/g,'<span') .replace(/a\s*>\s*$/g,'span>') ).attr('href', null); $t.unwrap().replaceWith($new); }); 

因为它没有任何意义,有一个带有href属性的span标签,我也删除它。 这样做是防弹的,并与jQuery支持的所有浏览器兼容。 人们尝试将所有属性复制到新元素还有其他方法,但这些方法与所有浏览器都不兼容。

虽然我觉得用这种方法做起来相当昂贵。

jquery插件使“tagName”可编辑:

 (function($){ var $newTag = null; $.fn.tagName = function(newTag){ this.each(function(i, el){ var $el = $(el); $newTag = $("<" + newTag + ">"); // attributes $.each(el.attributes, function(i, attribute){ $newTag.attr(attribute.nodeName, attribute.nodeValue); }); // content $newTag.html($el.html()); $el.replaceWith($newTag); }); return $newTag; }; })(jQuery); 

见: http : //jsfiddle.net/03gcnx9v/3/

还有另一个脚本来改变节点名称

 function switchElement() { $element.each(function (index, oldElement) { let $newElement = $('<' + nodeName + '/>'); _.each($element[0].attributes, function(attribute) { $newElement.attr(attribute.name, attribute.value); }); $element.wrapInner($newElement).children().first().unwrap(); }); } 

http://jsfiddle.net/rc296owo/5/

它会将属性和内部html复制到一个新元素中,然后replace旧元素。

 $(function(){ $('#switch').bind('click', function(){ $('p').each(function(){ $(this).replaceWith($('<div/>').html($(this).html())); }); }); }); 
 p { background-color: red; } div { background-color: yellow; } 
 <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> <p>Hello</p> <p>Hello2</p> <p>Hello3</p> <button id="switch">replace</button>