ChartDirector 6.0 (ColdFusion Edition)

Variable Width Bar Chart




This example demonstrates a bar chart with variable bar widths.

ChartDirector does not really have a bar layer for variable width bars. However, an area layer can be used to create the same effect.

The variable width bars in this example are actually 4 areas, created by 4 area layers. The data set for each area layer consists of 4 points for the 4 corners of a bar.

Source Code Listing

[File: cfdemo/varwidthbar.cfm]
<cfscript>

// ChartDirector for ColdFusion API Access Point
cd = CreateObject("java", "ChartDirector.CFChart");

// A utility to allow us to create arrays with data in one line of code
function Array() {
    var result = ArrayNew(1);
    var i = 0;
    for (i = 1; i LTE ArrayLen(arguments); i = i + 1)
        result[i] = arguments[i];
    return result;
}

// The data for the chart
data = Array(800, 600, 1000, 1400);
widths = Array(250, 500, 960, 460);
labels = Array("Wind", "Hydro", "Coal", "Natural Gas");

// The colors to use
colors = Array("0x00aa00", "0x66aaee", "0xee6622", "0xffbb00");

// Create a XYChart object of size 500 x 350 pixels
c = cd.XYChart(500, 350);

// Add a title to the chart using 15pt Arial Italic font
c.addTitle("Energy Generation Breakdown", "Arial Italic", 15);

// Set the plotarea at (60, 60) and of (chart_width - 90) x (chart_height - 100) in size. Use a
// vertical gradient color from light blue (f9f9ff) to sky blue (aaccff) as background. Set grid
// lines to white (ffffff).
plotAreaBgColor = c.linearGradientColor(0, 60, 0, c.getHeight() - 40, "0xaaccff", "0xf9fcff");
c.setPlotArea(60, 60, c.getWidth() - 90, c.getHeight() - 100, plotAreaBgColor, -1, -1, "0xffffff");

// Add a legend box at (50, 30) using horizontal layout and transparent background.
c.addLegend(55, 30, False).setBackground(cd.Transparent);

// Add titles to x/y axes with 10 points Arial Bold font
c.xAxis().setTitle("Mega Watts", "Arial Bold", 10);
c.yAxis().setTitle("Cost per MWh (dollars)", "Arial Bold", 10);

// Set the x axis rounding to false, so that the x-axis will fit the data exactly
c.xAxis().setRounding(False, False);

// In ChartDirector, there is no bar layer that can have variable bar widths, but you may create a
// bar using an area layer. (A bar can be considered as the area under a rectangular outline.) So by
// using a loop to create one bar per area layer, we can achieve a variable width bar chart.

// starting position of current bar
currentX = 0;

for (i = 0; i LT ArrayLen(data); i = i + 1) {
    // ending position of current bar
    nextX = currentX + widths[i + 1];

    // outline of the bar
    dataX = Array(currentX, currentX, nextX, nextX);
    dataY = Array(0, data[i + 1], data[i + 1], 0);

    // create the area layer to fill the bar
    layer = c.addAreaLayer(dataY, colors[i + 1], labels[i + 1]);
    layer.setXData(dataX);

    // Tool tip for the layer
    layer.setHTMLImageMap("", "", "title='" & labels[i + 1] & ": " & widths[i + 1] & " MW at $" &
        data[i + 1] & " per MWh'");

    // the ending position becomes the starting position of the next bar
    currentX = nextX;
}

// Output the chart
chart1URL = c.makeSession(GetPageContext(), "chart1");

// Include tool tip for the chart
imageMap1 = c.getHTMLImageMap("");

</cfscript>
<html>
<body style="margin:5px 0px 0px 5px">
<div style="font-size:18pt; font-family:verdana; font-weight:bold">
    Variable Width Bar Chart
</div>
<hr style="border:solid 1px #000080" />
<cfoutput>
<div style="font-size:9pt; font-family:verdana; margin-bottom:1.5em">
    <a href='viewsource.cfm?file=#CGI.SCRIPT_NAME#'>View Source Code</a>
</div>
<img src="getchart.cfm?#chart1URL#" usemap="##map1" border="0" />
<map name="map1">#imageMap1#</map>
</cfoutput>
</body>
</html>