Graphs and Charts in PHP using PEAR Image Graph

There are many 3rd party solutions out there for drawing charts and graphs in PHP. Some are a little ropey, many are over-priced (particularly for commercial users). My research into what is available boiled down to the Image_Graph package in the PEAR repository, and a PHP class called PHPlot from a guy named Miguel de Benito Delgado. Miguel's code offers the benefits of compactness - you only need add a single PHP file to your site in order to use his drawing functions. This single file defines the PHPlot class, and is admittedly over 4000 lines long. To draw charts with PEAR on the other hand, you need all the associated base PEAR classes, and set up is a fair bit more drawn out. However, the PEAR solution is considerably more versatile allowing a huge range of charts.
compton, 15 February 08
Updated 25 October 12
To install PHPlot, you simply need to place the phplot.php file from the download somewhere it can be easily included in any pages that use it.

PEAR installation is a bit more of a pain in the neck. Using the charting classes is also less intuitive due to its greater sophistication.

First thing to do is create an instance of an Image_Graph object, using the Image_Graph::factory() method. The Image_Graph class is defined in the Image/Graph.php file, and the factory() method will instantiate one of a variety of the classes that support the graphing functionality. The first argument for this function denotes the specific class we want, and the second is an array of parameters to pass to that class's constructor.

So we start by calling this method to get an instance of the Image_Graph class itself:
$Graph =& Image_Graph::factory('graph', array(400, 300));
The first argument for the factory() method specifies that we want an instance of the Image_Graph class, and the second is an array of the parameters to pass to the Image_Graph constructor. You can probably guess that they serve to specify the size of the graph that we want to create in pixels.

Now it's a good idea to add a font to the graph, which will be used for labels. Any true type font can be used (www.dafont.com has a fantastic selection of freely downloadable true type fonts, although not all are free for commercial use so check the licence), you just need to place the ttf file in Image/Canvas/Fonts (and make sure the extension is lowercase). Then you add the font to the graph like so:
$Font =& $Graph->addNew('font', 'CHERI'); $Font->setSize(11); $Graph->setFont($Font);
Next we need to set up the main components of the graph: vertical layout, the main title, the plot area, and a legend (key):
$Graph->add( Image_Graph::vertical( Image_Graph::factory('title', array('Sales Bobbles', 16)), Image_Graph::vertical( $Plotarea = Image_Graph::factory('plotarea'), $Legend = Image_Graph::factory('legend'), 90 ), 5 ) ); $Legend->setPlotarea($Plotarea);
We're now ready to import the data we want the chart to display. In this example, where we're going to show a bar chart with a group of three bars for each x value, we need to create three datasets:
$datasets = array(); $datasets[] =& Image_Graph::factory('dataset'); $datasets[] =& Image_Graph::factory('dataset'); $datasets[] =& Image_Graph::factory('dataset');
Because we'll be showing a legend on the chart, we need to label each dataset appropriately, and we might as well do this now:
$datasets[0]->setName('Net Amount'); $datasets[1]->setName('Gross Amount'); $datasets[2]->setName('Cost Price');
Now we can populate each dataset. In this example, we're getting the data from a SQL query resultset:
while ($row = mysql_fetch_array($result)) { $datasets[0]->addPoint($row['name'], $row['net_amount']); $datasets[1]->addPoint($row['name'], $row['gross_amount']); $datasets[2]->addPoint($row['name'], number_format($row['cost_price'], 2, '.', '')); }
Next, we add the datasets to the graph as a bar chart:
$Plot =& $Plotarea->addNew('bar', array($datasets));
We can define a colour for outlining the bars in the chart:
$Plot->setLineColor('gray');
And fill colours for each dataset:
$FillArray =& Image_Graph::factory('Image_Graph_Fill_Array'); $FillArray->addColor('blue@0.2'); $FillArray->addColor('yellow@0.2'); $FillArray->addColor('orange@0.2'); $Plot->setFillStyle($FillArray);
If we want, we can also have each bar labelled with the Y-value it corresponds to, like so:
$Marker =& $Plot->addNew('Image_Graph_Marker_Value', IMAGE_GRAPH_VALUE_Y); $Plot->setMarker($Marker);
We're now ready to render the chart:
$Graph->done();