tags:

views:

139

answers:

7

Hi,

I'm hoping that this isn't too subjective. I feel there is a definitive answer so here goes.

I want to create this html on the fly using JS (no libraries):

<a href="#" id="playButton">Play</a>
<a href="javascript: void(0)" id="muteUnmute">Mute</a>
<div id="progressBarOuter"> 
  <div id="bytesLoaded"></div>
    <div id="progressBar"></div>
</div>
<div id="currentTime">0:00</div>
<div id="totalTime">0:00</div>

using javascript. I know I can do this using createElement etc but it seems extremely long winded to do this for each element. Can anyone suggest a way to do this with more brevity.

I do not have access to a library in this project....so no jquery etc.

+1  A: 

You can concatenate raw HTML strings (being careful to escape text and prevent XSS holes), or you can rewrite jQuery (or something similar)

SLaks
Why was this downvoted?
SLaks
+2  A: 

If you don't need any validation for your syntax (which is what makes createElement() so nice) then you could always default to simply setting the innerHTML property of the element you want to insert your markup inside of.

Personally, I would stick with using createElement(). It is more verbose but there are far less things to worry about that way.

Justin Niessner
A: 

you need this.

Here Be Wolves
The author stated he didn't wish to use any libraries.
ianhales
aah, my bad. didn't notice.
Here Be Wolves
+3  A: 

Shove the entire thing into a JS variable:

var html = '<a href="#" id="playButton">Play</a>';
html += '<a href="javascript: void(0)" id="muteUnmute">Mute</a>';
html += '<div id="progressBarOuter"><div id="bytesLoaded"></div><div id="progressBar"></div></div>';
html += '<div id="currentTime">0:00</div>';
html += '<div id="totalTime">0:00</div>';

Then:

document.getElementById("parentElement").innerHTML = html;

if you want theN:

document.getElementById("totalTime").innerHTML = "5:00";
Ryan Ternier
Mixing code with markup --> :(
Ates Goral
It's not the nicest solution, but given what the conditions were, it was acceptable.
Ryan Ternier
I think I'm going to go with this.
elduderino
+2  A: 

You can use

<script type="text/javascript">
    function appendHTML() {
        var wrapper = document.createElement("div");
        wrapper.innerHTML = '\
<a href="#" id="playButton">Play</a>\
<a href="javascript: void(0)" id="muteUnmute">Mute</a>\
<div id="progressBarOuter"> \
<div id="bytesLoaded"></div>\
    <div id="progressBar"></div>\
</div>\
<div id="currentTime">0:00</div>\
<div id="totalTime">0:00</div>\
';
        document.body.appendChild(wrapper);
    }
</script>
yorick
+5  A: 

Keep your markup separate from your code:

You can embed the HTML snippets that you'll be using as hidden templates inside your HTML page and clone them on demand:

<style type="text/css">
#templates { display: none }
</style>
...
<script type="text/javascript">
var node = document.getElementById("tmp_audio").cloneNode(true);
node.id = ""; // Don't forget :)
// modify node contents with DOM manipulation
container.appendChild(node);
</script>
...
<div id="templates">
    <div id="tmp_audio">
        <a href="#" class="playButton">Play</a>
        <a href="#" class="muteUnmute">Mute</a>
        <div class="progressBarOuter"> 
            <div class="bytesLoaded"></div>
            <div class="progressBar"></div>
        </div>
        <div class="currentTime">0:00</div>
        <div class="totalTime">0:00</div>
    </div>
</div>

Update: Note that I've converted the id attributes in the template to class attributes. This is to avoid having multiple elements on your page with the same ids. You probably don't even need the classes. You can access elements with:

node.getElementsByTagName("div")[4].innerHTML =
    format(data.currentTime);

Alternatively, you can act on the HTML of the template:

<script type="text/javascript">
var tmp = document.getElementById("tmp_audio").innerHTML;
// modify template HTML with token replacement
container.innerHTML += tmp;
</script>
Ates Goral
doing it this way will create multiple elements with the same ID,
Ryan Ternier
@Ryan Ternier: No, it won't. Please note the `node.id = "";` line.
Ates Goral
@Ryan Ternier: Ah I see. You're not talking about the id of the template, but the ids within it. It's just that I copy-pasted the template of the OP. Normally, you wouldn't have ids inside the template. I'll edit my answer.
Ates Goral
I am currently doing it like this but this code is for a plugin so i want to use the script to autommate as many things as possible
elduderino
A: 

If performance is a concern, stay away from innerHTML. You should create the whole object tree using document.createElement() as many times as needed, including for nested elements.

Finally, append it to the document with one statement, not many statements.

In my informal testing over the years, this will give you the best performance (some browsers may differ).

If HTML is ever declared in a variable, it should be simple and for a very specific purpose. Usually, this is not the right approach.

Tim