PDA

View Full Version : (Beta 1) BarSeries Stacked Mode Issue



LEWJO10@ca.com
18 Dec 2011, 12:38 PM
Brendan,

The setting the setStacked method to true in the BarSeries class can lead to problematic consequences.

One example is a time series column chart where the percentage of each product’s contribution to total sales is plotted in stacked columns. In other words, each product’s percentage of total sales is stacked one on top of the other for each time interval, and the vertical axis is percentage of sales. Also, (and this is where things get to be problematic) each column has the same height, which is 100% of sales.

This seems at first to be a simple endeavor. Just calculate the percentage each product has of total sales and plot it in a BarSeries setting setStacked to true.

But wait, you run the chart and find that each column has a slightly different height. Some have a height that is exactly at 100%, some are lower than 100%, and some are higher than 100%. If you run the attached example (ColumnChart_Stacked.txt) you will see what I mean. Also, if you slowly resize the browser window to have less or more height, you will see some of the columns that were too low become too high and vice versa.

How can this be?

The problem is that you cannot display a fractional part of a pixel. Either a whole pixel is displayed or it is not. When plotting a stacked column, choices must be made that will ultimately be a little wrong. These little wrongs add up until the height of the column is noticeably wrong – especially on charts where the vertical height or horizontal length of each column or bar is expected to be the same well known value.

This is a problem inherent to charting with pixels. Not surprisingly, I ran into the same problem with Flex charting. But, Flex offers three modes for a bar series: grouped, stacked and overlaid. So, I solved the problem in the Flex charts by calculating a second set of cumulative percentages for each product, where the percentages of products lower in the column stack were added to the cumulative percentage for the next product higher in the stack. Then I set the mode to overlaid, plotted the cumulative percentages, and used the regular percentages in the tool tips.

As time went on, I found that I never used stacked mode, but instead did everything in overlaid mode – even for charts that appeared to be stacked.

Fortunately, I found a way to solve this problem in much the same way using the GXT 3.0 charts. I instantiate a separate BarSeries for each product, and add the BarSeries for the product highest in the stacked column to the chart first, followed by the second most highest, and so on.

The only problem I ran into was with the tool tips. You only want one tool tip to show for the overlaid bar that is visible – not all the tool tips possible. But, I found a way around this problem by formatting and then disabling the tool tip in the SeriesItemOverHandler for each BarSeries column, and launching a Timer to determine which one to ultimatly enable and show. I got the x and y coordinates to use by overriding the onMouseMove method in the BarSeries class to save off the PrecisePoint property class.

I scheduled the timer to start in one millisecond as (I am guessing) the code to determine which tool tip to show finishes long before the Time starts.

Fortunately, there are no problems with the SeriesSelectionHandlers. You just get one event, which is the correct one.

If you run the second attachment (ColumnChart_Overlaid.txt), you can see a working fix.

So here is my request.

I think the bar series really should have an overlaid mode, or at the very least have a Boolean option to set in some class to indicate that only the visible bar’s tool tip is to be shown.

Please let me know your thoughts.

I am very greatful to find a way to use the overlaid approach as I believe this would have been a show stopper with the customers we serve. Imagine explaining the chart to a customer, and then having to explain why the heights of the columns vary. The more products (series) in the column stack and intervals across the horizontal axis – the worse it looks.

Thanks,
John Lewis

LEWJO10@ca.com
23 Dec 2011, 5:06 AM
Brendan,

I have come up with a much better way to do an overlaid BarSeries chart that does not require the use of a Timer.

I still instantiate a separate BarSeries for each product, and add the BarSeries for the product highest in the stacked column to the chart first, followed by the second most highest, and so on (same as before).

To manage the tool tips so that only one tool tip shows for the correct bar (i.e., the portion of the bar that is not overlaid by another), I created an array of SpritLists, where each entry in the array is a reference to the SpritList of each BarSeries. Then I overrode the BarSeries class getIndex method to traverse the array and figure out which tool tip to show (returning the index to show and -1 to not show). To make the code a little more efficient, I save the value of the index when it is found for potential use by other BarSeries that may be overlaying the BarSeries where the find occurred.

If you run the second attachment (ColumnChart_Overlaid2.txt), you will see a better version of a working fix.

I still think the bar series really should have an overlaid mode, or at the very least have a Boolean option to set in some class to indicate that only one tool tip is to be shown for the correct bar (i.e., the portion of the bar that is not overlaid by another).

Please let me know your thoughts.

By the way, thank you for providing the means to show tool tips in the labels of a CategoryAxis or TimeAxis. I am currently using the feature and it works great!

John Lewis