jquerylinkedin-apidust.jsclient-side-templating

Repeatedly Render Dust.js Template with New Data


What would be the best way to go about repeatedly rendering a dust template while having it advance in the data file its referencing rather than just repeat from the start each time. For example:

Say I have a list of 100+ people stored as JSON in a variable called data:

{
    "people": [
        {
            "name": "Jerry",
            "age": "17"
        },
        {
            "name": "Darcy",
            "age": "19"
        },
        {
            "name": "Jacob",
            "age": "25"
        },
        ... and so on for 100 or so people
    ]
}

And I have this template.tl file that exports a row of three names/ages:

<div class="row">
    <div>{name} - {age}</div>
    <div>{name} - {age}</div>
    <div>{name} - {age}</div>
</div>

Which I precompile into template.js:

(function(){dust.register("template.tl",body_0);function body_0(chk,ctx){return chk.write("<div class=\"row\"><div>").reference(ctx.get(["name"], false),ctx,"h").write(" - ").reference(ctx.get(["age"], false),ctx,"h").write("</div><div>").reference(ctx.get(["name"], false),ctx,"h").write(" - ").reference(ctx.get(["age"], false),ctx,"h").write("</div><div>").reference(ctx.get(["name"], false),ctx,"h").write(" - ").reference(ctx.get(["age"], false),ctx,"h").write("</div></div>");}return body_0;})();

Then I have an index.html file that looks like:

<html>
    <head>
    ...
    </head>

    <body>
        <div id="people"></div>

        <button id="load-more" type="button">Load More</button>
    </body>

    <script src="js/dust-core.min.js"></script>
    <script src="js/template.js"></script>
</html>

What would be the best way to have it so each time the button is clicked, a row of three people would be appended inside the <div id="people"></div>, and each subsequent click would load the next three / test for the end of the data array (can assume the number of people is always a multiple of three for my needs).


Solution

  • Change template.tl to:

    <div class="row">
        {#.}
            <div>{.name} - {.age}</div>
        {/.}
    </div>
    

    There are 2 benefits to changing the template:


    JavaScript to perform the rendering:

    $('#load-more').on('click', function(){
        var next3 = data.people.splice(0, 3);
    
        if(next3.length == 0){
            return; // Array is empty
        }
    
        dust.render('template.tl', next3, function(err, str){
            if(str){
                $('#people').append(str);
            }
        });
    });
    

    The most important part is data.people.splice(0, 3), this removes 3 elements from the array and returns them - See Array.prototype.splice().

    The rest of the code is just JQuery to add an event listener and insert the rendered template.

    JSFiddle