Reputation: 48
I have to work on a visualization script written in javascript and svg using d3.
Now I am faced eith the different coordinates systems.
Does d3 or svg offer a way to setup a canvas with a transformation to adopt the math model, or shall I just do a coordiante conversion in code?
Upvotes: 1
Views: 171
Reputation: 102188
There are several different solutions, from the hacky transform = "scale(1,-1)"
to pure JavaScript functions for converting the coordinates.
However, the simplest idiomatic D3 solution is using a scale. For instance, a scale like this...
const scale = d3.scaleLinear()
.domain([0, height])
.range([height, 0])
... will quite easily invert the SVG top-bottom vertical axis, to the more common bottom-up math axis.
Here is a demo. First the normal code, plotting some circles with 0, 0
, 2, 2
, 4, 4
etc. as the data :
const data = d3.range(100).map((d, i) => ({
x: i * 2,
y: d * 2
}));
const svg = d3.select("svg");
const circles = svg.selectAll(null)
.data(data)
.enter()
.append("circle")
.attr("r", 1)
.attr("cx", d => d.x)
.attr("cy", d => d.y)
svg {
background-color: lavender;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/5.7.0/d3.min.js"></script>
<svg></svg>
Now the same code, but using a scale for inverting the vertical coordinates:
const data = d3.range(100).map((d, i) => ({
x: i * 2,
y: d * 2
}));
const scale = d3.scaleLinear()
.domain([0, 150])
.range([150, 0]);
const svg = d3.select("svg");
const circles = svg.selectAll(null)
.data(data)
.enter()
.append("circle")
.attr("r", 1)
.attr("cx", d => d.x)
.attr("cy", d => scale(d.y))
svg {
background-color: lavender;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/5.7.0/d3.min.js"></script>
<svg></svg>
Upvotes: 1