height should be of fixed size in responsive chart - d3.js

I have a responsive chart, but i want the height to be fixed and only width size should change with change in screen size. Is there a way to do that?
height = 200px;
d3.select(divId).selectAll("svg")
.datum(cData)
.transition().duration(500)
.call(chart).attr("width", width).attr("height", height).attr("viewBox", "0 0 " + width + " " + height);

Just set the width to a percentage value!
Let's say you want the width of the chart to always be 50% of the viewable area...you'd set html to width: 100%, and #chart (or whatever) to width: 50%.

Related

d3.js - Dendrogram display adjusted to the tree diagram

With d3.js I have created d3 dendrograms to visualize hierachicals relations between objects. Dimensions and margins of the graph are defined with fixed height and width values.
var width = 1000,
height = 800,
boxWidth = 150,
boxHeight = 35,
gap = {
width: 50,
height: 12
},
margin = {
top: 16,
right: 16,
bottom: 16,
left: 16
},
svg;
With a few relations, display is ok but with many relations it's doesn't fit, graph is 'cut' and I can't see the entire graph. How to set this width and height properties dynamically and adjusted to the size of the graph ?
An example with a correct display : Codepen
An example with an incorrect display : Codepen
Let's work this out, you need to know the bounding box of your content first and then adjust the svg size. To do that, in this particular case, you only have to look at the boxes or nodes and can ignore the links.
With that in mind you can do the following after populating the Nodes in your renderRelationshipGraph function and return the calculated value:
function renderRelationshipGraph(data) {
// ...
var bbox = Nodes.reduce(function (max, d)
{
var w = d.x + boxWidth;
var h = d.y + boxHeight;
if (w > max[0]) {max[0] = w}
if (h > max[1]) {max[1] = h}
return max
}, [0,0])
return bbox
}
then on the main code change use it to update height and width of the svg:
svg = d3.select("#tree").append("svg")
.attr("width", width)
.attr("height", height);
svg.append("g");
var bbox = renderRelationshipGraph(data);
svg.attr("width", bbox[0])
.attr("height", bbox[1]);
You can add a transition and limit the height but this does what you requested with a really large end result.

Scaling D3 chart inside svg while keeping margins the same width?

