Scrolling Flex Charts


If your TextArea has a lot of text, you get a scroll bar. If your datagrid has too many rows or columns, you get scroll bars. If your Image is too large, you can put it inside a container with scrollbars. Charts, however, do not have scrollbars. Charts with too much data look like this:

Replacement image.

I suppose it doesn't look too bad, but it is impossible to read the x-axis column labels. And of course, the dataset could be even bigger and the chart would be more unreadable.

You could put the chart inside a container with scroll bars, but that has a problem: the vertical axis scrolls out of view:

Replacement image.

I'm facing this problem now, so I created a component called 'ScrollableAxisRenderer'. It's derived from AxisRenderer and used in place of an AxisRenderer. Here's what it gives you:

Replacement image.

The scrollbar bits are skinnable. This example also has a zoom slider.

Replacement image.

I suppose the zoom would be better if the bottom gutter didn't jump around. But I don't really need it right now, so I'm not going to worry about it. I just threw it in for the heck of it.

BarCharts are also supported.

Replacement image.

How it works:

The ScrollableAxisRenderer contains another custom component: ChartDataScrollBar. When linked with the chart, it grabs the chart's dataprovider, wraps it in a SubRangeArrayColection and sets the chart's data provider to that. SubRangeArrayCollection implements IList and reveals only a subset of the inner collection; i.e. it acts as a filter. In psuedo-code:

chart.dataProvider = newSubRangeArrayCollection( 

The scrollbar's scrollPosition is bound to the SubRangeArrayCollection's startColumn property. Moving the scrollbar changes the data subset that the chart sees.

Note: While it would be easier to set the filterFunction property on the original collection, that would make the data unshareable. For example, if 2 charts were using that same collection as a dataprovider, using the filterFunction property for the first chart would break the second.

The next hurdle is getting the vertical range to stay fixed (in the case of a ColumnChart). As I scrolled the data, the axis values would jump around like crazy as the chart recalculated the optimal vertical range. I found that simply setting the min and max on the axis to themselves made them explicitly set. They were no longer recalculated as the data changed, and they did not jump around anymore.


axis.minimum = axis.minimum;
axis.maximum = axis.maximum;

I'm sure it has bugs in it. If you find anything, please let me know. If you have any suggestions about how to code it better, I would appreciate it. The updateProperties(), measure(), etc. are a bit voodoo-ish to me. When something should be updated in updateproperties() vs. updateDisplayList() is sometimes ambiguous.

The scrollbar skinning for this thing has a nasty hack. The ChartDataScrollBar wraps the Flex ScrollBar component which has a hard-coded minimum width of 16. I tried using that width here, but it looked ugly on top of the chart's axis. It really needs to be the same width as the axis, which is about 10 pixels. I can't override the 16-pixel value because the number is private (or internal or whatever). Therefore, I made the scrollbar skins 16 pixels wide, but half the width is invisible (alpha = 0). If you skin this thing, do the same thing. If you scale-9 the thumb, only include the ends of the thumb, not the width. If you change the axis stroke width, you'll have to fix the skin.

Again, if anyone has a better solution, please share it.

Here's the source.


Joel -- this is a great modification, and something that a _lot_ of people ask for often. If you're up for it, you should make it more widely available...submit it to one of the open source flex component libraries (I would suggest submitting it to the SDK, but I don't think charts are part of the open source codebase).

Anyway, great enhancement.
Ely Greenfield
Flex SDK.

I'll try to figure out where to submit it. I'm not familiar with the process of submitting code to an open source library. If you know precisely where I should submit this, please let me know. Or feel free to set it up yourself if you know where you want to put it. My feelings will not be hurt.

I might shoot you an email for advice on how to do this. I'll dig in over the weekend.

If anyone else can tell me precisely how to do this, or point me to the right place, please speak up.


This is so valuable. Great solution for a common problem.

This is an amazing component, please submit it to one of open source libraries like Flexlib or something. Any component that enhances data visualization, gets a big thumbs up from me.


FlexLib looks like a good place to put this.

Actually, I didn't even know about it until now. It's a great resource. It has some really useful components.


Beautiful, especially the internal graph scroll !, really impressive work.

you got some great stuff happenin.. love the way you have modified the graph.. and there are so many other things on this site to learn from ... u shud sure write often.. :)

