summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRichard Wall <richard@aziz>2010-06-13 23:07:16 +0100
committerRichard Wall <richard@aziz>2010-06-13 23:07:16 +0100
commit528caf8bdec86c43e10932249154da15cdc6d408 (patch)
treee5c1122b2a8aa8255ded3372c3ce0dd618c74f09
parent434d36f49c34538b88145c6d681a681f6154edbe (diff)
Add dynamic tabs
-rw-r--r--index.html93
-rw-r--r--jrrd.js46
-rw-r--r--style.css7
-rw-r--r--tabs-no-images.css62
4 files changed, 158 insertions, 50 deletions
diff --git a/index.html b/index.html
index b966eb6..966ed47 100644
--- a/index.html
+++ b/index.html
@@ -6,6 +6,7 @@
<meta http-equiv="content-type" content="text/html;charset=utf-8" />
<link rel="stylesheet" type="text/css" href="http://flowplayer.org/tools/demos/dateinput/css/skin1.css" />
+ <link rel="stylesheet" type="text/css" href="tabs-no-images.css" />
<link rel="stylesheet" type="text/css" href="style.css" />
<script type="text/javascript" src="http://svn.mochikit.com/mochikit/trunk/MochiKit/Base.js"></script>
@@ -24,7 +25,7 @@
<script type="text/javascript" src="jrrd.js"></script>
<script type="text/javascript">
// Recipes for the charts on this page
- var recipes = [
+ var application_recipes = [
{
title: 'Twisted Web TCP Stats',
data: [
@@ -42,33 +43,56 @@
],
options: jQuery.extend(true, {}, jrrd.Chart.BASE_OPTIONS, jrrd.Chart.STACKED_OPTIONS)
},
- ].concat(jrrd.COLLECTD_RECIPES.cpu,jrrd.COLLECTD_RECIPES.memory,jrrd.COLLECTD_RECIPES.load);
+ ];
function initialiseCharts(rrdUrlList) {
/**
* Setup chart date range controls and all charts
**/
- console.log(jrrd.COLLECTD_RECIPES.cpu);
- // Add dhtml calendars to the date input fields
- $(":date").dateinput({format: 'mmm dd yyyy', max: +1});
- $(":date[name=startTime]").data("dateinput").change(function() {
- $(":date[name=endTime]").data("dateinput").setMin(this.getValue(), true);
- });
- $(":date[name=endTime]").data("dateinput").change(function() {
- $(":date[name=startTime]").data("dateinput").setMax(this.getValue(), true);
- });
// Extract the chart template from the page
var chartTemplate = $('.chart-container').remove();
- var cc = new jrrd.ChartCoordinator($('.chartRangeControl'));
- cc.charts = jrrd.collectdChartFactory(
- rrdUrlList, recipes, function() {
+ function templateFactory(parentEl) {
+ return function() {
// The chart template must be appended to the page early, so
// that flot can calculate chart dimensions etc.
- return chartTemplate.clone().appendTo('.charts');
- });
+ return chartTemplate.clone().appendTo(parentEl);
+ }
+ }
+
+ var cc = new jrrd.ChartCoordinator($('.chartRangeControl'));
+ var t;
+ // Initialise tabs and update charts when tab is clicked
+ $(".css-tabs:first").bind('click', function(i) {
+ // XXX: Hack to give the tab just enough time to become visible
+ // so that flot can calculate chart dimensions.
+ window.clearTimeout(t);
+ t = window.setTimeout(function() { cc.update(); }, 100);
+ });
+
+ cc.charts = [].concat(
+ jrrd.collectdChartFactory(
+ rrdUrlList,
+ [].concat(
+ jrrd.COLLECTD_RECIPES.cpu,
+ jrrd.COLLECTD_RECIPES.memory,
+ jrrd.COLLECTD_RECIPES.load),
+ templateFactory('.system-charts')),
+ jrrd.collectdChartFactory(
+ rrdUrlList,
+ jrrd.COLLECTD_RECIPES.interface,
+ templateFactory('.network-charts')),
+ jrrd.collectdChartFactory(
+ rrdUrlList,
+ jrrd.COLLECTD_RECIPES.dns,
+ templateFactory('.dns-charts')),
+ jrrd.collectdChartFactory(
+ rrdUrlList,
+ application_recipes,
+ templateFactory('.application-charts'))
+ );
// Update all charts when a selection is made on one of them
$('.charts').bind("plotselected", function(event, ranges) {
@@ -90,6 +114,18 @@
}
$(function() {
+ // Add dhtml calendars to the date input fields
+ $(":date").dateinput({format: 'mmm dd yyyy', max: +1});
+ $(":date[name=startTime]").data("dateinput").change(function() {
+ $(":date[name=endTime]").data("dateinput").setMin(this.getValue(), true);
+ });
+ $(":date[name=endTime]").data("dateinput").change(function() {
+ $(":date[name=startTime]").data("dateinput").setMax(this.getValue(), true);
+ });
+
+ // Setup dhtml tabs
+ $(".css-tabs").tabs(".css-panes > div", {history: true});
+
// Download a list of available rrd files and use it to generate
// any viable chart recipes
$.getJSON('rrd_finder.rpy', initialiseCharts);
@@ -98,11 +134,6 @@
</head>
<body>
- <div class="notice">
- <p>To get this demo working, you will need to serve this page from a
- local webserver and serve the folder that contains your RRD files.</p>
- </div>
-
<form method="GET" class="chartRangeControl">
<div>
<label>Start: <input type="date" name="startTime" /></label>
@@ -112,11 +143,21 @@
</div>
<div class="range-preview"></div>
</form>
- <div class="charts">
- <div class="chart-container">
- <h2 class="title"></h2>
- <div class="chart"></div>
- </div>
+ <ul class="css-tabs">
+ <li><a href="#system">System</a></li>
+ <li><a href="#network">Network</a></li>
+ <li><a href="#dns">DNS</a></li>
+ <li><a href="#application">Application</a></li>
+ </ul>
+ <div class="css-panes charts">
+ <div class="system-charts"></div>
+ <div class="network-charts"></div>
+ <div class="dns-charts"></div>
+ <div class="application-charts"></div>
+ </div>
+ <div class="chart-container">
+ <h2 class="title"></h2>
+ <div class="chart"></div>
</div>
</body>
</html>
diff --git a/jrrd.js b/jrrd.js
index 7155a10..cab736f 100644
--- a/jrrd.js
+++ b/jrrd.js
@@ -504,12 +504,12 @@ jrrd.COLLECTD_RECIPES = {
{
title: 'CPU Usage',
data: [
- ['cpu-0/cpu-wait.rrd', 0, 'CPU-0 Wait', 'Jiffies'],
- ['cpu-1/cpu-wait.rrd', 0, 'CPU-1 Wait', 'Jiffies'],
- ['cpu-0/cpu-system.rrd', 0, 'CPU-0 System', 'Jiffies'],
- ['cpu-1/cpu-system.rrd', 0, 'CPU-1 System', 'Jiffies'],
- ['cpu-0/cpu-user.rrd', 0, 'CPU-0 User', 'Jiffies'],
- ['cpu-1/cpu-user.rrd', 0, 'CPU-1 User', 'Jiffies']
+ ['cpu-0/cpu-wait.rrd', 0, 'CPU-0 Wait', '%'],
+ ['cpu-1/cpu-wait.rrd', 0, 'CPU-1 Wait', '%'],
+ ['cpu-0/cpu-system.rrd', 0, 'CPU-0 System', '%'],
+ ['cpu-1/cpu-system.rrd', 0, 'CPU-1 System', '%'],
+ ['cpu-0/cpu-user.rrd', 0, 'CPU-0 User', '%'],
+ ['cpu-1/cpu-user.rrd', 0, 'CPU-1 User', '%']
],
options: jQuery.extend(true, {}, jrrd.Chart.BASE_OPTIONS,
jrrd.Chart.STACKED_OPTIONS)
@@ -534,10 +534,10 @@ jrrd.COLLECTD_RECIPES = {
{
title: 'DNS Query Types',
data: [
- ['dns/dns_qtype-A.rrd', 0, 'A', 'Q/sec'],
- ['dns/dns_qtype-PTR.rrd', 0, 'PTR', 'Q/sec'],
- ['dns/dns_qtype-SOA.rrd', 0, 'SOA', 'Q/sec'],
- ['dns/dns_qtype-SRV.rrd', 0, 'SRV', 'Q/sec']
+ ['dns/dns_qtype-A.rrd', 0, 'A', 'Q/s'],
+ ['dns/dns_qtype-PTR.rrd', 0, 'PTR', 'Q/s'],
+ ['dns/dns_qtype-SOA.rrd', 0, 'SOA', 'Q/s'],
+ ['dns/dns_qtype-SRV.rrd', 0, 'SRV', 'Q/s']
],
options: jQuery.extend(true, {}, jrrd.Chart.BASE_OPTIONS)
},
@@ -545,9 +545,9 @@ jrrd.COLLECTD_RECIPES = {
{
title: 'DNS Return Codes',
data: [
- ['dns/dns_rcode-NOERROR.rrd', 0, 'NOERROR', 'Q/sec'],
- ['dns/dns_rcode-NXDOMAIN.rrd', 0, 'NXDOMAIN', 'Q/sec'],
- ['dns/dns_rcode-SERVFAIL.rrd', 0, 'SERVFAIL', 'Q/sec']
+ ['dns/dns_rcode-NOERROR.rrd', 0, 'NOERROR', 'Q/s'],
+ ['dns/dns_rcode-NXDOMAIN.rrd', 0, 'NXDOMAIN', 'Q/s'],
+ ['dns/dns_rcode-SERVFAIL.rrd', 0, 'SERVFAIL', 'Q/s']
],
options: jQuery.extend(true, {}, jrrd.Chart.BASE_OPTIONS)
}
@@ -569,8 +569,8 @@ jrrd.COLLECTD_RECIPES = {
{
title: 'Wlan0 Throughput',
data: [
- ['interface/if_octets-wlan0.rrd', 'tx', 'Transmit', 'b/sec'],
- ['interface/if_octets-wlan0.rrd', 'rx', 'Receive', 'b/sec']
+ ['interface/if_octets-wlan0.rrd', 'tx', 'Transmit', 'b/s'],
+ ['interface/if_octets-wlan0.rrd', 'rx', 'Receive', 'b/s']
],
options: jQuery.extend(true, {}, jrrd.Chart.BASE_OPTIONS)
}
@@ -688,10 +688,14 @@ jrrd.ChartCoordinator.prototype.update = function() {
var endTime = new Date(this.ui[0].endTime.value);
var chartsLoading = [];
for(var i=0; i<this.charts.length; i++){
- chartsLoading.push(
- this.charts[i].setTimeRange(startTime, endTime));
+ // Don't render charts which are not currently visible
+ if(this.charts[i].template.is(':visible')) {
+ chartsLoading.push(
+ this.charts[i].setTimeRange(startTime, endTime));
+ }
+
}
- MochiKit.Async.gatherResults(chartsLoading).addCallback(
+ return MochiKit.Async.gatherResults(chartsLoading).addCallback(
function(self, startTime, endTime, chartData) {
var firstUpdate = new Date().getTime();
var lastUpdate = 0;
@@ -754,14 +758,14 @@ jrrd.ChartCoordinator.prototype.setTimeRange = function(startTime, endTime) {
**/
this.ui[0].startTime.value = startTime.toString().split(' ').slice(1,5).join(' ');
this.ui[0].endTime.value = endTime.toString().split(' ').slice(1,5).join(' ');
- this.update();
+ return this.update();
};
jrrd.ChartCoordinator.prototype.reset = function() {
/**
* Reset all charts and the input form to the default time range - last hour
**/
- this.setTimeRange(new Date(new Date().getTime()-1*60*60*1000),
- new Date());
+ return this.setTimeRange(new Date(new Date().getTime()-1*60*60*1000),
+ new Date());
};
diff --git a/style.css b/style.css
index 9b6b471..8f5798e 100644
--- a/style.css
+++ b/style.css
@@ -1,7 +1,7 @@
body {
font-family: sans;
- width: 800px;
- margin: 20px auto 0 auto;
+ width: 960px;
+ margin: 20px auto 10px auto;
}
form div {
@@ -23,12 +23,13 @@ h2 {
.range-preview {
height:50px;
- margin: 0 auto 0 auto;
+ margin: 0 auto 10px auto;
position: relative;
}
.chart {
height:200px;
+ width: 850px;
margin: 0 auto 0 auto;
}
diff --git a/tabs-no-images.css b/tabs-no-images.css
new file mode 100644
index 0000000..58a54b4
--- /dev/null
+++ b/tabs-no-images.css
@@ -0,0 +1,62 @@
+
+/* root element for tabs */
+ul.css-tabs {
+ margin:0 !important;
+ padding:0;
+ height:30px;
+ border-bottom:1px solid #666;
+}
+
+/* single tab */
+ul.css-tabs li {
+ float:left;
+ padding:0;
+ margin:0;
+ list-style-type:none;
+}
+
+/* link inside the tab. uses a background image */
+ul.css-tabs a {
+ float:left;
+ font-size:13px;
+ display:block;
+ padding:5px 30px;
+ text-decoration:none;
+ border:1px solid #666;
+ border-bottom:0px;
+ height:18px;
+ background-color:#efefef;
+ color:#777;
+ margin-right:2px;
+ -moz-border-radius-topleft: 4px;
+ -moz-border-radius-topright:4px;
+ position:relative;
+ top:1px;
+}
+
+ul.css-tabs a:hover {
+ background-color:#F7F7F7;
+ color:#333;
+}
+
+/* selected tab */
+ul.css-tabs a.current {
+ background-color:#ddd;
+ border-bottom:2px solid #ddd;
+ color:#000;
+ cursor:default;
+}
+
+
+/* tab pane */
+.css-panes > div {
+ display:none;
+ border:1px solid #666;
+ border-width:0 1px 1px 1px;
+ min-height:150px;
+ padding:15px 20px;
+ background-color:#ddd;
+}
+
+
+