JavaFX中Pane需先添加文本才能加载全部子节点问题求助
JavaFX窗口仅在Mac菜单栏显示,添加Text才正常的问题解决
嘿,我在Mac上开发JavaFX时碰到过一模一样的问题!你的情况根源在于初始阶段布局没有明确的尺寸约束,导致窗口无法正常初始化显示。
问题原因
当你的Pane里只有那些绑定了Pane自身尺寸的形状(椭圆、圆弧、直线)时,程序启动初期Pane的宽高都是0——因为这些形状的尺寸完全依赖于Pane,没有任何子节点能给Pane提供一个初始的最小尺寸。这种情况下,Scene也没有了初始大小,Mac的窗口管理器就会出现“只在菜单栏显示程序,窗口不可见也无法交互”的异常状态。
而当你添加Text后,Text有自己的固有尺寸,Pane会基于这个尺寸计算出初始大小,Scene也就有了合适的初始尺寸,窗口自然就能正常显示和交互了。
解决方案
你不需要依赖那个测试用的Text,只需要给Scene或者Pane设置一个初始尺寸约束就行,这里有两种简单的方法:
方法1:给Scene设置初始宽高
修改Scene的创建代码,直接指定初始尺寸,这样不管Pane有没有提供初始尺寸,窗口都会以这个大小启动,后续还能正常自适应缩放:
// 创建Scene时指定初始宽高,比如600x400 Scene scene = new Scene(pane, 600, 400);
方法2:给Pane设置最小尺寸
给Pane设置一个最小宽高,让它有初始的尺寸约束:
// 创建Pane后添加这行代码 pane.setMinSize(400, 300);
修改后的示例代码
比如用方法1修改你的代码,去掉Text也能正常运行:
import javafx.application.Application; import javafx.scene.Scene; import javafx.scene.layout.Pane; import javafx.scene.paint.Color; import javafx.scene.shape.Arc; import javafx.scene.shape.ArcType; import javafx.scene.shape.Ellipse; import javafx.scene.shape.Line; import javafx.stage.Stage; public class CylinderResize extends Application { @Override public void start(Stage primaryStage) { //Create Pane Pane pane = new Pane(); // 给Scene设置初始尺寸 Scene scene = new Scene(pane, 600, 400); //Create Elipse for top Ellipse ellipse = new Ellipse(); ellipse.centerXProperty().bind(pane.widthProperty().divide(2)); ellipse.centerYProperty().bind(pane.heightProperty().divide(3)); ellipse.radiusXProperty().bind(pane.widthProperty().divide(4)); ellipse.radiusYProperty().bind(pane.heightProperty().divide(8)); ellipse.setStroke(Color.BLACK); ellipse.setFill(Color.WHITE); //Create Solid arch for bottom Arc solidArc = new Arc(); solidArc.centerXProperty().bind(pane.widthProperty().divide(2)); solidArc.centerYProperty().bind(pane.heightProperty().multiply(2).divide(3)); solidArc.radiusXProperty().bind(pane.widthProperty().divide(4)); solidArc.radiusYProperty().bind(pane.heightProperty().divide(8)); solidArc.setStartAngle(180); solidArc.setLength(180); solidArc.setType(ArcType.OPEN); solidArc.setStroke(Color.BLACK); solidArc.setFill(Color.WHITE); //Create dashed line for bottom Arc dashedArc = new Arc(); dashedArc.centerXProperty().bind(pane.widthProperty().divide(2)); dashedArc.centerYProperty().bind(pane.heightProperty().multiply(2).divide(3)); dashedArc.radiusXProperty().bind(pane.widthProperty().divide(4)); dashedArc.radiusYProperty().bind(pane.heightProperty().divide(8)); dashedArc.setStartAngle(0); dashedArc.setLength(180); dashedArc.setType(ArcType.OPEN); dashedArc.setFill(Color.WHITE); dashedArc.setStroke(Color.BLACK); dashedArc.getStrokeDashArray().addAll(6.0, 21.0); //Create Vertical Lines for the sides Line leftLine = new Line(); leftLine.startXProperty().bind(ellipse.centerXProperty().subtract(ellipse.radiusXProperty())); leftLine.startYProperty().bind(ellipse.centerYProperty()); leftLine.endXProperty().bind(solidArc.centerXProperty().subtract(solidArc.radiusXProperty())); leftLine.endYProperty().bind(solidArc.centerYProperty()); leftLine.setStroke(Color.BLACK); Line rightLine = new Line(); rightLine.startXProperty().bind(ellipse.centerXProperty().add(ellipse.radiusXProperty())); rightLine.startYProperty().bind(ellipse.centerYProperty()); rightLine.endXProperty().bind(solidArc.centerXProperty().add(solidArc.radiusXProperty())); rightLine.endYProperty().bind(solidArc.centerYProperty()); rightLine.setStroke(Color.BLACK); // 去掉Text,直接添加形状 pane.getChildren().addAll(ellipse, solidArc, dashedArc, leftLine, rightLine); //Set Up Stage primaryStage.setTitle("Ellipse that scales"); primaryStage.setScene(scene); primaryStage.show(); } }
现在运行这个修改后的代码,窗口就能正常显示,而且圆柱体也会随着窗口大小变化自适应缩放啦!
内容的提问来源于stack exchange,提问作者DntMesArnd
相关产品推荐
相关产品推荐

