Reputation: 282885
What's the easiest way to turn an <a>
into <span>
keeping all the attributes and content? (except for perhaps the href).
.replaceWith()
replaces the whole shebang.
Upvotes: 3
Views: 1346
Reputation: 26228
Combine jQuery's replaceWith() and html() and copy attributes iteratively. Given your anchor tag has id #anchor
:
$('#anchor').replaceWith(function() {
var span = $('<span/>');
$.each(this.attributes, function(){
span.attr(this.name, this.value);
});
return span.html($(this).html());
});
See updated jsFiddle for an example.
Upvotes: 1
Reputation: 91497
You can iterate an element's attributes using the attributes
property. You can copy an attribute using attribute.cloneNode(true)
. You can add that cloned attribute to another element's attributes collection with element.attributes.setNamedItem(attribute)
.
Here's a quick plugin that does it:
$.fn.cloneTo = function (target) {
// copies the attributes, html, and event handlers of the first element to each of
// the elements in the provided jQuery object or that match the provided selector
if (!target || !target.jquery) {
target = $(target);
}
if (this.length) {
$.each(this[0].attributes, function(i, attr) {
target.each(function(){
this.attributes.setNamedItem(attr.cloneNode(true));
});
});
$.each(this.data("events"), function(evt, handlers){
$.each(handlers, function(i, handler){
target.bind(evt, handler);
});
});
target.empty().append(this.contents());
}
return this;
};
Use it like this:
var span = $("<span>");
$("#myLink").cloneTo(span).replaceWith(span);
Working demo: http://jsfiddle.net/gLqZJ/2
Edit: Updated above to copy event handlers and to keep the descendent nodes untouched, rather than duplicating the HTML.
Upvotes: 3
Reputation: 664548
How about
$element.html(function(html) {
return html.replace(/<(\/?)a/gi, "<$1span"); // string manipulation might be faster, but you get the concept
});
That would save the attributes and content, but not any data and event handlers. If you need those for the descendants, you should remove the child nodes and append them to the new span.
EDIT: Sorry, I'm not that familiar with jQuery. The .html()
method changes the innerHTML, not including the node itself. The function should be something like:
$element(s).each(function() {
var l = this.tagName.length + 1;
this.outerHTML = "<span"+this.outerHTML.slice(l, -l)+"span>";
});
Upvotes: 2