Scrolling and zooming chart with ChartScroller

Some time ago I presented scrolling chart by using modified axis renderer (ScrollableAxisRenderer). I rethought this concept and come to the point that axis renderer should render axis not scroll the chart, so chart scrolling should be implemented as separate component. This is especially true in case of charts with many axes and renderers. My new idea was to create nonvisual component which will take reference to a chart and add appropriate listeners modifying axes minimum/maximum to achieve scrolling /zooming.

It was the challenge to find the way to easily convert mouse position to data coordinates and vice versa. According to documentation DataTransform objects should be used for this purpose, but unfortunately this documentation is quite incomplete. I especially like this sentence “In theory, a chart can contain multiple overlaid DataTransform objects.” – what does it mean “in theory” ? Having two vertical or horizontal axes is quite common case and in such case different data transformation have to be done for each axis. If charting sources were open it would at least be possible to figure out how data transformation is working reading code…

Anyway, finally I have found that chart series (Series) inherits two function (localToData() and dataToLocal()) to transform points to and from data coordinates. Using these functions I have implemented component named ChartScroller.

All you have to do to enable chart scrolling/zooming using ChartScroller is create instance of ChartScroller and pass reference to the chart to it. You can do it in MXML using the code similar to the one below:

<charts:ChartScroller id="scroller" chart="{chart}" />

<mx:ColumnChart id="chart" width="100%" height="100%" 
    gutterLeft="40" gutterRight="10" dataProvider="{dp}">    
        <mx:ColumnSeries id="series1" xField="x" yField="y2" />
        <mx:ColumnSeries id="series2" xField="x" yField="y1" />

ChartScroller is hosted on Currently charts with LinearAxis or DateTimeAxis are supported.

Basic Example

View source is enabled, you can download zipped sources from here.

Example – using ChartScroller with many axes

You can use ChartScroller for chart with multiple axes, so that different axes can be scrolled separately. To scroll/zoom concrete axis grab series using this axis or axis renderer.

View source is enabled, you can download zipped sources from here.

Example – ChartScroller properties

This example demonstrates how you can adjust behavior of ChartScroller by setting some of it public properties.

ChartScroller dispatches change event every time axis minimum/maximum value is modified. It also dispatches valueCommit event after specified time from last modification. This event may be used to retrieve new data or update other controls based on new axes minimum/maximum values. I will present example retrieving data from remote service on valueCommit event in separate post.

Share on Google+Share on FacebookShare on LinkedInPin on PinterestTweet about this on Twitter