Working on rendering charts using D3 that has to scale to different resolutions.
I would like to keep everything except the chart path itself at static size which includes all text, line thickness and margins.
I think I have figured out how to handle everything except the margins and cant find anyone who has the same issue so hopefully someone can help.
I've written a short test script that hopefully explains how I have my margins and everything else setup. The red are margins and the grey rectangle is where I draw my chart. Added a text element to show how I scale texts, line thickness etc.
What I want to achieve is that the margin have a static width as I scale the window. If I scale the svg and make it 100px wider I want the red rectangle to become 100px wider while the red margins stay the same.
I had been thinking about increasing the middle rectangle using the scale variable to have it increase "faster" but trying to use something like transform(scale on the rectangle in the resized() function produced unexpected results.
var margin = {top: 100, right: 150, bottom: 100, left: 150}
var outerWidth = 1600,
outerHeight = 900;
var width = outerWidth - margin.right - margin.left,
height = outerHeight - margin.top - margin.bottom;
svg = d3.select(".plot-div").append("svg")
.attr("class", "plot-svg")
.style("background-color", "red")
.attr("width", "100%")
.attr("viewBox", "0 0 " + outerWidth + " " + outerHeight);
g = svg.append("g")
.attr("class", "plot-space")
.attr("transform", "translate(" + margin.left + "," + margin.top + ")")
.append("rect")
.attr("width", width)
.attr("height", height)
.attr("fill", "grey");
text = d3.select(".plot-space").append("text")
.text("Text with the background")
.attr("y", 50)
.attr("x", 50)
.attr("font-size", 16)
.attr("font-family", "monospace")
.attr("fill", "white");
window.addEventListener("resize", resized);
function resized(){
var current_width = svg.node().getBoundingClientRect().width;
var scale = outerWidth / current_width;
text.attr("transform", "scale(" + scale + " " + scale + ")");
}
resized();
jsfiddle for you to play around with.
https://jsfiddle.net/2tuompye/4/

d3 area graph going out of bounds

I am struggling to keep the area graph inbounds for a particular set of data. I am not able to figure out what exactly is making it go out of range
var xRange = d3.scale.linear().range([MARGINS.left, WIDTH - MARGINS.right]).domain([0, numberOfDays + 1]),
yRange = d3.scale.linear().range([HEIGHT - MARGINS.top, MARGINS.bottom]).domain([_.min(areaData), _.max(areaData)]);
js fiddle here
https://jsfiddle.net/sahils/o7df3tyn/20/
Its due to you setting them exactly so these lines :
<svg id="visualisation" width="1200" height="400"></svg>
And
WIDTH = 1000,
HEIGHT = 400,
Rather than this just use window size :
var WIDTH = window.innerWidth,
HEIGHT = window.innerHeight,
vis = d3.select('#visualisation').attr('width', WIDTH).attr('height', HEIGHT)
And remove the styling from your html. Updated fiddle : https://jsfiddle.net/thatOneGuy/o7df3tyn/23/

how to enforce some spacing between the elements of 'addCategoryAxis'

My goal is to make a bar chart that demonstrates the number of jobs advertised in particular locations.
I'm using this code, it draws on d3 and also dimple:
<script type="text/javascript">
function draw(data) {
/*
D3.js setup code
*/
"use strict";
var margin = 75,
width = 1400 - margin,
height = 600 - margin;
var svg = d3.select("body")
.append("svg")
.attr("width", width + margin)
.attr("height", height + margin)
.append('g')
.attr('class','chart');
/*
Dimple.js Chart construction code
*/
var myChart = new dimple.chart(svg, data);
myChart.addCategoryAxis("x", "Location");
myChart.addMeasureAxis("y", "Jobs");
myChart.addSeries(null, dimple.plot.bar);
myChart.draw();
};
</script>
It more or less works, but the thing is- the result is pretty useless because the X axis is so crowded that each individual location is essentially invisible.
Is there a way to enforce some reasonable amount of spacing there so that the different locations remain legible in such a way that it can withstand more records being added at a later date- so- with some kind of dynamism.
Ok, so- on the advice of #thisOneGuy I started playing around with increasing the width, and it worked.
At first I tried to increase the width too much and the chart just disappeared (if anyone knows why that happened I would be interested to hear about it in the comments perhaps)
from width = 1400 - margin, to width = 14000 - margin, it disappears
but width = 9000 - margin, was ok.
you can find the result here

How to fix the height of each bar on a rowChart?

I have a rowChart that can have more or less bars based on what you filter on other graphs.
The problem is that if I set the height of the graph to e.g. 500, if I have 50 bars they will be 10px height but if I have only one, it will be 500px
var graph = dc.rowChart (".graph")
.margins({top: 0, right: 10, bottom: 20, left: 10})
.height(300)
.width(200)
.gap(0)
.x(d3.scale.ordinal())
.elasticX(true)
.ordering(function(d){return -d.value})
.dimension(dim)
.group(filteredGroup);
The group will return the top 10, but if you filter (using other graphs, you might have as low as a single item. In that case, that bar is 300px height and it looks not good (and in general, having the height change that much is not pleasant IMO).
Is there a way to leave the height of the graph flexible but the height of each bar fixed?
So to say that each bar has a height of 30, but the height of the graph is going to adjust from 30 to 300.
According to the latest documentation for DC row charts:
.fixedBarHeight([height])
Get or set the fixed bar height. Default is [false] which will
auto-scale bars. For example, if you want to fix the height for a
specific number of bars (useful in TopN charts) you could fix height
as follows (where count = total number of bars in your TopN and gap is
your vertical gap space).
Example:
var chartheight = 500;
var gap = 5;
var count = 20;
var spaceForScales = 70;
c.fixedBarHeight((chartheight - (count + 1) * gap - spaceForScales) / count);

Resources