As the accepted answer have some limitations (like the attributes aren't migrated to the new element), I found a new way to replace tag name without loosing those. But it also have some limitations for example: The events set to the main element will not migrated to the new element. Anyways, I'm providing the function. Let me know if you have any better Idea.
With Pure Javascript:
function replaceTag(element, new_tag) {
let outerHTML = element.outerHTML;
let outerTag = outerHTML
.match(/<([a-zA-Z]*?)( |>)/)[0]
.replaceAll("<", "")
.replaceAll("/", "")
.replaceAll("=", "")
.replaceAll(">", "")
.trim();
let newHTML_pre = outerHTML.replace(outerTag, new_tag);
newHTML_pre = newHTML_pre.slice(0, newHTML_pre.length - outerTag.length - 3);
let newHTML;
if (outerHTML.endsWith('</' + outerTag + '>')) {
newHTML = newHTML_pre + '</' + new_tag + '>';
} else {
newHTML = newHTML_pre;
}
element.outerHTML = newHTML;
}
// let e = document.querySelector('div');
// replaceTag(e, 'img');
With Jquery:
$.fn.replaceTag = function (new_tag) {
return this.each(function () {
let outerHTML = $(this).prop("outerHTML");
let outerTag = outerHTML
.match(/<([a-zA-Z]*?)( |>)/)[0]
.replaceAll("<", "")
.replaceAll("/", "")
.replaceAll("=", "")
.replaceAll(">", "")
.trim();
let newHTML_pre = outerHTML.replace(outerTag, new_tag);
newHTML_pre = newHTML_pre.slice(0, newHTML_pre.length - outerTag.length - 3);
let newHTML;
if (outerHTML.endsWith("</" + outerTag + ">")) {
newHTML = newHTML_pre + "</" + new_tag + ">";
} else {
newHTML = newHTML_pre;
}
$(this).prop("outerHTML", newHTML);
});
};
// $('div').replaceTag('img');
Explanation:
The function replaces the start and end tag of the element's outerHTML with the new tag ignoring the child elements with the same tag name. Sometimes the element doesn't have end tag name like: (<div />
), in that case it just replace the start tag. That's All.
div
won't be a valid element wheretr
is located. – Boxhauldisplay:block
to make atr
act and look like adiv
without actually changing the tag name but you would probably want todisplay:block
ify the innertd
s as well with something liketr,tr>td{display:block}
. – Chronograph