Compared with HTML elements, more graphics can be drawn using SVG. This paper attempts to combine d3.js with SVG.
Since I'm also the first time to use SVG, I'm mainly based on the order of this blog. Let's Make a Bar Chart, II
Static SVG usage
Hand SVG
<style> .chart rect { fill: steelblue; } .chart text { fill: white; font: 10px sans-serif; text-anchor: end; } </style> <svg class="chart" width="420" height="120"> <g transform="translate(0,0)"> <rect width="40" height="19"></rect> <text x="37" y="9.5" dy=".35em">4</text> </g> <g transform="translate(0,20)"> <rect width="80" height="19"></rect> <text x="77" y="9.5" dy=".35em">8</text> </g> <g transform="translate(0,40)"> <rect width="150" height="19"></rect> <text x="147" y="9.5" dy=".35em">15</text> </g> <g transform="translate(0,60)"> <rect width="160" height="19"></rect> <text x="157" y="9.5" dy=".35em">16</text> </g> <g transform="translate(0,80)"> <rect width="230" height="19"></rect> <text x="227" y="9.5" dy=".35em">23</text> </g> <g transform="translate(0,100)"> <rect width="420" height="19"></rect> <text x="417" y="9.5" dy=".35em">42</text> </g> </svg>
g element: Container for composing objects, and transformations added to g element apply to all child elements
rect and text have nothing to say
At the same time, there is a confusing point in SVG: which styles must be written in attributes (such as rect width) and which styles can be represented by styles (such as fill, of course, they can also be written in attributes, but it is not clear why the priority is lower than that given by classes). A better way to remember is that shape geometry (such as rect width) is written in attributes, and modifying classes (such as fill) can be represented by style.
d3 generates SVG
Post code first, CSS unchanged
let data = [4, 8, 15, 16, 23, 42]; let width = 420, barHeight = 20; let x = d3.scaleLinear() .domain([0, d3.max(data)]) .range([0, width]); let chart = d3.select('.chart') .attr('width', width) .attr('height', barHeight * data.length); let bar = chart.selectAll('g') //Data is bound to g .data(data) .enter().append('g') .attr('transform', (d, i) => { return 'translate(0,' + i * barHeight + ')'}); bar.append('rect') .attr('width', d => x(d)) .attr('height', barHeight - 1); bar.append('text') .attr('x', d => x(d) - 3) //Character x-axis position .attr('y', barHeight/2) //Character y axis position .attr('dy', '.35em') //Relative position of characters .text(d => d);
In fact, the difference is not very much. It's just that SVG is used and data is bound to g without additional data binding.
Loading data
d3.tsv() can be used to load and parse data in TSV format
summary
This paper mainly talks about the use of svg, but the core idea remains unchanged.