Hey Joel, great component, I'm having some problems with using the firstIndexOffset property though. I'm basically trying to do something like this:

private function scrollHandler(event:MouseEvent):void{
scrollAxisRenderer.firstIndexOffset +=;

But any changes to the firstIndexOffset don't seem to be reflected in the graph. Is this a bug or am I just not doing it right? Thanks.


I'll look into it and post something in the next couple days. Thanks for trying it out and finding the problem.

Hi Joel, great work on this - just what I was looking to implement!

I have experienced some issues when using an ArrayCollection as the chart's dataProvider, i.e. the innerDP does not populate at 'innerDP = _chart.dataProvider as IList;' (ChartDataScrollBar).

It works fine with an XMLList however like in your example - maybe I'm doing something wrong?

I'll look into it this weekend. I have to actually use this component for a client project this weekend. I'll be exercising it more and make sure I fix this ArrayCollection issue.

Hi Joel, I've managed to get it working in code just need to explicitally state that the horizontal property of the ScrollAxisRenderer to either true or false.


scroll.axis = catAxis;
scroll.placement = "bottom";
scroll.maxVisibleColumns = 8;
scroll.horizontal = true;

Hope this helps :-)

Thanks Benjie, thank you, thank you.
I'm buried at the moment, and that helps huge.

could you please let me know what change is need to show lables on left hand side of barchart while keeping scrollbar on right hand side.
Please let me know as earky as possible

I honestly didn't think of that. It should be able to handle that. But the way I implemented it, the scrollbar connected to the axis renderer. Of course, the labels are also. Hmm. Before I submit it to flexlib, I'll try to address this issue. But in the meantime, if you look at the code, there is another component buried in there called 'ChartDataScrollBar'. You can put that anywhere you want, even on top of the other axis. You connect it to the chart, and it should work.

It's just a bit more work this way. ScrollableAxisRenderer is easier to use.

Unfortunately, I'm am under the gun right now, so I can't give you sample code using ChartDataScrollBar. Maybe in a few days.

I ahve done this .I have replaced following line of code:
var bInverted:Boolean = this.placement == "right";

in calcVertScrollBarRect() method of Scrollable Axis Renderer class with the following line:

var bInverted:Boolean = this.placement == "left";

and i n addition to this I have removed placement="right" property from VerticalAxisRenderer.

Thanks alot for creating such a wonder full sample

Thanks for figuring this out. When I get to cleaning the code up so I can submit it to flexlib, I'll incorporate your idea.

Putting the scrollbar on the side opposite the axis labels is actually a good idea. The scrollbar tends to visually separate the labels from the graph.

I really love this piece of work!

I got it working with AreaChart as well. I noticed that if you want a smooth update of your scrollbar using a DateTimeAxis with irregular dates, you need to add
in ChartDataScrollBar just after the updateScrollBar line 444. Not sure if you need all these invalidate functions, but it works better now.

BUT, one thing I can't seem to figure out is that when you update your dataProvider, it just shows you all your datapoints and the whole zoom and scroll stuff does not work. It seems to have lost its connection with the original chart or something. Any ideas?

(but thanks for the great work, it made a big impression here...!)

Hi am trying to implement the scrollable stuff for my AreaChart.
I was not able to figure out why the chart is not getting displayed. donno where exactly am going wrong.
The dataProvider to the ScrollableAxisRenderer is zero. Any ideas ???

Hi am trying to implement the scrollable stuff for my AreaChart.
I was not able to figure out why the chart is not getting displayed. donno where exactly am going wrong.
The dataProvider to the ScrollableAxisRenderer is zero. Any ideas ???

I cant use it on Flex Builder 3. How to use it? I download the zip file source and import it as a project, but it cant work at all.
The error messages show on browser include "RSL Error 1 of 2" and "Error #2032:". I think your creation is vary fantastic. You did a really good job.

In cases with a date, the zoom is actually more like a time window, in this case it'd be nice to make the conversion of the zoom value so that it gave the time windows in years, months, days, etc. It should be doable by just taking the ratio of the window time span to the total time span.

Hey, thank you very much for this!
It took me some time to get it to work, wich was completely my own fault :D
But got it working now in Flex 3, with an ArrayCollection that changes on user interaction.

Again, thanks!