Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Logarithmic Axis Labels/Ticks Customization

I am using the JFreeChart API to generate some chart in my Java application. In one of my charts, I try to use the LogAxis object to make my y-axis a log-scale axis (A in the figure) by the following code:

LogAxis logAxis = new LogAxis("Price($)");
logAxis.setMinorTickMarksVisible(true);
logAxis.setAutoRange(true);
xyplot.setRangeAxis(logAxis);

enter image description here

Then I got a y-axis in log-scale with ticks like 10^n (like figure A). I want to make it like B, which is more intuitive to the user, and each interval represents different values, as shown in the figure, 2->4, 4->8, 8->16, the interval grows as 2^n. Something minor is that, the intervals are displaying equally wide even if they are representing different value. However, when O try to achieve this by the following code :

LogAxis logAxis = new LogAxis("Price($)");
logAxis.setBase(2);
logAxis.setTickUnit(new NumberTickUnit(2));
logAxis.setMinorTickMarksVisible(true);
logAxis.setAutoRange(true);
xyplot.setRangeAxis(logAxis);

What I get is something like figure C.

How can I achieve figure B?

like image 759
Biscuitz Avatar asked Apr 27 '12 08:04

Biscuitz


People also ask

How do I create a custom tick in MatPlotLib?

Set the figure size and adjust the padding between and around the subplots. Create lists for height, bars and y_pos data points. Make a bar plot using bar() method. To customize X-axis ticks, we can use tick_params() method, with color=red, direction=outward, length=7, and width=2.

What is a tick mark on an axis?

A tick is a short line on an axis. For category axes, ticks separate each category. For value axes, ticks mark the major divisions and show the exact point on an axis that the axis label defines. Ticks are always the same color and line style as the axis. Ticks come in two types: major and minor.

How do I reduce the number of ticks in MatPlotLib?

Still, if we want only the first three values of the x-axis to visualize, you can use this xlim() and ylim() function to set a limit for the x-axis and y-axis of the plot and then use the locate param to reduce the number of ticks.


2 Answers

Even though you're using a LogAxis, you can specify integer tick units, as shown in the variation of @amaidment's example below.

LogAxis

/** @see http://stackoverflow.com/a/10353270/230513 */
private static void createFrame() {
    XYSeries series = new XYSeries("Series");
    for (int i = 0; i <= N; i++) {
        series.add(i, Math.pow(2, i));
    }
    NumberAxis xAxis = new NumberAxis("X");
    xAxis.setStandardTickUnits(NumberAxis.createIntegerTickUnits());
    LogAxis yAxis = new LogAxis("Y");
    yAxis.setBase(2);
    yAxis.setStandardTickUnits(NumberAxis.createIntegerTickUnits());
    XYPlot plot = new XYPlot(new XYSeriesCollection(series),
        xAxis, yAxis, new XYLineAndShapeRenderer(true, false));
    JFreeChart chart = new JFreeChart(
        "Chart", JFreeChart.DEFAULT_TITLE_FONT, plot, false);
    JFrame frame = new JFrame("LogAxis Test");
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    frame.setContentPane(new ChartPanel(chart));
    frame.pack();
    frame.setVisible(true);
}

public static void main(String[] args) {
    EventQueue.invokeLater(new Runnable() {

        @Override
        public void run() {
            createFrame();
        }
    });
}
like image 103
trashgod Avatar answered Oct 16 '22 12:10

trashgod


I think what you need is logAxis.setNumberFormatOverride(NumberFormat format);

EDIT: Since further help is needed... try this:

logAxis.setBase(10);
LogFormat format = new LogFormat(logAxis.getBase(), "", "", true);
logAxis.setNumberFormatOverride(format);

Here's a whole method that can be used to play with...:

  public static void main(String[] args) {
    XYSeries series = new XYSeries("");
    series.add(1, 10);
    series.add(2, 100);
    series.add(3, 1000);
    series.add(4, 10000);
    series.add(5, 100000);
    series.add(6, 1000000);

//    NumberAxis yAxis = new NumberAxis("");
    LogAxis yAxis = new LogAxis("");
    yAxis.setBase(10);
    LogFormat format = new LogFormat(yAxis.getBase(), "", "", true);
    yAxis.setNumberFormatOverride(format);
    XYPlot plot = new XYPlot(
      new XYSeriesCollection(series),
      new NumberAxis(""),
      yAxis,
      new XYLineAndShapeRenderer(true, false));
    JFreeChart chart = new JFreeChart("", JFreeChart.DEFAULT_TITLE_FONT, plot, false);

    JFrame frame = new JFrame("LogAxis Test");
    frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    frame.setContentPane(new ChartPanel(chart));
    frame.pack();
    frame.setVisible(true);
  }
like image 23
amaidment Avatar answered Oct 16 '22 12:10

amaidment