39 thoughts on “Scrolling and zooming chart with ChartScroller”

  1. Perfect solution but… how about CategoryAxis? I’m trying to solve this problem but i don’t now a valid solution.

    Any idea?

  2. @JAIME
    Unfortunately ChartScroller can’t be used with CategoryAxis since it doesn’t have minimum/maximum properties.

    The good news is that you can simulate CategoryAxis behaviour by using LinearAxis with parseFunction and labelFunction. I will post an example demonstrating how to do that tomorrow.

  3. I didn’t have time to post a full example but I can give you some hints how to simulate CategoryAxis with LinearAxis (assume “dp” is data provider and “cat” is category field):

    • Declare series without xField property (that way index of item will be used as x value).
    • Create category label function which will convert item index to category label.
      public function categoryLabelFunction(labelValue:Object, 
          previousValue:Object, axis:IAxis):String
          if (labelValue >= 0 && labelValue < dp.length)
              return dp[int(labelValue)].cat;
          return "";
    • Declare LinearAxis using created category function. Setting “interval” property to 1 will prevent the same category label to be repeated many times.
          <mx:LinearAxis labelFunction="categoryLabelFunction" interval="1" />

    Hope this will be of some help to you.

    I’ll be on holiday next week so I will not be able to answer any further questions till August.

  4. hi Iwo,
    that’s really a great stuff! thanx very much.. I have a question about scroll and zoom, is it possible to control these from buttons in addition to mouse events?

  5. Hi Turker,

    Currently ChartScroller supports zooming/scrolling based on mouse events only.

    Zooming and scrolling is done simply by modifying axis minimum/maximum properties so you can modify it from button click event handler as well.

    Alternatively you can extend ChartScroller and use protected zoomChart() and scrollChart() functions. Note that before calling these functions you have to initialize ChartScroller by calling one of initializeFor*() functions.


  6. Hey,

    thanks for this!! I need this with a LineChart (with dynamic Dataprovider) and the Category Axis.. your example at the top works well with CategoryAxis, but the LineSeries are loosing the reference to the axis.. means, that “lineSeries.xField” doesnt work. Since I have multiple lineSeries I need the “xField”-Property.. is there a way to manipulate this also?

  7. Hi Franziska,
    I have created separate post about using ChartScroller together with LinearAxis simulating CategoryAxis. Hope this will be of some help.

  8. Hi,

    I am getting following error when I am compiling the given example.
    1046: Type was not found or was not a compile-time constant: ChartScroller
    can you pls let me know the reason.

  9. I’m just now learning Flex and am looking for a class that provides a general ability to slide anything with click and drag, not just charts. I looked at your source but it seems that sliding is built in to the chart class. I’m trying to implement an historical timeline that is very “long” and that can be scrolled left or right, that contains tick marks and photos. HOpe this makes sense and is not too far off-topic. Thanks!

  10. Great work, Iwo.
    Just one thing. Take this data set and we dont see anything in the view.
    Probably the scale minimizes out. Am I missing something ?

    Thanks again.


  11. Further to my post above – Somehow my data set I posted is filtered out or isnt being seen in my post. In your linearaxis just change the values of x to huge to say 98, 200, 400 , 500, 1890, 2500, 3400, 4000 etc.

  12. I think I figured it out . You set the min-max to a small range for the bars to be wide enough and then scroll about – stupid me!

  13. ChartScroller is frankly the coolest chart modification I’ve run across. It has a great “gee-whiz” factor. Thank you for sharing as it is absolutely brilliant.

  14. Hello! great component! The only missing thing is:
    After scrolling and zooming in the chart, i want to go back to the first view where all data was fitting in my chart. Is there a function (autofitaxis)? How can i implement this?
    Many Thanks in advance!

  15. Hi,
    Excellent work. Can I use the same in my project. If any thing related to Licensing please let me know

  16. Sure you can use it!
    It’s released under MPL license (the same as Flex SDK) so if you improve it you should publish changes (of course only changes to my component not the code of your application).
    For example you can commit it to the google code project or simply send me a diff.

  17. Hi, I love this component, however it does have one limitation for me–the scroll wheel. Macs still do not (to my knowledge) support the scroll wheel, and some laptops dont have them either.

    Id like to modify your component to handle a keyboard event for zooming(such as using the + and – for zooming). How would you recommend doing this?

  18. Hi,

    Excellent work, very helpful. i want to use your component but i dont know how, i have linechart instead of columnchart,and the data of my dataprovider is like this :
    public var tableauGraph:ArrayCollection = new ArrayCollection([
    {gare: “Reiner”, heure: “10:00”, numero: 69000,ordre: 10},
    {gare: “Rein”, heure: “10:30”, numero: 69000,ordre: 11},
    {gare: “trdf”, heure: “10:45”, numero: 69000,ordre: 12},
    {gare: “Rei”, heure: “11:00”, numero: 69000,ordre: 13},
    {gare: “Rein”, heure: “10:00”, numero: 69100,ordre: 3},
    {gare: “Reibv”, heure: “10:45”, numero: 69100,ordre: 4},
    {gare: “fgf”, heure: “10:55”, numero: 69100,ordre: 5},
    {gare: “trtrdg”, heure: “11:00”, numero: 69100,ordre: 6},
    {gare: “trdf”, heure: “12:00”, numero: 69100,ordre: 7}

    now i want in Xaxes “gare” and in the Yaxes “heure”, i cant print the label of heure! can you help me?

    Thanks and sorry for my english.

  19. Will it work for the stacked charts… with different series..
    I am using column chart which has 6 column series and need to scroll chart.
    Will this work. I would like to use this example.
    Good scroll bar example really…!

  20. Terrific!

    Do you mind if I slightly changed your components and put your post on the Russian language to keep a reference to the source?

  21. hi!
    Thank you for your work. I have a question:
    1 I use your code to work with CandlestickChart. This chart is updated on a timer. How to make sure that-be when you add a new value, old moved to the left (with the axis Y)? There is now a zoom-out the whole chart.

    Thank you.

  22. Hi Iwo.. gr8 work..unfortunately..i am not yet able to get it work on a bar chart..any help will be appreciated..

  23. Hi, Excellent work, very helpful. I have a question about performance with Large Data Sets, I have a chart with 10000+ data points, it is slow when Scrolling and zooming the chart, but the CPU and ram is not fully in use.

  24. Hi Iwo,

    Thank you for the helpful tutorial and nice code.
    I have two question though.
    1. When I use the scrolling (setting minimum and maximum), if I have something drawn on the chart (on it CartesianDataCanvas) and if the draw goes out of sight, next time I scroll back to its position, it is gone!
    I use addDataChild to add a graphic.
    2. Something similar happens if I add another LineSeries with less data. While scrolling, the line segments can disappear at once.
    Can you please advice on this?

  25. hi ,
    i using column chart where it contain n number of bars i want to set horizontal scroll bar , i take example above but in that i find an error ( The prefix “charts” for element “charts:ScrollableAxisRenderer” is not bound.) the charts tag where it comes from?

    this is the line i got error.

    Please give me a solution thanks in advance..

  26. Report error in Flex 4.5:

    in As Class —-> styleManager
    Change to IStyleManager2?? or FlexGlobals.topLevelApplication.styleManager??


  27. @Nick
    I’m having the same issue with data labels disappear and then appear if I keep scrolling. Anyone solve this problem?

  28. I am getting this error

    In initializer for ‘mxmlContent’, type com.hp.commandview.tape.gui.tapeassure.presentation.comp.ChartScroller is not assignable to target Array element type mx.core.IVisualElement.

  29. Hi,
    Great work Iwo. We took similar approach, but found issues with localToData / globalToData + DateTimeAxis when disabledRanges are used. Those methods do not take disabledRanges into consideration. Do you have any clues for us how to resolve this?

  30. I want to scroll my cartesian chart on mouse press like wise, if i press for 2 secs on right side my chart should start scrolling and same for left side. Is this possible?

Leave a Reply

Your email address will not be published. Required fields are marked *