Can PieChart from JavaFX be displayed as a doughnut?

前端 未结 1 782
走了就别回头了
走了就别回头了 2020-12-18 09:10

I\'m using javafx.scene.chart.PieChart in my Java app which is built using Java7. Is there a way of making the PieChart hollow - turning it into a doughnut?

相关标签:
1条回答
  • 2020-12-18 10:07

    Yep, you can use a DoughnutChart class.

    doughnut

    *DoughnutChart.java**

    import javafx.collections.ObservableList;
    import javafx.geometry.Bounds;
    import javafx.scene.Node;
    import javafx.scene.chart.PieChart;
    import javafx.scene.layout.Pane;
    import javafx.scene.paint.Color;
    import javafx.scene.shape.Circle;
    
    public class DoughnutChart extends PieChart {
        private final Circle innerCircle;
    
        public DoughnutChart(ObservableList<Data> pieData) {
            super(pieData);
    
            innerCircle = new Circle();
    
            // just styled in code for demo purposes,
            // use a style class instead to style via css.
            innerCircle.setFill(Color.WHITESMOKE);
            innerCircle.setStroke(Color.WHITE);
            innerCircle.setStrokeWidth(3);
        }
    
        @Override
        protected void layoutChartChildren(double top, double left, double contentWidth, double contentHeight) {
            super.layoutChartChildren(top, left, contentWidth, contentHeight);
    
            addInnerCircleIfNotPresent();
            updateInnerCircleLayout();
        }
    
        private void addInnerCircleIfNotPresent() {
            if (getData().size() > 0) {
                Node pie = getData().get(0).getNode();
                if (pie.getParent() instanceof Pane) {
                    Pane parent = (Pane) pie.getParent();
    
                    if (!parent.getChildren().contains(innerCircle)) {
                        parent.getChildren().add(innerCircle);
                    }
                }
            }
        }
    
        private void updateInnerCircleLayout() {
            double minX = Double.MAX_VALUE, minY = Double.MAX_VALUE;
            double maxX = Double.MIN_VALUE, maxY = Double.MIN_VALUE;
            for (PieChart.Data data: getData()) {
                Node node = data.getNode();
    
                Bounds bounds = node.getBoundsInParent();
                if (bounds.getMinX() < minX) {
                    minX = bounds.getMinX();
                }
                if (bounds.getMinY() < minY) {
                    minY = bounds.getMinY();
                }
                if (bounds.getMaxX() > maxX) {
                    maxX = bounds.getMaxX();
                }
                if (bounds.getMaxY() > maxY) {
                    maxY = bounds.getMaxY();
                }
            }
    
            innerCircle.setCenterX(minX + (maxX - minX) / 2);
            innerCircle.setCenterY(minY + (maxY - minY) / 2);
    
            innerCircle.setRadius((maxX - minX) / 4);
        }
    }
    

    DoughnutChartSample.java

    import javafx.application.Application;
    import javafx.collections.*;
    import javafx.scene.Scene;
    import javafx.scene.chart.PieChart;
    import javafx.scene.layout.StackPane;
    import javafx.stage.Stage;
    
    public class DoughnutChartSample extends Application {
    
        @Override public void start(Stage stage) {
            stage.setTitle("Imported Fruits");
            stage.setWidth(500);
            stage.setHeight(500);
    
            ObservableList<PieChart.Data> pieChartData = createData();
    
            final DoughnutChart chart = new DoughnutChart(pieChartData);
            chart.setTitle("Imported Fruits");
    
            Scene scene = new Scene(new StackPane(chart));
            stage.setScene(scene);
            stage.show();
        }
    
        private ObservableList<PieChart.Data> createData() {
            return FXCollections.observableArrayList(
                    new PieChart.Data("Grapefruit", 13),
                    new PieChart.Data("Oranges", 25),
                    new PieChart.Data("Plums", 10),
                    new PieChart.Data("Pears", 22),
                    new PieChart.Data("Apples", 30));
        }
    
        public static void main(String[] args) {
            launch(args);
        }
    
    }
    
    0 讨论(0)
提交回复
热议问题