谁能解释为什么我在 JavaFX 中创建按钮时我的场景会失去颜色?
以下代码有效,场景背景变为红色
@Override
public void start(Stage primaryStage){
//Set Primary stage title and create a rootNode
primaryStage.setTitle("Hello World");
FlowPane rootNode = new FlowPane();
//Create a scene and add it to the rootNode
Scene myScene = new Scene(rootNode, 300, 200, Color.RED);
//Add the scene to the stage
primaryStage.setScene(myScene);
//Show the stage
primaryStage.show();
}
但是,当我创建另一个控件时,例如以下示例中的按钮(我什至不必将其添加到流程窗格中(,颜色将恢复为灰色。
@Override
public void start(Stage primaryStage){
//Set Primary stage title and create a rootNode
primaryStage.setTitle("Hello World");
FlowPane rootNode = new FlowPane();
//Create a scene and add it to the rootNode
Scene myScene = new Scene(rootNode, 300, 200, Color.CORAL);
Button newBtn = new Button();
//Add the scene to the stage
primaryStage.setScene(myScene);
//Show the stage
primaryStage.show();
}
有人知道这是为什么吗?我是否尝试错误地更改背景颜色?
你的场景背景色根本不应该可见,因为rootNode
覆盖了整个场景,并且rootNode
有自己的背景颜色,该背景颜色在默认的 JavaFx 主题中设置(这是你看到的灰色(:
//modena.css
.root {
...
/***************************************************************************
* *
* Set the default background color for the scene *
* *
**************************************************************************/
-fx-background-color: -fx-background;
}
因此,您需要更改rootNode
的背景颜色 ,正如另一个答案已经建议的那样。
剩下的问题是,为什么在第一个示例中,默认的根背景色不应用于rootNode
(它是透明的,不应该是透明的(,而你会看到场景的背景色。
答案 - 这可能是一个错误。在 JavaFx 中,缺省主题是使用方法PlatformImpl.setDefaultPlatformUserAgentStylesheet()
设置的,该方法仅在以下情况下调用:
- 当您呼叫
Application.setUserAgentStylesheet
时(来源( - 在
Control
和PopupControl
类(源和源(的静态初始值设定项块中
FlowPane
既不扩展Control
也不扩展PopupControl
,因此JavaFx甚至不会加载默认主题,并且您的rootNode
保持透明(您会看到场景的背景颜色(。
在另一个示例中,您创建了一个扩展类Control
Button
控件,因此将执行Control
类的静态初始值设定项块并加载默认 modena 主题 - 您的rootPane
从默认主题获取其默认灰色,并且您不再看到场景的背景色。
TL;DR将rootPane
的背景色设置为所需的颜色或Color.TRANSPARENT
。
这是一个非常奇怪的案例。
最初创建Button
时,将在 Button 的构造函数中调用initialize
方法:
private void initialize() {
getStyleClass().setAll(DEFAULT_STYLE_CLASS);
setAccessibleRole(AccessibleRole.BUTTON);
setMnemonicParsing(true); // enable mnemonic auto-parsing by default
}
我假设(但我不能 100% 肯定地告诉您(这会将样式应用于应用程序中的元素(如本答案中所述,这是因为静态初始值设定项(,因为如果您创建一个Button
(甚至不将其添加到您的rootNode
中(,rootNode
将在调用primaryStage.show()
后具有背景。为了证明这一点,我修改了您的代码:
System.out.println("background: " + rootNode.getBackground());
Button newBtn = new Button();
primaryStage.setScene(myScene);
primaryStage.show();
System.out.println("background after showing scene: " + rootNode.getBackground());
输出如下所示(背景颜色为灰色(:
background: null
background after showing scene: javafx.scene.layout.Background@20c95282
如果我删除按钮创建并再次运行它,背景颜色为红色,我有以下输出:
background: null
background after showing scene: null
所以我建议你要么将背景颜色设置为rootNode
,要么将rootNode
的背景颜色显式设置为透明(Color.TRANSPARENT
(。这两种解决方案都对我有用。
rootNode.setBackground(new Background(new BackgroundFill(Color.CORAL, null, null)));