Comment faire pivoter les étiquettes de graduation sur le domaine d’un axe numérique dans JFreeChart?

Comme dans l’exemple suivant, je souhaite que les étiquettes de graduation sur le domaine du graphique soient tournées de 45 degrés comme indiqué dans ce graphique: http://left.subtree.org/2007/08/14/rotate -labels-jfreechart /

La différence est que je veux le faire sur un nuage de points avec un axe numérique. Je ne trouve pas d’équivalent à setCategoryLabelPositions () dans la classe NumberAxis.

La méthode setVerticalTickLabels() peut être une alternative. Sinon, je ne vois pas d’autre choix que de remplacer refreshTicksHorizontal() . Voir aussi cet exemple .

entrez la description de l'image ici

 import java.awt.Color; import java.awt.Dimension; import java.util.*; import org.jfree.chart.*; import org.jfree.chart.axis.NumberAxis; import org.jfree.chart.plot.PlotOrientation; import org.jfree.chart.plot.XYPlot; import org.jfree.chart.renderer.xy.XYItemRenderer; import org.jfree.data.xy.XYDataset; import org.jfree.data.xy.XYSeries; import org.jfree.data.xy.XYSeriesCollection; import org.jfree.ui.ApplicationFrame; import org.jfree.ui.RefineryUtilities; /** * @see https://stackoverflow.com/questions/7208657 * @see https://stackoverflow.com/questions/7071057 */ public class ScatterTickLabels extends ApplicationFrame { public ScatterTickLabels(Ssortingng s) { super(s); final ChartPanel chartPanel = createDemoPanel(); chartPanel.setPreferredSize(new Dimension(640, 480)); this.add(chartPanel); } public static ChartPanel createDemoPanel() { JFreeChart jfreechart = ChartFactory.createScatterPlot( "Scatter Plot Demo", "X", "Y", samplexydataset(), PlotOrientation.VERTICAL, true, true, false); XYPlot xyPlot = (XYPlot) jfreechart.getPlot(); xyPlot.setDomainCrosshairVisible(true); xyPlot.setRangeCrosshairVisible(true); XYItemRenderer renderer = xyPlot.getRenderer(); renderer.setSeriesPaint(0, Color.blue); NumberAxis domain = (NumberAxis) xyPlot.getDomainAxis(); domain.setVerticalTickLabels(true); return new ChartPanel(jfreechart); } private static XYDataset samplexydataset() { int cols = 20; int rows = 20; XYSeriesCollection xySeriesCollection = new XYSeriesCollection(); XYSeries series = new XYSeries("Random"); Random rand = new Random(); for (int i = 0; i < rows; i++) { for (int j = 0; j < cols; j++) { double x = rand.nextGaussian(); double y = rand.nextGaussian(); series.add(x, y); } } xySeriesCollection.addSeries(series); return xySeriesCollection; } public static void main(String args[]) { ScatterTickLabels demo = new ScatterTickLabels("Scatter Plot Demo"); demo.pack(); RefineryUtilities.centerFrameOnScreen(demo); demo.setVisible(true); } } 

La première réponse donnée concerne un axe de domaine numérique. Si vous avez un axe de catégorie, vous voulez ce code:

 CategoryAxis domainAxis = plot.getDomainAxis(); domainAxis.setCategoryLabelPositions(CategoryLabelPositions.UP_90); 

Vous devez regarder la super classe: Axis.setLabelAngle (rad) .

Et voici un exemple .

EDIT : ci-dessus n’était pas utile, désolé.

J’ai regardé le code de org.jfreechart.chart.axis.NumberAxis.refreshTicksHorizontal. Il existe en fait un angle défini sur 0.0 (dernier argument de tous les new NumberTick(...,0.0) ). Vous pouvez créer une sous-classe de NumberAxis qui remplace la méthode refreshTicksHorizontal par une autre utilisant un angle différent (spécifié dans votre constructeur).

Il semble que refreshTicks soit toujours appelé lors du tracé du graphique, vous n’avez donc pas à vous soucier de ne pas l’appeler.

 /** * Calculates the positions of the tick labels for the axis, storing the * results in the tick label list (ready for drawing). * * @param g2 the graphics device. * @param dataArea the area in which the data should be drawn. * @param edge the location of the axis. * * @return A list of ticks. */ protected List refreshTicksHorizontal(Graphics2D g2, Rectangle2D dataArea, RectangleEdge edge) { List result = new java.util.ArrayList(); Font tickLabelFont = getTickLabelFont(); g2.setFont(tickLabelFont); if (isAutoTickUnitSelection()) { selectAutoTickUnit(g2, dataArea, edge); } TickUnit tu = getTickUnit(); double size = tu.getSize(); int count = calculateVisibleTickCount(); double lowestTickValue = calculateLowestVisibleTickValue(); if (count <= ValueAxis.MAXIMUM_TICK_COUNT) { int minorTickSpaces = getMinorTickCount(); if (minorTickSpaces <= 0) { minorTickSpaces = tu.getMinorTickCount(); } for (int minorTick = 1; minorTick < minorTickSpaces; minorTick++) { double minorTickValue = lowestTickValue - size * minorTick / minorTickSpaces; if (getRange().contains(minorTickValue)){ result.add(new NumberTick(TickType.MINOR, minorTickValue, "", TextAnchor.TOP_CENTER, TextAnchor.CENTER, 0.0)); } } for (int i = 0; i < count; i++) { double currentTickValue = lowestTickValue + (i * size); String tickLabel; NumberFormat formatter = getNumberFormatOverride(); if (formatter != null) { tickLabel = formatter.format(currentTickValue); } else { tickLabel = getTickUnit().valueToString(currentTickValue); } TextAnchor anchor = null; TextAnchor rotationAnchor = null; double angle = 0.0; if (isVerticalTickLabels()) { anchor = TextAnchor.CENTER_RIGHT; rotationAnchor = TextAnchor.CENTER_RIGHT; if (edge == RectangleEdge.TOP) { angle = Math.PI / 2.0; } else { angle = -Math.PI / 2.0; } } else { if (edge == RectangleEdge.TOP) { anchor = TextAnchor.BOTTOM_CENTER; rotationAnchor = TextAnchor.BOTTOM_CENTER; } else { anchor = TextAnchor.TOP_CENTER; rotationAnchor = TextAnchor.TOP_CENTER; } } Tick tick = new NumberTick(new Double(currentTickValue), tickLabel, anchor, rotationAnchor, angle); result.add(tick); double nextTickValue = lowestTickValue + ((i + 1)* size); for (int minorTick = 1; minorTick < minorTickSpaces; minorTick++) { double minorTickValue = currentTickValue + (nextTickValue - currentTickValue) * minorTick / minorTickSpaces; if (getRange().contains(minorTickValue)){ result.add(new NumberTick(TickType.MINOR, minorTickValue, "", TextAnchor.TOP_CENTER, TextAnchor.CENTER, 0.0)); } } } } return result; }