First, a special security-breach-related notice
"Ask not what is the weakest link. It's clicked by you." -- Bruce BellatollisThe laptop I used to build and upload previous releases was "owned" (rootkitted) by an attacker for an unknown period of time. My best guess is that a "drive by download" initiated by clicking on what I believed to be a legit GChart-related link was responsible. Regardless of how it happened, once the attacker had the ability to remotely control the machine that built, administered, and released GChart, they could in principle have, say, injected Trojans into my releases. It's bad to be owned. Fortunately, I have not seen any specific evidence that the project's on-line artifacts were tampered with in a manner dangerous to GChart users. Knock wood.
To help eliminate such uncertainties and prevent future breaches, this release contains substantial security-related improvements, including:
So, besides working to assure we actually get the code you wrote when we download the product (great feature, but we assumed you already had that one before) what's new in GChart 2.7? Well, there are a few actual features--read on.
Overview of GChart 2.7 improvements
The main purpose of the improvements of this release is to facilitate the creation of interactive charts (e.g. mouse driven pan and zoom) as illustrated in the live demo's updated LayZLine™ chart editor, and to facilitate the creation of charts with curvy (Bezier) connecting lines (c.f. the live demo's oil price simulation chart)
GChart still does not natively support such features. Instead, this release adds a small set of helper features, such as support for all of GWT's mouse-event-handling interfaces and the ability to quickly translate each previously rendered curve. As the live demo illustrates, such features make it possible for you to implement drag-to-pan, curvy connecting lines, and similar advanced features efficiently.
This approach of "externalizing" (essentially, placing them into example code) such features keeps GChart simpler, gives you more flexibility, and saves me a heck of a lot of work.
The Bezier curve functionality is realized by implementing the lineTo and related method of the GChartCanvasLite interface so that they draw curvy, rather then straight, point-to-point connecting lines using GWTCanvas.cubicCurveTo and related methods.
Finally, this release adds the ability to reposition or replace (c.f. setLegendLocation, setLegend) a chart's legend, and several bugfixes.
Detailed change log:
Specifically, in addition to the previously supported HasClickHandlers a GChart now also implements HasDoubleClickHandlers, HasMouseDownHandlers, HasMouseMoveHandlers, HasMouseOutHandlers, HasMouseOverHandlers, HasMouseUpHandlers, and HasMouseWheelHandlers.
The new methods addDoubleClickHandler, addMouseDownHandler, addMouseMoveHandler, etc. implement these interfaces.
With this release, you can use the new setLegendLocation method, passing it one of the following predefined LegendLocations: INSIDE_BOTTOM, INSIDE_BOTTOMLEFT, INSIDE_BOTTOMRIGHT, INSIDE_LEFT, INSIDE_RIGHT, INSIDE_TOP, INSIDE_TOPLEFT, INSIDE_TOPRIGHT, OUTSIDE_LEFT, and OUTSIDE_RIGHT
Finally, the new setLegendXShift and setLegendYShift methods let you fine-tune the legend positions via pixel-based shifts away from these initial "base" positions.
To help you workaround such limitations, the new setLegend method lets you replace the built-in legend with a Widget of your own creation. Positioning options (see above) work exactly the same as for a built-in Legend. In fact, I suspect that a small GChart with an appropriately annotated one or two point curve corresponding to each curve on the main chart can serve as a much improved GChart Legend.
To workaround this problem, GChart now allows you to set hard limits (expressed in multiples of the plot area's pixel dimensions) beyond which points are simply dropped without being rendered at all.
Note that GChart by default renders such points and (when you have requested it) clips the so rendered points to the plot area. Though this default behavior is more accurate (since connecting lines to and from the far-off-the-plot-area points will still get rendered properly) it can be a lot slower if there are many such points.
Applications that manipulate axis limits to show a subset of a large point set should be able to get a substantial performance boost by using this feature, since rather than rendering and then clipping to the visible region, the out-of-bounds points are simply ignored.
With this release, explicitly setting a non-zero axis label thickness will cause GChart to leave the requested amount of space even if there is not actually any axis label specified.
In usage scenarios in which the tick label padding of an axis was specified after custom ticks were added, the tick label padding specification would be ignored. This bug is now fixed.
In previous releases, setFontFamily set the font family of the top-level GChart element, relying on the CSS cascade to thereby define the font-family of every lower level point annotation, tick label, legend label, title, or footnote.
This didn't always work. But, the problem only became obvious (and serious) after GWT introduced default stylesheets ("themes") that defined the font-family of the td element. Since GChart places all textual elements within tables to facilitate alignment, the td styling in these new, default, GWT stylesheets short-circuited the CSS cascade, and the GChart setFontFamily setting was ignored.
To correct this problem, GChart now makes the font-family setting at the td level, which overrides any stylesheet-based font-family settings that may be in effect. The CSS cascade can be tricky so there are likely still CSS settings that could cause font-family to get overridden inappropriately, but I think you would have to work a bit to make it happen now.
This bug corrects GChart issue #42. Much thanks to the person who reported this problem.
Note that if you just want to define a single font-family for all text on the chart you don't need to bother with these methods. Whenever these more fine-grained fontFamily properties are null (their default), the top-level fontFamily setting made via theGChart.setFontFamily is automatically used at the lower level.
Finally, if you prefer to use the CSS cascade exclusively to define font-family (in general, you'll have to modify any explicit td or similar font-family stylings if you take this route) just use theGChart.setFontFamily(GChart.USE_CSS) and leave these new, finer-grained, fontFamily properties at their default value (null).
For example, the LayZLine™ chart editor in the live demo uses these methods to provide near-instantaneous "drag feedback". Initially, we tried to implement this feature by simply re-rendering the entire chart after shifting each point's position appropriately. Though that also "worked" it was too slow to produce the illusion of direct manipulation.
Another potential application for this new feature is animations (a "flying pie chart" demo is waiting in the wings).
Earlier GChart versions supported only a single, chart-wide, clipToPlotArea attribute: either all curves were clipped to the plot area, or none of them were.
That proved too restrictive for some applications. For example, most curves on the live demo's LayZLine™ chart editing example are clipped to the plot area. But its help system is implemented via popup hover text associated with a single-point curve placed outside of the plot area--so this "hover-help" curve must not be clipped to the plot area.
The previous, chart-wide, attribute is now the default for any curves that don't explicitly set their own clipToPlotArea attribute.
Previously, you had to make a "do nothing" change to the curve's properties to force such an update.
The getCurrentCurveData method allows you to retrieve this reference from within code you write to implement GChart's GChartCanvasLite interface (used to plug GChart into an external GWT vector graphics library such as GWTCanvas).
The oil price simulation chart of the live demo uses this feature to retrieve a "tension" parameter it needs to define the "curvyness" of connecting lines.
It was found empirically that some browsers behave unpredictably if the total number of pixels on a rendering canvas gets too large. In addition, large rendering canvases can use inordinate amounts of memory in Firefox. This method was added to make it easy for you to workaround such problems without having to explicitly control the size of the rendering canvas, which is typically defined implicitly as the smalest rectangle that can contain all of the rendered points of the associated curve.
By default, this factor is zero which leaves GChart free to drop off-the-clipping-region content, speeding rendering in the common case when such a "shift into view" functionality isn't required.
The live demo's LayZLine™ chart editor uses a render padding factor of 1.5 to allow the user to drag the chart 1.5 screenfuls in any direction without having to do an explicit curve redraw, thus creating the illusion of direct manipulation.
In such cases, the algorithm used to "shrink wrap" the canvas around a curve's point set won't always provide enough space for such curvy lines, because their curves can "overshoot" the smallest rectangle that contains the curve's point set.
This method allows you to expand the canvas rectangle a bit, so that such curvy connecting lines don't get clipped. This feature could possibly be useful for similar advanced applications, where the containing rectangle computed under the assumption of straight connecting lines isn't quite big enough to hold the vector-graphic-rendered content.
I also added @Override markers to various methods that lacked them previously.
"I'd rather be a real person impersonating a fake expert than a fake person impersonating a real expert." -- Groucho Marx
For the curvy connecting lines, I have to thank the authors of jFreeChart, since several pages of code written by them that implemented Bezier curve support was incorporated into a GChart example that was posted onto the GChart issue tracker by a person who claimed (even affixing his own copyright notice to the top) that he had written that code himself.
Though none of that jFreeChart code was used in my implementation, the fact that the jFreeChart authors had written it, and made it freely available, was materially important to the proof of concept for this feature.
The plagiarist of the jFreeChart code also posted example code that helped motivate changes in this release intended to make implementing pan and zoom type features easier. Though none of his code was used in GChart, his posts motivated these new features, and I gratefully acknowledge that.
But, it isn't fair to the authors of jFreeChart to copy several pages of their carefully crafted Bezier curve code and then claim that you wrote it yourself. I strongly deprecate this behavior. By engaging in it this person has lost the respect that his good suggestions would have otherwise entitled him to. So, while I'm flattered that someone with his level of skill took an interest in GChart, I request that he refrain from any future posts on our issue tracker.