我有一个Handlebar模板我希望将d3生成的svg图包含到该模板中。图形应该在模板内
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>
车把模板
<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>
答案 0 :(得分:5)
如果模板中只有一个图形实例,那么您需要做的就是告诉d3将svg元素附加到<script id="datatemplate">
标记而不是正文中。
var svg = d3.select("#datatemplate").append("svg").attr("width",w).attr("height",h);
另一方面,如果您希望模板在每次调用时生成d3图形,我认为这不是正确的做事方式。由于d3将数据绑定到DOM元素,Handlebars从数据结构生成HTML字符串。
您可以将图形代码包装在一个闭包中,您将要绑定的数据和元素传递给该闭包,然后从Handlebars帮助程序生成图形的新实例:
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 );
});
然后在你的模板中:
<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>