A Quick Look at Visualforce Charting

It’s been almost two weeks since the end of Dreamforce, but if anything, the excitement level here is going up. Winter ’12 is just around the corner, and we’re getting amped to see what you can do with it. Today I want to give a quick tour of one of the features I documented—charting in Visualforce.

Note: Visualforce charting components are currently available through a pilot program. For information on enabling this feature for your organization, contact salesforce.com. At this time it is not recommended that this feature be used in production code or managed packages.

Visualforce charting is a way for you to create custom “business style” charts on your Visualforce pages—pie, bar, and line charts. It simplifies the process of connecting a data source (generally a custom controller method) to JavaScript charting libraries that render groovy charts in the browser. If you want to, you can work exclusively in Visualforce and Apex, and let the charting components take care of all the JavaScript for you.

But enough with the description—let’s look at some code! Here’s what a simple pie chart looks like in a Visualforce page:

<apex:page controller="PieChartController" title="Pie Chart">
    <apex:chart height="350" width="450" data="{!pieData}">
        <apex:pieSeries dataField="data" labelField="name"/>
        <apex:legend position="right"/>
    </apex:chart>
</apex:page>

This needs to be paired with a controller that can supply the pie chart data. Normally you would perform a SOQL query or otherwise calculate the pie wedge data from your live business data, but to keep this simple (and to give you something to copy and paste once you have Winter ’12 yourself), here’s an example that uses dummy data:

public class PieChartController {
    public List<PieWedgeData> getPieData() {
        List<PieWedgeData> data = new List<PieWedgeData>();
        data.add(new PieWedgeData('Jan', 30));
        data.add(new PieWedgeData('Feb', 15));
        data.add(new PieWedgeData('Mar', 10));
        data.add(new PieWedgeData('Apr', 20));
        data.add(new PieWedgeData('May', 20));
        data.add(new PieWedgeData('Jun', 5));
        return data;
    }

    // Wrapper class
    public class PieWedgeData {

        public String name { get; set; }
        public Integer data { get; set; }

        public PieWedgeData(String name, Integer data) {
            this.name = name;
            this.data = data;
        }
    }
}

But here’s what you really want to see—the chart itself:

A simple pie chart

Deliberately Spartan, but it’s awfully easy to create! Before we look at a more interesting chart, here’s a few things to note in this simple example.

  • The chart itself is defined using four new components, on lines 2-5. The structure is simple: an overall chart component creates a context and wraps various child components that define how to construct the chart.
  • You should have no difficulty identifying how the getPieData() controller method that supplies the data is linked to the chart component, using the {!pieData} expression that calls it.
  • What’s interesting here is the format in which the data is supplied. The controller defines an inner class that “wraps” the data for each pie wedge. The properties of the inner class—name and data—create a simple name/value pair for accessing the elements for each data point in the chart. I’ll expand on this in the second example.

Pie charts are pretty simple, with only one data series per chart. Bar and line charts can layer multiple data series, combining lines and bars to tell a compelling story. Here’s a chart that combines three different sets of data to show the relationship between them:

A combined bar and line chart

Pretty snazzy, huh? Here’s the Visualforce markup to display that chart:

<apex:page controller="ChartController">
    <apex:chart height="400" width="700" data="{!data}">
        <apex:legend position="right"/>
        <apex:axis type="Numeric" position="left" fields="data1"
            title="Opportunities Closed" grid="true"/>
        <apex:axis type="Numeric" position="right" fields="data3"
            title="Revenue (millions)"/>
        <apex:axis type="Category" position="bottom" fields="name"
            title="Month of the Year">
            <apex:chartLabel rotate="315"/>
        </apex:axis>
        <apex:barSeries title="Monthly Sales" orientation="vertical" axis="right"
            xField="name" yField="data3">
            <apex:chartTips height="20" width="120"/>
        </apex:barSeries>
        <apex:lineSeries title="Closed-Won" axis="left" xField="name" yField="data1"
            fill="true" markerType="cross" markerSize="4" markerFill="#FF0000"/>
        <apex:lineSeries title="Closed-Lost" axis="left" xField="name" yField="data2"
            markerType="circle" markerSize="4" markerFill="#8E35EF"/>
    </apex:chart>
</apex:page>

The preview documentation has extensive details for these charting components, but here are two differences to highlight compared to the pie chart:

  • Notice the three <apex:axis> components, lines 4-11, which define the units and labels for the three chart axes that are in use here. An axis automatically calculates its minimum, maximum, and tick mark increments based on the data found in the data series defined in the fields attribute. You can also set the start and end of the axis manually.
  • After the axes definitions are three data series—one <apex:barSeries> and two <apex:lineSeries> components, on lines 12-19. Each series represents a set of points plotted on the chart. The points are defined by the xField and yField attributes in the series, which define the properties (the name part of the name/value pair) in the {!data} collection that represents each data point. So, for the <apex:barSeries>, the X value of the point is the name property, representing a month of the year, and the Y value of the point is the data3 property, representing dollars (in millions).

