i have a fiddle of a bar that I am working on. I needed it to update dynamically. the problem I am having is the x axis exit and call for when the bar is re drawn. the title on the x-axis is not removed when an array item is removed.
bars.exit()
.transition()
.duration(1000)
.attr("width", 0)
.remove();
d3.transition(svg).select(".x.axis")
.transition()
.duration(1000)
.call(d3.axisBottom(x));
my bar
Since you are selecting by class, it's a good idea setting the class when drawing the axis:
svg.append("g")
.attr("class", "x axis")//set the class here
.attr("transform", "translate(0," + height + ")")
.call(d3.axisBottom(x));
Here is your updated fiddle with that change: https://jsfiddle.net/3mkd3njj/
Related
I'd like to make only the x-axis labels disappear. Currently, I have the following code, but it makes the entire x-axis disappear, and I'd like to keep the horizontal line.
Is there a way to just target the ticks and the text alone?
// Make x-axis
let xAxis = d3.axisBottom(scaleX);
svg.append("g")
.attr("class", "axis")
.attr("transform", "translate(0," + height + ")")
.attr("opacity", 0.7)
.call(xAxis);
// Target x-axis; but this targets the entire axis
let setXAxisOpacity = (opacity, duration=120) => {
d3.select(".axis")
.transition()
.duration(duration)
.ease(d3.easeLinear)
.style("opacity", opacity)
}
you need to target the text and line parts of the axis
d3.select('.axis').selectAll('text')
.transition()
.duration(duration)
.ease(d3.easeLinear)
.style("opacity", opacity);
d3.select('.axis').selectAll('line')
.transition()
.duration(duration)
.ease(d3.easeLinear)
.style("opacity", opacity);
I have a time-series d3.js chart which I can't seem to get lined up properly. Initially I create the x-axis with:
var x_domain = d3.extent(active_data, function(d) { return d.date; })
var x = d3.time.scale()
.domain(x_domain)
.range([bar_width/2, width-bar_width/2]); // stop bars going outside chart
var date_format = d3.time.format("%b %y");
var xAxis = d3.svg.axis()
.orient("bottom")
.scale(x)
.ticks(8)
.tickFormat(date_format);
// create the xAxis
svg.append("g")
.attr("class", "x axis")
.attr("transform", "translate(0," + height + ")")
.call(xAxis)
.selectAll("text")
.style("text-anchor", "end")
.attr("dx", "-.8em")
.attr("dy", "-.55em")
.attr("transform", "rotate(-90)");
svg.selectAll(".x text") // some legacy code I had lying around
.attr("transform", function(d) {
return "translate(" + this.getBBox().height*3 + "," + this.getBBox().height + ")rotate(0)";
and then I update later on when user selects a date range. "active_data" is updated with the actual values/dates that will show from my total data before this update.
function update_chart(start){
/*...update active_data and other stuff...*/
x.domain(d3.extent(active_data, function(d){return d.date;}))
.range([bar_width/2, width-bar_width/2]);
/*...*/
var svg = d3.select("body").transition().duration(500);
svg.select(".x.axis").call(xAxis);
}
There's a lot more going on, but those are the related bits that I'm having trouble with. I've tried everything I can think of, searched online and I just don't understand what I'm doing wrong. It produces the following sort of problem:
d3 time scale some ticks on second line
You can see the dates go onto the second line. On some charts, when I update to the lowest or the maximum date, it draws it correctly, then draws all of them correctly afterwards. On another chart, it does this:
ticks all over each other
On this second one, I don't change the .ticks(8), so I don't know why it does that. Any insight would be greatly appreciated.
Ok I figured it out, and there were a couple bugs.
Then, the following was giving some dates a special x location, but not all of them:
// create the xAxis
svg.append("g")
.attr("class", "x axis")
.attr("transform", "translate(0," + height + ")")
.call(xAxis)
.selectAll("text")
.style("text-anchor", "end")
.attr("dx", "-.8em")
.attr("dy", "-.55em")
.attr("transform", "rotate(-90)");
I changed it to:
// create the xAxis
svg.append("g")
.attr("class", "x axis")
.attr("transform", "translate(0," + height + ")")
.call(xAxis);
and let the update do all the work (let D3 figure it out). The date was now in the right spot, except it was vertical instead of horizontal. I fixed that by removing this:
svg.selectAll(".x text") // some legacy code I had lying around
.attr("transform", function(d) {
return "translate(" + this.getBBox().height*3 + "," + this.getBBox().height + ")rotate(0)";
And it works properly!
I want zoom + brush on a bar chart. I was able to implement zooming ok: demo here, but I found out that after zooming, when you mouse down to drag, the bar chart moves. I don't want the bar chart to move on mouse drag. I want the bar chart to stay in its original place and I want to use the mouse drag for brushing. The bar chart could probably scroll left and right, but it should not be dragged left and right.
How do I make the bar chart stay in its original place?
My code snippet is below. Full script here (134 lines)
var zoom = d3.behavior.zoom()
.x(x)
.scaleExtent([0.8, 10])
.on("zoom", zoomed);
function zoomed() {
// scale x axis
svg.select(".x.axis").call(xAxis);
// scale the bars
var width_scaled = columnwidth * d3.event.scale;
svg.selectAll(".bargroup rect")
.attr("x", function(d) {return x(d.date) - width_scaled/2;})
.attr("width", width_scaled);
}
var brush = d3.svg.brush()
.x(x)
.on("brush", brushed);
function brushed() {
//console.log(brush.extent());
}
var svg = d3.select("#timeline").append("svg")
.attr("width", width + margin.left + margin.right)
.attr("height", height + margin.top + margin.bottom)
.append("g")
.attr("transform", "translate(" + margin.left + "," + margin.top + ")")
.call(zoom);
svg.append("g")
.attr("class", "x brush")
.call(brush)
.selectAll("rect")
.attr("y", -6)
.attr("height", height + 7);
Any thoughts on why the text is missing for the first rectangle yet others are all fine?
http://jsfiddle.net/sjp700/bhwpu/
vis = d3.select("#chart")
.append('svg')
.attr('width', width + margin.right + margin.left)
.attr('height', height + margin.top + margin.bottom)
.style("fill", "pink")
.attr('class', 'chart');
vis.append("g") // container element
.attr("class", "x axis") // so we can style it with CSS
.attr("transform", "translate(0," + height + ")") // move into position
.call(xAxis); // add to the visualisation
//add in the y axis
vis.append("g") // container element
.attr("class", "y axis") // so we can style it with CSS
.call(yAxis); // add to the visualisation
I am trying to plot a customized yAxis using D3.js. My ideal result should be like this: JSFiddle.
But I haven't found the way to export the SVG image together with CSS styles. So I would like to move the styles to the SVG elements:
var yNode = svg.append("g")
.style("fill", "none")
.style("stroke", "#000")
.attr("transform", "translate(" + left + ",0)")
.attr("class", "axis")
.call(yAxis);
yNode.selectAll('text')
.style('font-size', '11px')
.style('font-family', 'Lucida Console');
The code is here: JSFiddle.
All the styles are the same. But somehow the yAxis label of the later one becomes blur and bold. How to fix it? Thanks.
Here it is : JsFiddle
You selected the whole axis dom element and applied the fill: none and stroke: black to it. The axis contains both: the path and the text, and both are going to be affected by the stroke. That's why your text is stroked.
So I commented out the fill & stroke here
var yNode = svg.append("g")
//.style("fill", "none")
//.style("stroke", "#000")
.attr("transform", "translate(" + left + ",0)")
//.attr("class", "axis")
.call(yAxis);
Selected the path and added the fill and stroke styles
yNode.select('path')
.style("fill", "none")
.style("stroke", "#000");