Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

CSS bar graph - very simple

Tags:

css

charts

I have some very basic code and it works except everything aligns to the top...ideally the bars would align to the bottom. I suppose I could use fixed positioning as the dimensions are squared at 50px by 50px but I'd prefer something a little less "fixed".

      <div style="border: 1px solid #aeaeae; background-color: #eaeaea; width: 50px; height: 50px;">
        <div style="position: relative; bottom: 0; float: left; width: 8px; height: 22px; background-color: #aeaeae; margin: 1px;"></div>
        <div style="position: relative; bottom: 0; float: left; width: 8px; height: 11px; background-color: #aeaeae; margin: 1px;"></div>
        <div style="position: relative; bottom: 0; float: left; width: 8px; height: 6px; background-color: #aeaeae; margin: 1px;"></div>
        <div style="position: relative; bottom: 0; float: left; width: 8px; height: 49px; background-color: #aeaeae; margin: 1px;"></div>
        <div style="position: relative; bottom: 0; float: left; width: 8px; height: 28px; background-color: #aeaeae; margin: 1px;"></div>
      </div>

I don't want to use a library or JS add on. Keeping this light weight is mission critical.

Also I'd prefer the bars were vertical. Any CSS guru care to shed the bit of light I seem to be missing? I've googled and most examples are far to complicated/sophisticated,

like image 331
Alex.Barylski Avatar asked May 24 '12 02:05

Alex.Barylski


2 Answers

First of all, separate your CSS from your HTML. You're repeating too much code when you could just use a bar class for your inner divs.

bottom: 0 doesn't change anything for relatively positioned div.

If you wish to use relative positioning, get rid of float and bottom and use display: inline-block and vertical-align: baseline;. Also, in this case, you need to get rid of any space in the HTML between the inner divs (newline).

Like this (you can see the demo at http://dabblet.com/gist/2779082 ):

HTML

<div class="graph">
        <div style="height: 22px;" class="bar"></div><!--
        --><div style="height: 11px;" class="bar"></div><!--
        --><div style="height: 6px;" class="bar"></div><!--
        --><div style="height: 49px;" class="bar"></div><!--
        --><div style="height: 28px;" class="bar"></div>
</div>

CSS

.graph {
    width: 50px;
    height: 50px;
    border: 1px solid #aeaeae;
    background-color: #eaeaea;
}
.bar {
    width: 8px;
    margin: 1px;
    display: inline-block;
    position: relative;
    background-color: #aeaeae;
    vertical-align: baseline;
}
like image 67
Ana Avatar answered Sep 18 '22 12:09

Ana


I would personally avoid setting xpos explicitly on every element, makes things less maintainable. In some scenarious percentage-basedvalue dumps would be more appropriate too. With that in mind, an imo more scalable and semanticaly correct approach has been mocked up in a fiddle. HTML:

<ul class="graph">
    <li><span style="height:45%"></span></li>
    <li><span style="height:12%"></span></li>
    <!--as many more items as you want !-->
</ul>

and CSS:

.graph {
    border: 1px solid #aeaeae; background-color: #eaeaea;/*"canvas" styling*/
    float:left; /*should be clearfix'd instead, but this is OK for a demo*/
}
.graph li {
    width:8px; height:50px; /*set a bar width and a full height*/
    float:left; /*to have bars "left-aligned"*/
    position:relative; /*needed for the actual bar fill element*/
    margin:2px;
 }
 .graph li+li {
    margin-left:0; /*avoid margin double-up between bars as they don't collapse*/
 }
 .graph span {
    position:absolute;right:0;bottom:0;left:0; /*"bottom-align" the bars,
                                                  widths will be set inline*/
    background-color: #aeaeae;
 }

This also gives you potential to get quite fancy - bars could have content with a negative text indent for semantic value or <span> elements could be abandoned altogether in favor of pseudo-elements.

like image 40
Oleg Avatar answered Sep 22 '22 12:09

Oleg