在swing应用程序中显示一行(中位数,最小值,最大值,平均值)的简单统计数据

时间:2018-02-11 09:04:00

标签: java swing diagram

我希望在简单的一行(在Java,Swing中)显示一些统计数据。它应该是这样的:

enter image description here

但是经过几个小时的搜索,我无法找到这样的图表......我甚至都不知道它的名字......它看起来有点像时间线图上有里程碑......一个标准的lib会很棒...

有人有想法吗?任何提示?

2 个答案:

答案 0 :(得分:0)

我能建议的最接近的是带有JFreeChart的Box Chart:

JFreeChart Box and Whisker Demo

JFreeChart确实有一个非常陡峭的学习曲线,你需要决定是使用它的组件还是实现自己的JComponent。

答案 1 :(得分:0)

正如用户RealSceptic建议的那样,我设计了自己的图表。这是非常基本的,但可能对将来的某些人有帮助,所以我分享它:

public class BasicLineChart extends JPanel {

    /**
     * 
     */
    private static final long serialVersionUID = 1L;

    private static final int GRAPH_LINE_TOP_DISTANCE = 50;
    private static final int GRAPH_LINE_LEFT_RIGHT_DISTANCE = 30;

    private static final int VERTICAL_LINE_START_POS = 30;
    private static final int VERTICAL_LINE_END_POS = 70;

    private Map<String, Money> statisticData;


    /**
     * Sets the statistic data which is used to paint the graph
     * 
     * @param statisticData
     */
    public void setStatisticData(Map<String, Money> statisticData) {
        if (statisticData == null || statisticData.values() == null || statisticData.values().size() < 2)
            throw new IllegalArgumentException("There must be at least 2 static values to create this chart!");
        this.statisticData = statisticData;
    }

    private void __paintVerticalLine(Graphics2D g2d, Money currentValue, Money minValue, Money maxValue, String label) {
        int lineWidthPosition = GRAPH_LINE_LEFT_RIGHT_DISTANCE + __calcWidthPositionForVerticalLine(currentValue.getAmount(), minValue.getAmount(), maxValue.getAmount());
        g2d.drawLine(lineWidthPosition, VERTICAL_LINE_START_POS, lineWidthPosition, VERTICAL_LINE_END_POS);

        __drawString(g2d, label, lineWidthPosition, VERTICAL_LINE_START_POS - 5);
        __drawString(g2d, currentValue.toString(), lineWidthPosition, VERTICAL_LINE_END_POS + 20);
    }

    private void __drawString(Graphics2D g2d, String text, int lineWidthPosition, int verticalPosition) {
        int labelStartTextPosition = lineWidthPosition - (text.length()/2*7);
        g2d.drawString(text, labelStartTextPosition, verticalPosition);
    }

    private int __calcWidthPositionForVerticalLine(BigDecimal currentValue, BigDecimal minValue, BigDecimal maxValue) {
        BigDecimal percentage = __calcPositionInPercentage(currentValue, minValue, maxValue);
        int width = this.getWidth();
        width = width - (GRAPH_LINE_LEFT_RIGHT_DISTANCE * 2);
        BigDecimal result = new BigDecimal(width).multiply(percentage);
        return result.intValue();
    }

    private BigDecimal __calcPositionInPercentage(BigDecimal currentValue, BigDecimal minValue, BigDecimal maxValue) {
        if (currentValue.compareTo(maxValue) > 0 || currentValue.compareTo(minValue) < 0)
            throw new IllegalArgumentException("Value must be between min and maxvalue!");
        if (minValue.compareTo(currentValue) == 0)
            return BigDecimal.ZERO;
        if (maxValue.compareTo(currentValue) == 0)
            return BigDecimal.ONE;

        BigDecimal tmp = currentValue.subtract(minValue);
        return tmp.divide(maxValue.subtract(minValue), 5, RoundingMode.HALF_UP);
    }

    public void paintComponent(Graphics g) {
        super.paintComponent(g);

        Graphics2D g2d = (Graphics2D) g;
        g2d.setColor(Color.BLUE);
        Stroke stroke = new BasicStroke(5f, BasicStroke.CAP_SQUARE, BasicStroke.CAP_SQUARE);
        g2d.setStroke(stroke);

        //paint the horizontal line
        g2d.drawLine(GRAPH_LINE_LEFT_RIGHT_DISTANCE, GRAPH_LINE_TOP_DISTANCE, this.getWidth() - GRAPH_LINE_LEFT_RIGHT_DISTANCE,
                GRAPH_LINE_TOP_DISTANCE);

        //paint the vertical lines including the labels
        if (statisticData != null){
            Money minValue = Collections.min(statisticData.values());
            Money maxValue = Collections.max(statisticData.values());
            for (String label : this.statisticData.keySet()){
                __paintVerticalLine(g2d, this.statisticData.get(label), minValue, maxValue, label);
            }
        }
    }

}