I am rendering dynamically multiple rectangles that have rotate applied to them. What I'm trying to achieve is to put diamond like shapes one below another and isolate the transform attribute. Is it possible?
const svg = d3
.select('#root')
.append('g')
.attr('transform', 'translate(200,200)');
svg.selectAll('.device')
.data([1, 2, 3, 4])
.enter()
.append('rect')
.attr('width', 10)
.attr('height', 10)
.attr('x', 0)
.attr('y', (d, i) => { return i * 10 * Math.sqrt(2); })
.attr('transform', 'rotate(45)')
.attr('fill', '#000');
Here you can find the JSFiddle
Obs. I could resolve this issue by altering the x attribute but I don't want that.
Thank you in advance!
The issue here has nothing to do with D3. It's an SVG specification: the rotate function of the transform attribute rotates the element around the origin (0,0), not around its center.
There are a couple of solutions here. Since you said that you don't want to change the x attribute, the easiest solution is setting the position in the same transform:
.attr('transform', (d, i) => 'translate(0,' + (i * 10 * Math.sqrt(2)) + ') rotate(45)')
//this is the x attribute---------------^ ^----- and this is the y
Here is your code with that change:
const svg = d3
.select('#chart')
.append('g')
.attr('transform', 'translate(200,50)');
svg.selectAll('.device')
.data([1, 2, 3, 4])
.enter()
.append('rect')
.attr('width', 10)
.attr('height', 10)
.attr('transform', (d, i) => 'translate(0,' + (i * 10 * Math.sqrt(2)) + ') rotate(45)')
.attr('fill', '#000');
<script src="https://d3js.org/d3.v4.min.js"></script>
<svg id="chart" width="400" height="200"></svg>
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