OcR19
OcR19

Reputation: 23

JFreeChart show one single value

I have a chart where I display the values of a table (stock and date). The stock is displayed in the y axis and the dates in the x axis. As long as the query returns 2 entries, it is shown normally as a line, but if the query returns only one entry, nothing is shown (there should be a point there).

Any suggestions on how to fix this would be highly appreciated.

2 entries: enter image description here

1 entry: enter image description here

Code (the chart is built in an action listener):

        historyButton.addActionListener(e -> {
        // stock list and dates list retrieved from database
            int articleNr = Integer.parseInt(articleIDText.getText());
            List<Integer> displayStockHistory;
            List<String> displayDatesStockHistory;

            try {
                displayStockHistory = business.displayStockHistory(articleNr);
            } catch (Exception ex) {
                throw new RuntimeException(ex);
            }
            try {
                displayDatesStockHistory = business.displayDatesStockHistory(articleNr);
            } catch (Exception ex) {
                throw new RuntimeException(ex);
            }
            DefaultCategoryDataset  dataset = new DefaultCategoryDataset();
            
            // add db values to the dataset
            for(int i = 0; i < displayStockHistory.size(); i++){
                dataset.addValue(displayStockHistory.get(i), "Articles in Stock", displayDatesStockHistory.get(i));
            }
            
            // compose chart
            JFreeChart chart = ChartFactory.createLineChart(
                    "Stock History",
                    "Date",
                    "Stock",
                    dataset,
                    PlotOrientation.VERTICAL,
                    true,
                    true,
                    false);

            chart.setBackgroundPaint(c2);
            chart.getTitle().setPaint(c3);

            CategoryPlot p = chart.getCategoryPlot();
            p.setForegroundAlpha(0.9f);

            CategoryItemRenderer renderer = p.getRenderer();
            //renderer.setSeriesPaint(0, c4);
            renderer.setSeriesStroke( 0, new BasicStroke( 5 ) );

            chart.getCategoryPlot().setBackgroundPaint(c1);
            ChartPanel chartPanel = new ChartPanel(chart);
            chartPanel.setBackground(c2);
            chartScrollPane.getViewport().add(chartPanel);
            chartPanel.setPreferredSize(new Dimension(2000, 270));
            ChartFrame frame1 = new ChartFrame("Line graph", chart);

            frame1.setVisible(true);
            frame1.setSize(500, 400);
        });
    }

Upvotes: 1

Views: 197

Answers (1)

trashgod
trashgod

Reputation: 205775

Your chosen chart factory instantiates a LineAndShapeRenderer, so one approach is to make the renderer's shapes visible for all series, as shown here; note that the API has changed:

CategoryPlot plot = (CategoryPlot) chart.getPlot();
LineAndShapeRenderer r = (LineAndShapeRenderer) plot.getRenderer();
r.setDefaultShapesVisible(true);

To enable shapes only for series having a single, non-null value, you'll have to iterate through the data explicitly:

DefaultCategoryDataset data = new DefaultCategoryDataset();
data.addValue(3, "Data1", LocalDate.now());
data.addValue(2, "Data2", LocalDate.now());
data.addValue(1, "Data2", LocalDate.now().plusDays(1));
…
for (int row = 0; row < data.getRowCount(); row++) {
    int count = 0;
    for (int col = 0; col < data.getColumnCount(); col++) {
        count += data.getValue(row, col) != null ? 1 : 0;
    }
    if (count == 1) {
        r.setSeriesShapesVisible(row, true);
    }
}

image

Upvotes: 1

Related Questions