To design the stats feature of Backbone, our Ruby on Rails CMS, we needed to show a stacked bar graph of page views vs unique visitors. I looked around for a sample of how others did stacked bar graphs and came up empty handed. There are plenty of CSS bar graph interpretations, but none of them did stacked bar graphs. So I’ve done it here. Based off Alen Grakalic’s Pure CSS Data Chart.
The Markup
The first thing I do anytime I start HTML/CSS work is code the HTML. It’s a personal preference to make sure it’s all going to look good for screen readers and be as semantic as possible, and since it’s my article we’re going to do the HTML first.
[code lang="html"]<br />
<dl id="csschart"><br />
<dt>Mon</dt><br />
<dd>36</dd><br />
<dd>30</dd><br />
</dl><br />
[/code]
Like Alen Grakalic’s implementation, I used a definition list. I found it to be the most semantic way of presenting data like this. To explain, each day of the week is in a <dt> tag and the data for that day is in a <dd> tag. There are two <dd> tags for each day, one for our page views and one for our unique visitors.
[code lang="html"]<br />
<dt>Mon</dt><br />
<dd class="p36"><span><b>36</b></span></dd><br />
<dd class="sub p30" ><span><b>30</b></span></dd><br />
</dl><br />
[/code]
Each <dd> is given a class that corresponds to the percentage of that bar. p100 is 100% the height of the graph and p0 is 0% the height of the graph. Making 100 classes is a pain and a lot of CSS but it makes it so easy when you’re turning these graphs out dynamically.
The other class to which we’ve added some of the <dd> tags is “sub”. This denotes the stacked bars in the graph that will be put on top of the other <dd>.
Finally, we wrap our data in <b> and <span> tags so we have enough to work with when we’re styling it.
Styling the Graph.
[code lang="css"]<br />
dl#csschart, dl#csschart dt, dl#csschart dd{<br />
margin:0;<br />
padding:0;<br />
}<br />
dl#csschart{<br />
"color: #0000ee;">
Add the Axes.
Ok now you’ll notice we don’t have labels on our axes. So we use some simple unordered lists. One before the cssChart:
[code lang="html"]<br />
<ul class="yAxis"><br />
<li>100</li><br />
<li>90</li><br />
<li>80</li><br />
<li>70</li><br />
<li>60</li><br />
<li>50</li><br />
<li>40</li><br />
<li>30</li><br />
<li>20</li><br />
<li>10</li><br />
</ul></p>
<p>[/code]
and one after the cssChart:
[code lang="html"]<br />
<ul class="xAxis"><br />
<li>Mon</li><br />
<li>Tue</li><br />
<li>Wed</li><br />
<li>Thu</li><br />
<li>Fri</li><br />
<li>Sat</li><br />
<li>Sun</li><br />
</ul></p>
<p>[/code]
Styling the Axes.
[code lang="css"]<br />
ul.xAxis{<br />
margin:0 0 0 27px;<br />
padding:0;<br />
float:left;<br />
clear:left;<br />
display:inline;<br />
px;<br />
}<br />
ul.yAxis{<br />
margin:14px 0 0 0;<br />
padding:0;<br />
display:inline;<br />
float:left;<br />
}<br />
ul.xAxis li{<br />
float:left;<br />
list-style:none;<br />
px;<br />
text-align:center;<br />
}<br />
ul.yAxis li{<br />
list-style:none;<br />
px;<br />
text-align:right;<br />
float:left;<br />
clear:left;<br />
}</p>
<p>[/code]
Styling the axes is really just floating the the y-axis left and using some margins to push it in place. Then you can use some margins to push the li tags to line up with the tick marks of your background image.
Can you describe what advantages something like this has over simply using an off-the-shelf graphing solution (e.g. Google Charts or www.filamentgroup.com/lab/creating_accessible_charts_using_canvas_and_jquery/ )
I suppose there are some advantages (highly customizable, can add links/actions to chart elements), but the downsides would seem to be considerable. Most notably you’re restricted to bar-graph style charts, and even then if you want to vary the style (e.g. horizontal .vs. vertical bars), you’ve got to invent a whole new set of CSS.
In the past when I’ve developed HTML/CSS graph solutions, the result ends up being hard to work with and maintain. I invariably end up needing it to do something other than what I originally intended, and spending hours trying to figure out some CSS “hack” to get it to all render properly.
Well Broofa, I don’t disagree with you that going with Google Charts or some sort of Canvas solution is by far more powerful than doing something with plain CSS/HTML. This however is pretty quick to set up if you know what you’re doing, doesn’t require a learning curve of some other language or framework, and its also very lightweight. If you need to do some pretty hardcore graphing, than by all means add a framework or hook up to Google’s API, but if you need to do just one bar graph, or just bar graphs alone I think its overkill to make extra HTTP requests with Google or add a framework of JS just to make a bar graph.
Using a DL tag for this is improper. If you dont use tags for what they are meant for, you might as well just use tables.
I would make these either all LIs or DIVs.
Nice tutorial, thanks
This sucks. Why does every newbie have to publish his rubbish experiments on the web?
Sorry, but turn off css and you will see that nonsense markup.
Very interesting! I use it on my blog www.ecogiochi.it with games chart
Hi Steve, it does not matter if somebody turn off his css, or even if he turn off his browser. What matters is your users, if they find your charts usefull.
I use this type of graphs for many years on intranet for visualization of production plan, production results, downtime and many others. If you want to see some screenshots and description of intranet applications where bar charts are used, please visit swatelier.info site.
This is great, thanks!
A relatively small quibble: “dl#csschart” is worse than “#csschart” and no more meaningful.
Firefox’s CSS parser will actually slow down on “dl#csschart” versus “#csschart”.
“#id-name” can only refer to one element in the page, so denoting what kind of element #id-name isn’t necessary and such changes also require updating should you decide to use another kind of element at that ID.
The element, man I’ve not seen that for ages and considering you spoke about wanting to use semantic mark-up I found that a big surprise!
Also as you mention screen-readers during the article too and wanting to keep content accessible to them you really shouldn’t be using display: none on content. The majority of screen-readers will not read content set to display: none out. Use position: absolute, left: -99999em instead
Argh – mark-up removed from comments. Of course I was refering to the use of b tags ;>
I’d be inclined to use an ordered list for the axis labels – the order of the list items is critical after all.
Not sure about the use of the DL’s – I’d like to see a scheme which uses a table as the underlying structure – it’d no doubt be a pain to get working in older browsers though. It would solve the problem of ‘CSS off’ though.
<b>? Really, you should be using strong elements instead, as they have a semantical meaning as opposed to the pure-style purpose of b elements.
However, the idea of creating stacked bar graphs using HTML and CSS is a bit redundant – graphs are much better represented using images, and with correct use of alt attributes screen readers will benefit more than they do from this example.
Can someone help me figure out why my cart doesn’t simply items in IE 6/7, but does in Safari and Firefox? (And how to fix it). Thanks.
…Rene
It’s cool
it’s okay
Fantastic piece of tutorial! I am going to add it to my CSS aggregator website.Hope you dont mind!
amazing! Can I use it in my blog?
There is by no means any long run good fortune with this sort of diet. The kid on a regular basis starts by means of fasting (except for for water) under close medical supervision for twenty-four hours. A explanation why to devour vegetables and fruit daily. Early continual kidney disease. If you in finding that an exclusion diet identifies certain foods that make your ibs symptoms worse, they’re often referred to as ’cause meals’ (as a result of they ‘trigger’ the symptoms). Three-day diets move through many different names, including the fax diet, military vitamin, army nutrition, cleveland hospital diet, and lots of others. Such a lot end result are limited, however a few fruit (rather than watermelons and bananas) is permitted so long as it does not produce weight gain
Hello, I’m Chinese, I want to learn some knowledge more with you, if you please contact me.
There are a lot of “<”,you can change it as “<", to make it clear~~~~~
谢谢你的代码 学习了
very good,it’s beautiful!
Thinks!
ssss
realy
very good,it’s beautiful!