Reputation: 12394
I am creating a div
container which I then fill with a svg
var someContainer = d3.select("#abc")
.append("div")
.classed("svg-container", true)
.append("svg")
.attr("preserveAspectRatio", "xMinYMin meet")
.attr("viewBox","0 0 400 100")
.classed("svg-content-responsive", true)
.selectAll("circle")
.data(someScale.range());
I then append my data to it
someContainer.remove();
someContainer.enter()
.append("circle")
.attr("x", function (d, i) {
return i * 2;
})
.attr("y", 5)
.attr("height", 15)
....;
However, whenever I update the content of the svg
, i.e. append new circles, a completely new div-container
and svg-container
gets created. That leaves me with the old data visually staying in its place and right on the bottom (meaning, 100px further down) there is the new data. Its basically a visual copy, but with the new data... Whenever I udpate my data, a new coy gets replaced under the old one, leaving me with n graphics.
Here is the css
that styles the relative container and makes sure, it scales when the window size is changed. Source: Resize svg when window is resized in d3.js */
.svg-container {
display: inline-block;
position: relative;
width: 100%;
padding-bottom: 50%; /* aspect ratio */
vertical-align: top;
overflow: hidden;
}
.svg-content-responsive {
display: inline-block;
position: absolute;
top: 10px;
left: 0;
}
Any ideas what I am doing wrong?
Upvotes: 4
Views: 4154
Reputation: 12394
The problem is that each time the data gets updated, a new div
gets created.
var someContainer = d3.select("#abc")
.append("div")
.classed("svg-container", true)
...
In order to update the data, the div
needs to be replaced instead of creating a new div
each time the data changes.
That can be done by adding this line
d3.select(".svg-container").remove();
above the var someContainer = d3.select...
Upvotes: 2
Reputation: 555
If you just need to delete all the old circles you can do it as follows:
someContainer.selectAll("circle").remove()
And then add new circles by data -> enter -> append sequence.
someContainer.selectAll("circle")
.data(new_circle_data)
.enter()
.append("circle")
.attr("x", function (d, i) {
return i * 2;
})
.attr("y", 5)
.attr("height", 15)
....;
If you only want to delete some of the existing circles and keep the others you can use the general update pattern. You need to do something like this:
var circleUpdate = someContainer.selectAll("circle")
.data(new_circle_data)
circleUpdate.enter().append("circle")
.attr("x", function (d, i) {
return i * 2;
})
.attr("y", 5)
.attr("height", 15)
....;
circleUpdate.exit().remove()
Upvotes: 2