JavaFX将ArrayList中存储的形状展示在Pane时圆形不显示问题
问题原因分析
- 节点添加逻辑错误:
root.getChildren().addAll(circleList)只会在执行时把列表中当时存在的元素添加到Pane中,后续你往circleList里新增元素不会自动同步到Pane的显示节点列表里,所以新的圆根本没有被加到渲染树中,自然不会显示。 - 全局复用同一个Circle实例:你代码里全程只用了初始化时创建的唯一一个Circle对象,每次修改属性都会覆盖之前的配置,就算显示也只能同时存在一个圆,满足不了创建多个圆形的需求。
修复方案
- 去掉初始化时的
root.getChildren().addAll(circleList)代码,改为每次确认创建新圆后主动将新Circle实例添加到root的子节点中 - 每次首次点击开始画圆时新建Circle实例,不要复用同一个对象
- 可以保留
circleList做后续的圆形管理(比如修改、删除),但不要依赖它来同步渲染节点
修正后的关键代码片段
// 只保留当前正在绘制的圆形的引用,不用全局提前创建 private Circle currentDrawingCircle; private Line line; private boolean isClicked = false; private ArrayList<Circle> circleList = new ArrayList<>(); @Override public void start(Stage primaryStage) { root = new Pane(); line = new Line(); root.getChildren().add(line); // 只提前加辅助线就行 root.setOnMousePressed(new mouseClick()); root.setOnMouseMoved(new moveMouse()); // 其余初始化代码保持不变 } // 鼠标点击事件的handle方法修改 @Override public void handle(MouseEvent e) { if (!isClicked) { if(e.getEventType() == MouseEvent.MOUSE_PRESSED){ // 每次新建独立的圆形实例 currentDrawingCircle = new Circle(); currentDrawingCircle.setRadius(0); currentDrawingCircle.setCenterX(e.getSceneX()); currentDrawingCircle.setCenterY(e.getSceneY()); currentDrawingCircle.setStroke(Color.RED); currentDrawingCircle.setFill(Color.TRANSPARENT); // 新建后立刻加到Pane中,才能实时显示拖拽过程的预览 root.getChildren().add(currentDrawingCircle); line.setStartX(e.getSceneX()); line.setStartY(e.getSceneY()); line.setStroke(Color.RED); isClicked = true; circleList.add(currentDrawingCircle); } } else { currentDrawingCircle.setRadius(getRadius(e.getSceneX(),e.getSceneY(),currentDrawingCircle.getCenterX(), currentDrawingCircle.getCenterY())); currentDrawingCircle.setStroke(Color.GREEN); line.setStroke(Color.TRANSPARENT); isClicked = false; } } // 鼠标移动事件的handle方法里把原来的全局circle替换成currentDrawingCircle即可 @Override public void handle(MouseEvent e) { if (isClicked) { currentDrawingCircle.setRadius(getRadius(e.getSceneX(),e.getSceneY(),currentDrawingCircle.getCenterX(), currentDrawingCircle.getCenterY())); line.setEndX(e.getSceneX()); line.setEndY(e.getSceneY()); } }
内容的提问来源于stack exchange,提问作者user15554594
相关产品推荐
相关产品推荐

