I have a Handlebar template i want to include a svg graph generated from d3 into that template.Graph should be inside the template
D3 Graph
var dataset = [1200,3000,3200];
// dataset will change dynamically.
<script type="text/javascript">
var w = 154;
var h = 42;
var rect_1_h = 5;
var rect_2_h = rect_1_h * 2;
var rect_2_w = rect_1_h/2;
var rect_1_color = "#A1C9D9";
var rect_2_color = "#999999";
var text_color = "#555555";
var font_size = 18;
var font_family = "Segoe UI"
var dataset = [1200,3000,3200];
/*------controller----*/
var xScale = d3.scale.linear().domain([dataset[0],dataset[2]])
.range([0,w]);
var svg = d3.select("body").append("svg").attr("width",w).attr("height",h);
var rect1 = svg.append("rect").attr("x",0).attr("y",3*h/4).attr("width",w).attr("height",rect_1_h)
.style("fill",rect_1_color);
var rect2 = svg.append("rect").attr("x",xScale(dataset[1])).attr("y",3*h/4-rect_1_h/2).attr("width",rect_2_w)
.attr("height",rect_2_h).style("fill",rect_2_color);
//var texts = svg.selectAll("text").data(dataset).enter().append("text").text(function(d){ return d; }).attr("fill","red").attr("x",function(d,i){ return i*50 }).attr("y",30)
var text1 = svg.append("text").attr("x",2).attr("y",h/3+2).text(dataset[0]).style("fill",text_color)
.attr("font-size",font_size).attr("font-family",font_family);
var text2 = svg.append("text").attr("x",w-42).attr("y",h/3+2).text(dataset[2]).style("fill",text_color)
.attr("font-size",font_size).attr("font-family",font_family);
</script>
Handlebar template
<script id="datatemplate" type="text/x-handlebars-template">
{{#each objects}}
<tr>
<td>{{lp}}<span class="text1">{{lp2}}</span></td>
<td>{{dc}}<span class="text1">{{dc2}}</span></td>
<td>{{lp}}<span class="text1">{{lp2}}</span></td>
</tr>
{{/each}}
</script>
If there should be only one instance of the graph inside the template, then all you need to do is tell d3 to append the svg element inside the <script id="datatemplate">
tag instead of the body.
var svg = d3.select("#datatemplate").append("svg").attr("width",w).attr("height",h);
If, on the other hand, you would like your template to generate a d3 graph each time it is called, I don't think this is the proper way of doing things. Since d3 binds data to DOM elements and Handlebars generates HTML strings from data structures.
You could wrap your graph code inside a closure to which you pass your data and element you wish to bind to and then generate a new instance of the graph from a Handlebars helper:
function graphic( dataset, element ) {
var w = 154;
var h = 42;
var rect_1_h = 5;
var rect_2_h = rect_1_h * 2;
var rect_2_w = rect_1_h/2;
var rect_1_color = "#A1C9D9";
var rect_2_color = "#999999";
var text_color = "#555555";
var font_size = 18;
var font_family = "Segoe UI";
/*------controller----*/
var xScale = d3.scale.linear().domain([dataset[0],dataset[2]])
.range([0,w]);
var svg = d3.select( element ).append("svg").attr("width",w).attr("height",h);
var rect1 = svg.append("rect").attr("x",0).attr("y",3*h/4).attr("width",w).attr("height",rect_1_h)
.style("fill",rect_1_color);
var rect2 = svg.append("rect").attr("x",xScale(dataset[1])).attr("y",3*h/4-rect_1_h/2).attr("width",rect_2_w)
.attr("height",rect_2_h).style("fill",rect_2_color);
//var texts = svg.selectAll("text").data(dataset).enter().append("text").text(function(d){ return d; }).attr("fill","red").attr("x",function(d,i){ return i*50 }).attr("y",30)
var text1 = svg.append("text").attr("x",2).attr("y",h/3+2).text(dataset[0]).style("fill",text_color)
.attr("font-size",font_size).attr("font-family",font_family);
var text2 = svg.append("text").attr("x",w-42).attr("y",h/3+2).text(dataset[2]).style("fill",text_color)
.attr("font-size",font_size).attr("font-family",font_family);
return svg;
};
Handlebars.registerHelper('graphics', function( dataset, id ) {
graphic( dataset, '#' + id );
});
And then in your template:
<script id="datatemplate" type="text/x-handlebars-template">
{{#each objects}}
<tr>
<td>{{lp}}<span class="text1">{{lp2}}</span></td>
<td>{{dc}}<span class="text1">{{dc2}}</span></td>
<td>{{lp}}<span class="text1">{{lp2}}</span></td>
</tr>
{{/each}}
<div id={{ id }}></div>
{{graphics dataset id}}
</script>
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With