HOWTO: Use CSS3 transitions to save space
- Introduction
- The necessary HTML
- The CSS to define the sizes and transitions
- The RGraph libraries and code
- A downloadable demo
Introduction
What do you do when you have a finite and small
amount of space that
you can use but need to squeeze multiple charts into
it? CSS3 transitions
to the rescue! The example code below shows you how you
can adjust the canvas
tag's width
and height
so that you can fit nine
canvas
tags into the same space
that a regular (or two) full-size canvas
tags would take up.
The canvas
tags then have some css
applied to them
that makes them respond to them getting focus, become
larger, and by using
a css
transition
, the expansion is animated.
I'll stress that the effect shown here does not use javascript
!
The trigger
for the effect is when the canvas
gains focus - in this case, that means
that you can
click on them. Tabbing to the canvas
tags also works because that also gives
the elements
focus.
Being css
, the transition
effect is smooth and jerk-free and css
is also
used to
remove the focus outline. The code to achieve this effect is shown below.
The necessary HTML
These are the canvas
tags that the charts are drawn on. The width
and
height
attributes on the tags stipulate the full width and height of
the canvas
tags (ie when they're enlarged). Though the canvas
tags
are set by the css
:focus
pseudo-selector to be 90% of this. It's also
necessary to add the tabindex
attribute because without this the
tags cannot be tabbed to and thus will not get focus.
<div id="container"> <canvas id="cvs1" width="900" height="375" tabindex="1">[No canvas support]</canvas> <canvas id="cvs2" width="900" height="375" tabindex="1">[No canvas support]</canvas> <canvas id="cvs3" width="900" height="375" tabindex="1">[No canvas support]</canvas> <canvas id="cvs4" width="900" height="375" tabindex="1">[No canvas support]</canvas> <canvas id="cvs5" width="900" height="375" tabindex="1">[No canvas support]</canvas> <canvas id="cvs6" width="900" height="375" tabindex="1">[No canvas support]</canvas> <canvas id="cvs7" width="900" height="375" tabindex="1">[No canvas support]</canvas> <canvas id="cvs8" width="900" height="375" tabindex="1">[No canvas support]</canvas> <canvas id="cvs9" width="900" height="375" tabindex="1">[No canvas support]</canvas> </div>
The CSS to define the sizes and transitions
css
is used to size the canvas
tags, position them and set the
transition
(animation) effect that you see when you click on the
tags. It also turns off the focus ring that you see when you click
on the tags. See the comments below for more details.
<style> // // This is the <div> that the <canvas> tags are defined in. It's sized to // be the same size as the full-sized <canvas> tags (ie 900x375). It // also sets the position to relative so that the <canvas> tags // that it contains can be positioned absolutely. Themargin-left
and //margin-right
properties are set toauto
so that the block of charts is aligned // centrally in the page. // #container { position: relative; width: 900px; height: 375px; margin-left: auto; margin-right: auto; } // // These styles are applied to all of the <canvas> tags. It makes them positioned // absolutely, turns off the focus ring (with the outline property), defines // the transition details (the animation effect) and sets the initial z-index // to zero. // #container canvas { outline: none; position: absolute; transition: top .5s, left .5s, width .5s, height .5s, z-index .5s, transform .25s, box-shadow .5s; transition-delay: .25s; z-index: 0; background-color: rgba(255,255,255,0.9); width: 300px; height: 125px; } // // The following styles are applied to the <canvas> tags in // order to initially position them correctly. // #container canvas#cvs1 {top: 0; left: 0;} #container canvas#cvs2 {top: 0; left: 300px;} #container canvas#cvs3 {top: 125px; left: 0;} #container canvas#cvs4 {top: 125px; left: 300px;} #container canvas#cvs5 {top: 0; left: 600px;} #container canvas#cvs6 {top: 125px; left: 600px;} #container canvas#cvs7 {top: 250px; left: 0;} #container canvas#cvs8 {top: 250px; left: 300px;} #container canvas#cvs9 {top: 250px; left: 600px;} // // These styles are applied to the <canvas> tags when they // are clicked on - ie they get focus. They're repositioned, // resized and have a shadow applied to them. // #container canvas#cvs1:focus, #container canvas#cvs2:focus, #container canvas#cvs3:focus, #container canvas#cvs4:focus, #container canvas#cvs5:focus, #container canvas#cvs6:focus, #container canvas#cvs7:focus, #container canvas#cvs8:focus, #container canvas#cvs9:focus { top: 5%; left: 5%; width: 90%; height: 90%; z-index: 999; box-shadow: 0 0 25px #ccc; } // // When the screen size is smaller the block of charts changes, // using media queries, from being three charts wide to two. The // small versions of the charts have to be repositioned as well // as the enlarged versions. // @media screen and (max-width: 700px) { #container {width: 600px; height: 625px} #container canvas#cvs1 {top: 0; left: 0;} #container canvas#cvs2 {top: 0; left: 300px;} #container canvas#cvs3 {top: 125px; left: 0;} #container canvas#cvs4 {top: 125px; left: 300px;} #container canvas#cvs5 {top: 250px; left: 0px;} #container canvas#cvs6 {top: 250px; left: 300px;} #container canvas#cvs7 {top: 375px; left: 0;} #container canvas#cvs8 {top: 375px; left: 300px;} #container canvas#cvs9 {top: 500px; left: 0px;} #container canvas#cvs1:focus, #container canvas#cvs2:focus, #container canvas#cvs3:focus, #container canvas#cvs4:focus, #container canvas#cvs5:focus, #container canvas#cvs6:focus, #container canvas#cvs7:focus, #container canvas#cvs8:focus, #container canvas#cvs9:focus { left: 0; width: 600px; height: 250px; z-index: 999; box-shadow: 0 0 25px #ccc; } #container canvas#cvs1:focus, #container canvas#cvs2:focus {top:-62.5px;} #container canvas#cvs3:focus, #container canvas#cvs4:focus {top:62.5px;} #container canvas#cvs5:focus, #container canvas#cvs6:focus {top:187.5px;} #container canvas#cvs7:focus, #container canvas#cvs8:focus {top:312.5px;} #container canvas#cvs9:focus {top:437.5px;} }</style>
The RGraph libraries and code
And finally here is the html
to include the RGraph libraries and the
javascript
that creates the charts. There's nothing special happening
here - just some basic charts.
<!--Include the RGraph libraries-->
<script src="RGraph.common.core.js" ></script>
<script src="RGraph.bar.js" ></script>
<script src="RGraph.line.js" ></script>
<script src="RGraph.waterfall.js" ></script>
<script src="RGraph.hbar.js" ></script>
<!--
This is the code that creates the charts. It's not using the
window.onload
event so it should be placed after the <canvas>
tags in your page
-->
<script>
new RGraph.Bar({
id: 'cvs1',
data: [4,5,3,1,2,6,5,4,8],
options: {
xaxisLabels: ['Dave','Loui','Luis','Pete','Olga','Steve','Kevin','John','Cuthbert'],
textSize: 14
}
}).draw();
new RGraph.Bar({
id: 'cvs5',
data: [4,7,9,5,3,7,6],
options: {
xaxisLabels: ['Mon','Tue','Wed','Thu','Fri','Sat','Sun'],
marginInner: 20
}
}).draw();
new RGraph.Line({
id: 'cvs2',
data: [1,3,5,2,6,4,7,8,9],
options: {
xaxisLabels: ['Dave','Loui','Luis','Pete','Olga','Steve','Kevin','John','Cuthbert'],
textSize: 14,
spline: true
}
}).draw();
new RGraph.Line({
id: 'cvs6',
data: [3,7,8,4,4,2,7],
options: {
xaxisLabels: ['Mon','Tue','Wed','Thu','Fri','Sat','Sun'],
textSize: 14,
marginInner: 25,
spline: true
}
}).draw();
new RGraph.Waterfall({
id: 'cvs3',
data: [45,-2,-9,4,6,3,-23,2,4],
options: {
xaxisLabels: ['Dave','Loui','Luis','Pete','Olga','Steve','Kevin','John','Total'],
textSize: 14
}
}).draw();
new RGraph.Waterfall({
id: 'cvs4',
data: [4,5,3,1,2,6,5,4,-8],
options: {
xaxisLabels: ['Dave','Loui','Luis','Pete','Olga','Steve','Kevin','John','Total'],
textSize: 14
}
}).draw();
new RGraph.HBar({
id: 'cvs7',
data: [8,3,7,4,6,9,8],
options: {
yaxisLabels: ['Jolly','Wolly','Lolly','Colly','Dolly','Molly','Polly'],
textSize: 14,
marginLeft: 75,
marginLeftAuto: false,
marginInner: 10
}
}).draw();
new RGraph.Line({
id: 'cvs8',
data: [8,3,7,4,6,9,8],
options: {
xaxisLabels: ['Jolly','Wolly','Lolly','Colly','Dolly','Molly','Polly'],
textSize: 14,
marginInner: 25,
spline: true,
linewidth: 20,
shadow: true,
backgroundGridVlines: false,
backgroundGridBorder: false,
xaxis: false,
yaxis: false,
textSize: 20
}
}).draw();
new RGraph.Bar({
id: 'cvs9',
data: [7,3,9,7,4,8,3],
options: {
xaxisLabels: ['Mon','Tue','Wed','Thu','Fri','Sat','Sun'],
marginInner: 25
}
}).grow();
</script>
A downloadable demo
If you want to see a standalone demo page of this
technique then there's one available in
the download archive
called bar-css-expand.html