Finally, here’s the controller that supplies the data:

public class ChartController {
    // Return a list of data points for a chart
    public List<Data> getData() {
        List<Data> data = new List<Data>();
        data.add(new Data('Jan', 30, 90, 55));
        data.add(new Data('Feb', 44, 15, 65));
        data.add(new Data('Mar', 25, 32, 75));
        data.add(new Data('Apr', 74, 28, 85));
        data.add(new Data('May', 65, 51, 95));
        data.add(new Data('Jun', 33, 45, 99));
        data.add(new Data('Jul', 92, 82, 60));
        data.add(new Data('Aug', 87, 73, 45));
        data.add(new Data('Sep', 34, 65, 55));
        data.add(new Data('Oct', 78, 66, 56));
        data.add(new Data('Nov', 80, 67, 53));
        data.add(new Data('Dec', 17, 70, 70));
        return data;
    }

    // Wrapper class
    public class Data {
        public String name { get; set; }
        public Integer data1 { get; set; }
        public Integer data2 { get; set; }
        public Integer data3 { get; set; }
        public Data(String name, Integer data1, Integer data2, Integer data3) {
            this.name = name;
            this.data1 = data1;
            this.data2 = data2;
            this.data3 = data3;
        }
    }
}

Really, this isn’t meaningfully different from the PieChartController in the first example. All I’ve done is added additional properties to the wrapper class, one per data series. If I wanted to be a little more semantic, I could name those properties to be related to their underlying data—for example, dataClosedWon instead of data1. I’ll leave that as an exercise for you when you create your first chart. ;-)

That’s all for this week. You can read more about Visualforce charting in the preview release notes and documentation we published last week. The whole Visualforce team is looking forward to seeing what you do with Winter ’12!

tagged , , , , , Bookmark the permalink. Trackbacks are closed, but you can post a comment.
  • http://forcearchitects.deliveredinnovation.com/2011/09/19/force-feed-4/ Force Feed | Force Architects: Delivered Innovation Blog

    [...] A quick, straightforward summary of all the Force.com and Salesforce posts from the previous week. A Quick Look at Visualforce Charting @Alderete_SFDC A look at Visualforce charting, a way for you to create custom business charts (pie, [...]

  • omar vazquez vargas

    I have a question if a need print this Chart in a PDF document is there any problem? because some time ago we make this using other libraries.

    Regards

  • http://twitter.com/Alderete_SFDC Michael Alderete

    Visualforce charting is currently in pilot, and has a number of limitations. One of them is that it does not work when you render a page as a PDF. You’ll want to review the documentation on this feature to get the full scoop, check out the link above for the preview docs.

  • Olaf Molenveld

    Would it be possible to integrate the HighCharts javascript charting library for charting? This could be a nice addition..

  • Olaf Molenveld

    Would it be possible to integrate the HighCharts javascript charting library for charting? This could be a nice addition..

  • http://twitter.com/Alderete_SFDC Michael A. Alderete

    The short answer is no. This is detailed in the Limitations section of the Visualforce charting documentation, along with other limitations of the charting pilot. There’s a link to the prerelease docs at the end of the post.

  • http://twitter.com/Alderete_SFDC Michael A. Alderete

    If you are asking can the new charting features use this library, instead of the charting JavaScript it uses currently, the answer is no.

    If you are asking if you can use HighCharts on your own, to develop your own charting solution, the answer should be yes. See the JavaScript chapter in the Visualforce Developer’s Guide for details about working with third-party JavaScript libraries.

  • http://www.facebook.com/people/Alex-Ferguson/1844389575 Alex Ferguson

    I’m on winter 12 but getting Error: Unknown component apex:chart in pieChart

  • http://twitter.com/Alderete_SFDC Michael A. Alderete

    Charting is a pilot. It is not enabled by default, and when it’s not enabled, you’ll get that error message. You will have to contact Support and request to be added to the pilot program.

  • http://twitter.com/gi0_0iv Hitoshi Sasaki

    Hi,
    Does the Scatter Chart came to be usable?

  • http://twitter.com/Alderete_SFDC Michael A. Alderete

    We don’t currently have a scatter chart available in Visualforce charting. If that’s a chart type that is important to you, please do join the charting pilot program, and give us that feedback. Or, just log that feedback with Support. We love to hear from our customers, and new charting features WILL be driven by customer feedback. Thanks for your ideas and help!

  • Mohan Elango

    Is there an option to enable this in production? I know this is in Pilot.

  • http://twitter.com/Alderete_SFDC Michael A. Alderete

    Mohan, you’ll want to talk to Support and learn about what options you have for using Visualforce charting. But, be aware that we explicitly do not recommend using charting in production pages at this time.

  • http://twitter.com/gi0_0iv Hitoshi Sasaki

    Thank you for Reply!
    The Scatter Chart is used for the product which we produce.
    When possible, I stop use of Google chart and want to use Chart which is a native.

    Then we joined in the charting pilot program.

  • ravi samani

    Thanks.