Supposed I have a node that looks like this
<a>
<span class="glyphicons glyphicons-collapse"></span>Collapse All
</a>
And I want to toggle it to this
<a>
<span class="glyphicons glyphicons-expand"></span>Expand All
</a>
If I use innerHTML
or innerText
or textContent
it just replaces the text. My first pass at a solution is
function toggleLastTextNode(element, textWhenTrue, textWhenFalse, value) {
element.removeChild(obj.childNodes[1]);
element.insertAdjacentHTML("beforeend", value ? textWhenTrue: textWhenFalse);
}
As I know where the text is, it's always the obj.childNodes[1]
so I just remove it and replace it. The function call would be something like this
toggleLastTextNode(element,"Expand","Collapse",true)
With the current HTML is there a better way to do this? I want to avoid innerHTML if I can.
Supposed I have a node that looks like this
<a>
<span class="glyphicons glyphicons-collapse"></span>Collapse All
</a>
And I want to toggle it to this
<a>
<span class="glyphicons glyphicons-expand"></span>Expand All
</a>
If I use innerHTML
or innerText
or textContent
it just replaces the text. My first pass at a solution is
function toggleLastTextNode(element, textWhenTrue, textWhenFalse, value) {
element.removeChild(obj.childNodes[1]);
element.insertAdjacentHTML("beforeend", value ? textWhenTrue: textWhenFalse);
}
As I know where the text is, it's always the obj.childNodes[1]
so I just remove it and replace it. The function call would be something like this
toggleLastTextNode(element,"Expand","Collapse",true)
With the current HTML is there a better way to do this? I want to avoid innerHTML if I can.
Share Improve this question edited May 6, 2015 at 12:32 Matt McCabe asked May 6, 2015 at 12:22 Matt McCabeMatt McCabe 3,4762 gold badges24 silver badges30 bronze badges 3-
If you're not dealing with several languages, a CSS pseudo-element
::before
or::after
might also do the trick, leaving that semantically useless text out of your HTML – Laurent S. Commented May 6, 2015 at 12:26 - Thanks for the tip that looks like a nicer solution, I guess something like a css3 toggle switch? – Matt McCabe Commented May 6, 2015 at 12:39
- I made it an answer as an alternative. Working through the classes has the advantage of letting you switch text and image/whatever style at the same time, while the other way you need to address those changes in several instructions. I made it in jQuery for quick response, but it can also be done in vanillaJS – Laurent S. Commented May 6, 2015 at 12:44
3 Answers
Reset to default 6How about
document.getElementById('elementid').firstChild.nodeValue = new_text;
innerHTML has side effects (like disconnecting existing DOM nodes and rerendering that might be heavy).
Nowadays when I'm confronted with this kind of functionality I always try to look at semantic, removing everything which is not content. In this case, you could leave the text in the CSS as it is kinda part of the UX/UI rather than content (a screen reader shouldn't "read" this for example, Google search bot neither, it can't do anything useful with that content). In your case, not changing the HTML (that might also probably be shortened, I e to a solution like this :
HTML (almost same as yours, added href
attribute) :
<a href="#">
<span class="glyphicons glyphicons-collapse"></span>
</a>
CSS :
.glyphicons-collapse::after{content: 'Collapse All'}
.glyphicons-expand::after{content: 'Expand All'}
JS (jquery) :
$('a').on('click','.glyphicons-collapse',function(e){
e.preventDefault();
$(this).removeClass('glyphicons-collapse');
$(this).addClass('glyphicons-expand');
});
$('a').on('click','.glyphicons-expand',function(e){
e.preventDefault();
$(this).removeClass('glyphicons-expand');
$(this).addClass('glyphicons-collapse');
});
And the fiddle with all that in it
define your html content with id
<a id="glyphicons">
<span class="glyphicons glyphicons-collapse"></span>Collapse All
</a>
then toggleExpandCollapse()
var toggleExpandCollapse = function () {
var oElements = document.getElementById('glyphicons').childNodes;
if (oElements[1].className === "glyphicons glyphicons-collapse") {
oElements.childNodes[2].nodeValue = "Expand All";
oElements[1].className = "glyphicons glyphicons-expand"
} else {
oElements.childNodes[2].nodeValue = "Collapse All";
oElements[1].className = "glyphicons glyphicons-collapse"
}
}