#!/usr/bin/perl
# Explore rrd via clickable graphs by. james@type-this.com (Claus Norrbohm)

# Basic idea: click high -> zoom out, click low -> zoom in,
# click left -> back history, click right -> forward history

use CGI::Carp;
use CGI;
use POSIX;
use lib qw( /usr/local/rrdtool/lib/perl );
use RRDs;

my $query = new CGI;

# modify as needed
$hight = 300; # Image size
$width = 600;
$refresh = 3600;
$expiredate = strftime "%a, %e %b %Y %H:%M:%S GMT", gmtime(time); # Format date(now)
$root = $ENV{"DOCUMENT_ROOT"}; # Location of rrd

print "Content-type: text/html\n"; # Use html
print "Cache-Control: no-cache\n"; # Ensure no cashing of page
print "Expires: $expiredate\n"; # Expire now
print "Refresh: $refresh\n\n";

print $query->start_html("Clickable rrd-graph"); # Title of html page

if ($query->param()) { # the form has already been filled out

  $rrd = $query->param("rrd"); # which rrd file are we tracking
  $start = $query->param("start"); # Start time
  $end = $query->param("end"); # End time
  $x = $query->param("img.x"); # x/y cordinates of click
  $y = $query->param("img.y");

  # see contrib/rrdfetchnames
  my ($begin,$step,$name,$data) = RRDs::fetch "$root$rrd","AVERAGE","--start","now","--end","start+1";
  if ( my $ERR = RRDs::error) {
    die "ERROR while fetching data from $NAME $ERR\n";
  }
  @names = @$name; # list of DS's "@$name"
  $j = @names;
  $esu = "";

  for ($i = 0; $i < $j; $i++) { # here we find which DS we are curently tracking
    if ($query->param("@names[$i]") == "1") {
      @use[$i] = 1;
      $esu .= "1"; # DS included
    } else {
      @use[$i] = 0;
      $esu .= "0"; # DS not included
    }
  }

  $intv = $end - $start; # Last used interval
  $zoom = ($hight + 100 - $y) / $hight; # Find zoom factor + 100 because hight is not exact
  $center = $start + $intv * $x / $width;  # Find time corresponding to click

  $start = int($center - $intv * $zoom); # Calc new start
  $end = int($center + $intv * $zoom); # Calc new end

} else { # first time through, so present clean form

  $rrd = $ENV{"REQUEST_URI"}; # Location of rrd

  $end = time(); # use now for end
  $start = $end - 86400; # and go back 24 hours

  # see rrdfetchnames
  my ($begin,$step,$name,$data) = RRDs::fetch "$root$rrd","AVERAGE","--start","now","--end","start+1";
  if ( my $ERR = RRDs::error) {
    die "ERROR while fetching data from $NAME $ERR\n";
  }
  @names = @$name; # list of DS's "@$name"
  $j = @names;
  $esu = "";

  for ($i = 0; $i < $j; $i++) { # All DS is included first time
    @use[$i] = 1;
    $esu .= "1";
  }

}

# Create a form with clickable image see page xxx in: Wallace, Shawn P.
# Programming Web Graphics with Perl
# and GNU Software
# O'Reilly UK,1999, UK, Paperback

print "
\n";

print "
\n";
print " Click on top to zoom out
\n";
print " Click
left
to
go
back
in
time";
print " \n";
# png.cgi prints the rrd graph, by printing to std.out (browser)
print "\n";
print "\n";
print "\n";
print "\n";
print "";
print " Click
right
to
go
forward
in
time
\n";
print " Click on bottom to zoom in
\n";
print "
\n";

print "

 Select / Deselect DS: \n";
for ($i = 0; $i < $j; $i++) { # present user with list of DS to select / deselect
  if (@use[$i] == 0) {
    print " @names[$i] \n";
  } else {
    print " @names[$i] \n";
  }
}
print "

\n";

print "
\n";

print "
Created by - Claus Norrbohm - james\@type-this.com
";

print $query->end_html(); # lmth ....
