Is there a good way to scale the fonts on a chart (I'm using a servlet that returns a PNG stream) so that as I increase the width not only the chart scales up in size but the fonts do as well?
I've come up with a way to do it, but I didn't know if there was an easier setting in JFreeChart that does this for me. Right now I go through the work of pulling the Font objects out of each text piece (axis labels, legend items, titles) and scaling them manually. Here's my example of scaling a tick label:
// after creating the chart
Plot plot = chart.getPlot();
HorizontalCategoryAxis cAxis = (HorizontalCategoryAxis)plot.getAxis(Plot.HORIZONTAL_AXIS);
axisFont = cAxis.getTickLabelFont();
axisFont = axisFont.deriveFont((float)axisFont.getSize() * scale);
cAxis.setTickLabelFont(axisFont);
Where scale is a float value that tells me how to scale. I set this by calling a width of 400 my baseline and then calculating the scale off of that using the width passed to the servlet:
// default width to 400
int width = 400;
try {
// grab width passed to servlet
width = Integer.parseInt( req.getParameter( "width" ) );
}
catch (Exception e) {
}
// determine scale value
float scale = (float)width / 400;
So, for now I'll keep doing this, but if there's an easier way to scale the entire chart I'd love to know.
Thanks,
David
Font scaling on Servlet-based chart?
Re: Font scaling on Servlet-based chart?
Hi David,
You can scale everything by applying an AffineTransform to the Graphics2D object.
In JFreeChartPanel I use this technique to handle small charts by drawing them at a larger size, then scaling them down to fit the available space. You could do the same thing, drawing your charts at some default size then scale them up to fit a larger image.
Regards,
DG.
You can scale everything by applying an AffineTransform to the Graphics2D object.
In JFreeChartPanel I use this technique to handle small charts by drawing them at a larger size, then scaling them down to fit the available space. You could do the same thing, drawing your charts at some default size then scale them up to fit a larger image.
Regards,
DG.
Re: Font scaling on Servlet-based chart?
Ok, so let me see if I understand. I would have to not use the ChartUtilities function for writeChartAsPNG, instead I would make my own function similar to createBufferedImage, but do something like this:
double desiredWidth = 0.0;
double desiredHeight = 0.0;
double defaultWidth = 400.0;
double defaultHeight = 300.0;
boolean scale = false;
// get desired width and height from somewhere then...
if (desiredWidth > 0 || desiredHeight > 0) {
scale = true
}
double scaleX = desiredWidth/defaultWidth;
double scaleY = desiredHeight/defaultHeight;
BufferedImage image = new BufferedImage(desiredWidth , desiredHeight, BufferedImage.TYPE_INT_RGB);
Graphics2D g2 = image.createGraphics();
if (scale) {
AffineTransform saved = g2.getTransform();
g2.transform(AffineTransform.getScaleInstance(scaleX, scaleY));
chart.draw(g2, new Rectangle2D.Double(0, 0, defaultWidth, defaultHeight), null);
g2.setTransform(saved);
g2.dispose();
}
else chart.draw(g2, new Rectangle2D.Double(0, 0, defaultWidth, defaultHeight), null);
return image;
And then write that out as a PNG or JPEG using similar functions to what's in ChartUtilities. Sound close?
I'll give that a shot.
Thanks,
David
double desiredWidth = 0.0;
double desiredHeight = 0.0;
double defaultWidth = 400.0;
double defaultHeight = 300.0;
boolean scale = false;
// get desired width and height from somewhere then...
if (desiredWidth > 0 || desiredHeight > 0) {
scale = true
}
double scaleX = desiredWidth/defaultWidth;
double scaleY = desiredHeight/defaultHeight;
BufferedImage image = new BufferedImage(desiredWidth , desiredHeight, BufferedImage.TYPE_INT_RGB);
Graphics2D g2 = image.createGraphics();
if (scale) {
AffineTransform saved = g2.getTransform();
g2.transform(AffineTransform.getScaleInstance(scaleX, scaleY));
chart.draw(g2, new Rectangle2D.Double(0, 0, defaultWidth, defaultHeight), null);
g2.setTransform(saved);
g2.dispose();
}
else chart.draw(g2, new Rectangle2D.Double(0, 0, defaultWidth, defaultHeight), null);
return image;
And then write that out as a PNG or JPEG using similar functions to what's in ChartUtilities. Sound close?
I'll give that a shot.
Thanks,
David
Re: Font scaling on Servlet-based chart?
That's the kind of thing I had in mind. Let me know if it works - it might be worth incorporating it somehow as a general feature.
DG.
DG.