创建完成之后直接运行即可:
前置条件(必须)
通过Maven原型创建项目:
如果在第四步中找不到对应原型需要手动添加:
接下来输入自己的项目信息:
编辑archetypeArtifactId
,如果使用FXML就使用javafx-archetype-fxml
,否则就使用javafx-archetype-simple
。
之后再添加一个属性指定JavaFX的版本:
点击完成即可创建,创建后的项目结构如下:
pom文件如下:
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0modelVersion>
<groupId>com.chinesecoolygroupId>
<artifactId>learn-javafxartifactId>
<version>1.0-SNAPSHOTversion>
<properties>
<project.build.sourceEncoding>UTF-8project.build.sourceEncoding>
<maven.compiler.source>11maven.compiler.source>
<maven.compiler.target>11maven.compiler.target>
properties>
<dependencies>
<dependency>
<groupId>org.openjfxgroupId>
<artifactId>javafx-controlsartifactId>
<version>17.0.1version>
dependency>
dependencies>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.pluginsgroupId>
<artifactId>maven-compiler-pluginartifactId>
<version>3.8.0version>
<configuration>
<release>11release>
configuration>
plugin>
<plugin>
<groupId>org.openjfxgroupId>
<artifactId>javafx-maven-pluginartifactId>
<version>0.0.6version>
<executions>
<execution>
<id>default-cliid>
<configuration>
<mainClass>com.chinesecooly.AppmainClass>
configuration>
execution>
executions>
plugin>
plugins>
build>
project>
接下来使用compiler插件编译项目:
最后使用javafx插件运行项目:
运行结果如下:
每个JavaFX应用都继承自Application
类(子类必须声明为public
,并且必须有一个公共的无参数构造函数)。当JavaFX应用启动时,会按顺序执行以下步骤:
Application
类的实例。init()
方法。start(javafx.stage.Stage)
方法。Platform.exit()
方法implicitExit
属性为true
stop()
方法。一个简单的例子如下:
public class HelloApplication extends Application {
@Override
public void start(Stage stage) throws IOException {
FXMLLoader fxmlLoader = new FXMLLoader(HelloApplication.class.getResource("hello-view.fxml"));
Scene scene = new Scene(fxmlLoader.load(), 320, 240);
stage.setTitle("Hello!");
stage.setScene(scene);
stage.show();
}
public static void main(String[] args) {
launch();
}
}
在main()
方法中调用了launch()
方法,实际上JavaFX应用启动时的六个步骤就是由此方法发起的,通过分析源码得出以下线程模型:
一个JavaFX应用由一个或多个Stage组成,一个Stage对应一个窗口。但一个JavaFX应用程序有一个主要的Stage(在执行 start(javafx.stage.Stage)
方法时由应用程序线程创建并传入)。要想在Stage上显示任何东西,就必须为其附加Scene,在运行时可以交换Stage的Scene,但一个Stage同一时间只能展示一个Scene。所有的视觉组件都要附加到Scene上展示,这些视觉组件被称为节点,所有附加到场景的节点总体被称为Scene Graph。
每一个组件都有一些属性(成员变量),它们控制着组件的外观和行为,这些属性的类型不是简单的Java类型,而是属于JavaFX类型系统的包装类型。
ObservableValue封装了一个值,该值可以被读取和监听,以进行失效和更改。
这个封装值可以用以下方法获取并且支持惰性求值。
T getValue()
ObservableValue包装类型可以生成两种事件:更改事件和无效事件。更改事件指示值已经更改。无效事件指示当前值已经无效。可以通过以下方法为包装类型添加和移除事件监听器:
void addListener(InvalidationListener listener)
void addListener(ChangeListener<? super T> listener)
void removeListener(ChangeListener<? super T> listener)
void removeListener(InvalidationListener listener)
WritableValue系列接口是一个包装类型框架,它包装了一个可以读取和设置的值。
T getValue()
void setValue(T value)
ReadOnlyProperty是一个只读包装类型,它实现了ObservableValue框架。
该接口定义了两个方法:
Object getBean()
String getName()
Property是一个可写包装类型,它实现了ReadOnlyProperty接口和ObservableValue框架。
该接口定义了可读属性的通用方法:
void bind(ObservableValue<? extends T> observable)
void bindBidirectional(Property<T> other)
boolean isBound()
void unbind()
void unbindBidirectional(Property<T> other)
集合框架没有对传统的Java集合实现类进行包装,而是直接继承了集合类的父接口(List,Map,Set),并且添加了三个默认方法:
default SortedList<E> sorted()
default SortedList<E> sorted(Comparator<E> comparator)
default FilteredList<E> filtered(Predicate<E> predicate)
所以集合框架不再是一个包装类型框架,因此在使用集合框架时JavaFX为其提供了具体的实现,而这些实现由FXCollections静态工具类提供,并且此类还提供了一些常用方法,可自行查阅。
绑定属性由一个或多个依赖项组装而成。绑定属性观察其依赖项的变化,并根据依赖项的变化更新自己的值。绑定属性的值也是惰性计算的。
Binding是绑定属性的父类,它提供了一些绑定属性通用的方法:
void dispose()//销毁绑定属性
ObservableList<?> getDependencies()//返回绑定属性的依赖项
void invalidate()//将绑定属性值标记为无效。这将强制在下一次请求时重新计算绑定属性的值。
boolean isValid()//检查绑定属性是否是无效的
绑定属性可以通过两套API关联到它的依赖项:
低级API的使用方式如下:
DoubleBinding bindingTest = new DoubleBinding() {
{
//依赖项
super.bind(a, b, c, d);
}
//绑定属性的计算方法
@Override
protected double computeValue() {
return a.getValue() * b.getValue() + c.getValue() * d.getValue();
}
};
而抽象属性的高级API由Bindings工具类提供(以BooleanBinding为例):
static BooleanBinding and(xxx)//绑定到与运算
static BooleanBinding booleanValueAt(xxx)//绑定到集合的一个值
static BooleanBinding createBooleanBinding(xxx)//帮助函数,用于创建自定义布尔绑定。
static BooleanBinding equal(xxx)//绑定一个判等运算
static BooleanBinding notEqual(double op1, ObservableNumberValue op2, double epsilon)//绑定一个不等运算
static BooleanBinding greaterThan(xxx)//绑定一个大于运算
static BooleanBinding greaterThanOrEqual(xxx)//绑定一个大于等于运算
static BooleanBinding isEmpty(xxx)//绑定一个判空运算
static <K,V> BooleanBinding isNotEmpty(xxx)//绑定一个非空运算
static BooleanBinding isNull(ObservableObjectValue<?> op)//绑定一个判null运算
static BooleanBinding isNotNull(ObservableObjectValue<?> op)//绑定一个非null运算
static BooleanBinding lessThan(double op1, ObservableNumberValue op2)//绑定一个小与运算
static BooleanBinding lessThanOrEqual(double op1, ObservableNumberValue op2)//绑定一个小于等于运算
static BooleanBinding not(ObservableBooleanValue op)//绑定一个非运算
static BooleanBinding selectBoolean(Object root, String... steps)//绑定到判断成员是否存在
ObservableValue包装类型产生的事件,就是JavaFX事件处理框架的实现,该框架的结构体系如下:
Event是JavaFX事件框架的顶级接口,在该接口中定义了一些事件的通用属性和方法:
static final EventType<Event> ANY//所有事件类型的通用超类型。
void consume()//将此事件标记为已使用
Event copyFor(Object newSource, EventTarget newTarget)//使用指定的事件源和目标创建并返回此事件的副本。
static void fireEvent(EventTarget eventTarget, Event event)//触发指定事件
EventType<? extends Event> getEventType()//获取事件类型
EventTarget getTarget()//获取事件目标
boolean isConsumed()//该事件是否被使用
每一个事件都关联着一个事件来源、事件类型(EventType)和事件目标(EventTarget)。事件来源是注册事件处理器(EventHandler)并将事件发送给处理器的对象。
//EventHandler中的方法
void handle(T event)/特定类型事件的处方法
事件类型为事件提供了分类,所有的事件类型形成一个以Event.ANY
为根的层次结构。基于这个层次结构,事件处理器可以注册一个超级事件类型,并接收它的子类型事件。(注意,不能构造两个具有相同名称和父类的不同EventType对象。)
final String getName()//返回事件类型的名称
final EventType<? super T> getSuperType()//返回事件类型的超类型
事件目标(EventTarget)定义了事件发布时所经过的路径(EventDispatchChain):
EventDispatchChain buildEventDispatchChain(EventDispatchChain tail)为此目标构造事件分发链。
EventDispatchChain可以将事件从一个事件调度器(EventDispatcher)传递到链中的下一个事件调度器。并且可以添加其它事件调度器到此链中。
Event dispatchEvent(Event event)//通过EventDispatchChain分派指定的事件。
EventDispatchChain append(EventDispatcher eventDispatcher)//将指定的事件调度器追加到此链。
EventDispatchChain prepend(EventDispatcher eventDispatcher)//将指定的事件调度器前置到此链。
EventDispatcher可以将事件通过指定的EventDispatchChain分派给关联的EventTarget。一个事件处理器可以出现在多个事件处理器链中。
Event dispatchEvent(Event event, EventDispatchChain tail)
事件处理框架定义了事件交付的两个阶段。第一个阶段称为捕获阶段,当事件从与EventTarget关联的EventDispatchChain的第一个元素传递到最后一个元素时发生。第二阶段被称为冒泡阶段,其发生顺序与第一阶段相反。
每当ObservableValue包装类型的包装值发生变化时,ChangeListener就会被通知。一个ChangeListener可以监听多个ObservableValue。
void changed(ObservableValue<? extends T> observable, T oldValue, T newValue)//当ObservableValue的值发生变化时调用。
每当Observable的包装值变为无效时,InvalidationListener就会被通知。一个InvalidationListener可以监听多个Observable。
void invalidated(Observable observable)//
我们实现中的所有绑定都使用WeakInvalidationListener的实例,这意味着通常不需要处理绑定。但是,如果您计划在不支持WeakReferences的环境中使用应用程序,则必须销毁未使用的Bindings以避免内存泄漏。
原文链接:https://openjfx.cn/javadoc/18/javafx.fxml/javafx/fxml/doc-files/introduction_to_fxml.html
FXML是一种可编写的、基于XML的用于构造JavaFX场景图的标记语言。在FXML中,一个FXML标签代表以下类型之一:
一个FXML属性表示以下类型之一:
要想在FXML使用Java类,必须使用以下语句进行导入:
在FXML中创建实例最简单的方法是通过FXML元素。任何遵循JavaBean构造函数和属性命名约定的类都可以通过此方式创建实例。
<Label text="Hello world FXML"/>
fx:value
属性可以用来实例化没有默认构造函数但提供静态valueOf(String)
方法的类:
<String fx:value="Hello, World!"/>
fx:factory
属性可以使用静态工厂方法实例类:
<FXCollections fx:factory="observableArrayList">
<String fx:value="A"/>
<String fx:value="B"/>
<String fx:value="C"/>
FXCollections>
构造器可以用于实例化不符合Bean约定的类,FXML中的构造器支持由两个接口提供,javafx.util.Builder
接口定义了一个名为build()
的方法,它负责构造实际的对象:
public interface Builder<T> {
public T build();
}
javafx.util.BuilderFactory
接口负责生成能够实例化给定类型的构造器:
public interface BuilderFactory {
public Builder<?> getBuilder(Class<?> type);
}
JavaFX中提供了一个默认的构建器工厂JavaFXBuilderFactory
,这个工厂能够创建和配置大多数不可变的JavaFX类型:
<Color red="1.0" green="0.0" blue="0.0"/>
构建器构造的对象直到到达元素的结束标记时才会实例化。这是因为在元素被完全处理之前,所有必需的参数可能都不可用。
标签可以从在另一个文件中定义的FXML标签实例化对象:
<fx:include source="filename"/>
标签还支持用于指定应用于本地化所包含内容的资源包名称的属性,以及用于编码源文件的字符集:
<fx:include source="filename" resources="resource_file" charset="utf-8"/>
标签用于创建对类常量的引用:
<Button>
<minHeight>
<Double fx:constant="NEGATIVE_INFINITY"/>
minHeight>
Button>
标签可以创建对现有实例的引用:
<ImageView>
<image>
<fx:reference source="myImage"/>
image>
ImageView>
属性标签可以表示以下几种形式之一:
如果属性元素表示的是可读写属性,那么属性元素的内容将作为可读写属性的setter的值传递:
<Label>
<text>Hello, World!text>
Label>
只读列表属性的getter返回java.util.List的一个实例,并且没有相应的setter方法。只读列表元素的内容在处理时自动添加到列表中:
<VBox>
<children>
<Label>
<text>line 1text>
Label>
<Label>
<text>line 2text>
Label>
children>
VBox>
只读map属性的getter返回java.util.Map的一个实例,并且没有相应的setter方法。只读map元素的属性在处理结束标记时应用于映射。
<Button>
<properties foo="123" bar="456"/>
Button>
JavaFX组件可以有一个默认属性。这意味着,如果FXML元素包含没有嵌套在属性元素中的子元素,则假定这些子元素属于默认属性。比如上文中的
完全可以改写成以下形式:
<VBox>
<Label>
<text>line 1text>
Label>
<Label>
<text>line 2text>
Label>
VBox>
JavaFX组件的默认属性使用注释@DefaultProperty(value="propertyName")
进行标记。
静态属性是只有在特定上下文中才有意义的属性,因为它们不是应用到的类的固有属性,而是由另一个类(通常是控件的父容器)定义的。静态属性以定义它们的类的名称作为前缀来使用:
<GridPane>
<Label>
<text>my labeltext>
<GridPane.rowIndex>0GridPane.rowIndex>
<GridPane.columnIndex>0GridPane.columnIndex>
Label>
TabPane>
元素用于创建存在于场景图之外但可能需要在其它地方引用的对象。例如,在处理单选按钮时,通常需要定义一个ToggleGroup来管理按钮的选择状态。这个组不是场景图本身的一部分,所以不应该添加到按钮的父节点。定义块可以用来创建按钮组,而不影响文档的整体结构:
<VBox>
<fx:define>
<ToggleGroup fx:id="myToggleGroup"/>
fx:define>
<children>
<RadioButton text="A" toggleGroup="$myToggleGroup"/>
<RadioButton text="B" toggleGroup="$myToggleGroup"/>
<RadioButton text="C" toggleGroup="$myToggleGroup"/>
children>
VBox>
FXML属性也可以用来配置实例的属性:
<Button text="Click Me!"/>
当属性值是复杂类型,不能使用简单的基于字符串的FXML属性表示时,或者值的字符长度太长,以至于将其指定为FXML属性会对可读性产生负面影响时,通常使用属性标签。FXML属性和属性标签一个区别在于FXML属性必须在各自标签到达结束标签时才会起作用,另一个区别在于FXML属性支持可以扩展其功能的操作符,支持的操作符如下:
位置解析操作符(属性值前加前缀@
)用于指定属性值应被视为相对于当前文件的URL(URL中的空白值必须经过编码),而不是一个简单的字符串:
<ImageView>
<image>
<Image url="@my_image.png"/>
image>
ImageView>
FXML文档定义了一个变量名称空间,在这个名称空间中,变量可以被唯一的标识。如果将fx:id
属性值赋给标签,那么将在文档的名称空间中创建一个变量,变量解析操作符(在属性值前面加前缀$
)允许调用者在调用相应的setter方法之前,将标签的属性值替换为指定变量的实例:
<fx:define>
<ToggleGroup fx:id="myToggleGroup"/>
fx:define>
<RadioButton text="A" toggleGroup="$myToggleGroup"/>
<RadioButton text="B" toggleGroup="$myToggleGroup"/>
<RadioButton text="C" toggleGroup="$myToggleGroup"/>
绑定表达式(将属性值使用${}
包裹)可以将属性的值绑定到其它属性上,这样当被绑定的属性值变化时,绑定的属性值也会变化:
<TextField fx:id="textField"/>
<Label text="${textField.text}"/>
绑定表达式支持的数据类型如下:
绑定表达式支持的运算符如下:
FXML属性表示的静态属性和FXML标签标识的类似:
<GridPane>
<children>
<Label text="My Label" GridPane.rowIndex="0" GridPane.columnIndex="0"/>
children>
TabPane>
区别在于FXML属性表示的静态属性支持功能性操作符(绑定表达式除外)。
事件处理器属性是将事件处理器附加到FXML元素的一种方便方法,FXML支持三种类型的事件处理程序:
脚本事件处理程序是在事件触发时执行脚本代码的事件处理程序:
<VBox>
<children>
<Button text="Click Me!" onAction="java.lang.System.out.println('You clicked me!');"/>
children>
VBox>
注意在代码片段开始时使用语言处理指令。这个指令告诉FXML加载程序应该使用脚本语言来执行事件处理程序。若要关闭脚本代码的自动编译,请放置处理指令在包含脚本的标签的前面。若要再次启动脚本代码编译,请使用
。
控制器方法事件处理器是由FXML文档的控制器定义的方法:
<VBox fx:controller="com.foo.MyController"
xmlns:fx="http://javafx.com/fxml">
<children>
<Button text="Click Me!" onAction="#handleButtonAction"/>
children>
VBox>
通常情况下,事件处理器应该接受一个扩展自javafx.event.Event
类型的单一参数,并返回void
,当然,参数也可以省略。
package com.foo;
public class MyController {
public void handleButtonAction(ActionEvent event) {
System.out.println("You clicked me!");
}
}
指向javafx.event.EventHandler
类型的任何表达式都可以用作表达式处理程序:
<VBox fx:controller="com.foo.MyController"
xmlns:fx="http://javafx.com/fxml">
<children>
<Button text="Click Me!" onAction="$controller.onActionHandler"/>
children>
VBox>
public class MyController {
@FXML
public EventHandler<ActionEvent> onActionHandler = new EventHandler<>() { ... }
}
注意,其他类型的表达式,如绑定表达式,在此上下文中不受支持。
不能使用setOnEvent()方法监听集合的变化,因此,ObservableList,、ObservableMap和ObservableSet 使用一个一个特殊的onChange属性,该属性指向带有 ListChangeListener.Change,、MapChangeListener.Change、和 SetChangeListener.Change参数的处理方法。
<VBox fx:controller="com.foo.MyController"
xmlns:fx="http://javafx.com/fxml">
<children onChange="#handleChildrenChange"/>
VBox>
处理器方法如下:
package com.foo;
import javafx.collections.ListChangeListener.Change;
public class MyController {
public void handleChildrenChange(ListChangeListener.Change c) {
System.out.println("Children changed!");
}
}
也不能使用setOnEvent()方法监听属性的变化,要注册到一个属性,必须使用一个特殊的on
属性:
<VBox fx:controller="com.foo.MyController"
xmlns:fx="http://javafx.com/fxml" onParentChange="#handleParentChange"/>
处理器方法如下:
public class MyController {
public void handleParentChange(ObservableValue value, Parent oldValue, Parent newValue) {
System.out.println("Parent changed!");
}
}
标记允许将脚本代码导入或嵌入FXML文件中。可以使用任何JVM脚本语言编写脚本。如果脚本引擎实现了javax.script.Compilable
接口,那么脚本在第一次加载时将被默认编译。如果编译失败,FXMLLoader将退回到解释模式。
<VBox xmlns:fx="http://javafx.com/fxml">
<fx:script>
function handleButtonAction(event) {
java.lang.System.out.println('You clicked me!');
}
fx:script>
<children>
<Button text="Click Me!" onAction="handleButtonAction(event);"/>
children>
VBox>
<VBox xmlns:fx="http://javafx.com/fxml">
<fx:script source="example.js" charset="cp1252"/>
<children>
<Button text="Click Me!" onAction="handleButtonAction(event);"/>
children>
VBox>
//example.js
function handleButtonAction(event) {
java.lang.System.out.println('You clicked me!');
}
虽然在脚本中编写简单的事件处理程序很方便,但通常更可取的做法是在编译后的强类型语言中定义更复杂的应用程序逻辑。如前所述,fx:controller
属性允许将控制器类与FXML文档关联起来。控制器是一个编译类,它实现了文档定义的对象层次结构的背后代码。这个属性包含控制器类全类名。该类的一个实例在加载FXML文件时创建,因此控制器类必须有一个无参数的构造函数。
<VBox fx:controller="com.foo.MyController"
xmlns:fx="http://javafx.com/fxml">
<children>
<Button text="Click Me!" onAction="#handleButtonAction"/>
children>
VBox>
package com.foo;
public class MyController {
public void handleButtonAction(ActionEvent event) {
System.out.println("You clicked me!");
}
}
在许多情况下,以这种方式简单地声明事件处理程序就足够了。然而,当需要对控制器及其管理的元素的行为进行更多的控制时,控制器可以定义一个initialize()
方法,当其关联文档的内容被完全加载后,该方法将在实现控制器上调用:
public void initialize();
可以将FXML文件中的JavaFX组件绑定到控制器类中的字段,前提是需要为JavaFX组件的FXML元素提供一个fx:id
属性,该属性具有要绑定的控制器字段的名称作为值。
public class MyFxmlController {
public Label label;
}
<VBox xmlns:fx="http://javafx.com/fxml" >
<Label fx:id="label" text="Line 1"/>
VBox>
注意,在前面的示例中,控制器成员字段和事件处理程序方法被声明为公共的,因此可以由加载器设置或调用它们。但是,对于那些喜欢限制控制器字段或处理程序方法可见性的开发人员,可以使用@FXML
注解。这个注解将一个受保护的或私有的类成员标记为FXML可访问的。
通过
标签加载的嵌套FXML文档的控制器实例被直接映射到包含控制器的成员字段。例如,给定以下代码:
<VBox fx:controller="com.foo.MainController">
<fx:define>
<fx:include fx:id="dialog" source="dialog.fxml"/>
fx:define>
VBox>
public class MainController extends Controller {
@FXML private Window dialog;
@FXML private DialogController dialogController;
}
当调用控制器的initialize方法时,dialog字段将包含从dialog.fxml中加载的根元素,dialogController字段将包含包含dialog对象的控制器。
FXMLLoader类负责实际加载FXML源文件并返回结果对象图。
URL location = getClass().getResource("example.fxml");
ResourceBundle resources = ResourceBundle.getBundle("com.foo.example");
FXMLLoader fxmlLoader = new FXMLLoader(location, resources);
Pane root = (Pane)fxmlLoader.load();
MyController controller = (MyController)fxmlLoader.getController();
在加载时,FXMLLoader使用com.sun.javafx.fxml.BeanAdapter的一个实例来包装一个实例化的对象,并调用它的Setter方法。这个私有类实现了java.util.Map接口,并允许调用者以键值对的形式获取和设置Bean属性值。如果一个元素表示一个已经实现了Map的类型,它不会被包装,它的get和put方法会被直接调用。
原文链接:https://openjfx.cn/javadoc/18/javafx.graphics/javafx/scene/doc-files/cssref.html
JavaFX允许使用CSS样式修饰JavaFX组件,JavaFX使用与Web CSS相同的CSS语法,但CSS属性是特定于JavaFX的,因此与Web对应的名称略有不同。除了少数例外,JavaFXCSS属性名的前缀是-fx-
。CSS样式应用于JavaFX场景图中的节点,其方式类似于CSS样式应用于HTML DOM中的元素。样式首先应用于父类,然后应用于其子类。CSS选择器用于将样式与场景图节点相匹配。Node和CSS选择器的关系如下:
JavaFX应用程序有一个默认的CSS样式表,它应用于所有的JavaFX组件。如果不提供组件的样式,默认的CSS样式表将对JavaFX组件进行样式设置。
可以为JavaFX场景对象设置CSS样式表,这个样式表被应用于所有添加到场景图中的JavaFX组件。Scene样式表中指定的样式优先于默认样式表中指定的样式。
scene.getStylesheets().add("style1/button-styles.css");
在所有布局组件上也可以设置样式表,这个样式表应用于包含在布局组件内的所有组件,布局组件样式表指定的CSS样式通常优先于Scene样式表中指定的CSS样式。
Button button1 = new Button("Button 1");
Button button2 = new Button("Button 2");
VBox vbox = new VBox(button1, button2);
vbox.getStylesheets().add("style1/button-styles.css");
可以通过在组件上直接设置CSS样式属性来设置组件的CSS样式,
此方式设置的样式优先于布局组件样式表中指定的样式。
Button button = new Button("Button 2");
button.setStyle("-fx-background-color: #0000ff");
项目地址:FX计算器
Window是诸如舞台、弹出窗口等顶层窗口的父类,它的属性如下:
final void setScene(Scene value)//设置场景对象
final void show()//使Stage可见并立即退出该方法
void showAndWait()//使Stage可见但阻塞至Satge关闭再退出该方法
一个Stage可以被另一个Stage所拥有。可以通过以下方法设置Stage的所有者:
final void initOwner(Window owner)//设置拥有者
可以通过以下方式设置Stage的窗口模式:
final void initModality(Modality modality)//设置模式
Stage的窗口模式决定表示Stage的窗口是否会阻塞同一JavaFX应用程序打开的其它窗口:
Modality.APPLICATION_MODAL//新创建的Stage窗口会阻塞在应用程序中打开的其它窗口
Modality.NONE//新创建的Stage窗口不会阻塞在应用程序中打开的其它窗口
Modality.WINDOW_MODAL//新创建的Stage将阻塞拥有新创建Stage的Stage窗口
可以通过以下方法设置Stage的样式:
final void initStyle(StageStyle style)//设置样式
所有的Stage装饰如下:
StageStyle.DECORATED//白色背景并带有操作系统装饰
StageStyle.UNDECORATED//白色背景没有操作系统装饰
StageStyle.TRANSPARENT//透明背景没有操作系统装饰
StageStyle.UNIFIED//白色背景带有操作系统装饰,但工作区域和装饰区域没有分割线
StageStyle.UTILITY//白色背景带有最简的操作系统装饰
弹出式窗口的父接口,Popup是它的一个实现,它的属性如下:
用于描述显示设备。
FileChooser是一个文件选择器。
DirectoryChooser是一个目录选择器。
Scene(场景)是场景图的容器,在实例化场景对象时必须设置它的root
属性来指定场景图的根节点。场景在被附加到正在显示的窗口之前可以在任何线程上创建和修改。在附加之后只能JavaFX应用程序线程上修改。它的属性如下:
场景图是一个由节点组成的树形结构,Node是场景图节点的基类,一个节点在场景图中只能出现一次,如果一个程序向父节点添加了一个子节点,并且该节点已经是不同父节点的子节点或场景的根节点,该节点将自动从其前父节点中移除,并且节点之间不能存在循环结构。和Scene类似,节点在被附加到正在显示窗口的场景之前可以在任何线程上创建和修改。在附加之后只能JavaFX应用程序线程上修改。以下是场景图节点的通用设计:
节点的属性如下:
布局节点内可以嵌套其它节点(控件节点和布局节点)。一旦其它节点被添加进来,布局节点将自动管理它门的布局,所以应用程序不应该直接定位或调整这些节点的大小。场景图同时支持可调整大小和不可调整大小的节点类。Node上的isResizable()方法返回给定的节点是否可以调整大小。一个可调整大小的节点类支持一个可接受的大小范围(minimum <= preferred <= maximum),允许它的父节点在布局期间根据父节点自己的布局策略和同级节点的布局需求在这个范围内调整它的大小。另一方面,不可调整大小的节点类没有一致的调整大小API,因此它们的父类在布局期间不会调整大小。应用程序必须通过在每个实例上设置适当的属性来确定不可调整大小的节点的大小。这些类返回它们的min、pref和max的当前布局边界,而resize()方法将成为一个无操作。可调整大小的类:Region, Control, WebView。不可调整大小的类:Group, Shape, Text。应用程序无法可靠地查询可调整大小的节点的边界,直到它被添加到场景中,因为节点的大小可能依赖于CSS。
Region是所有基于JavaFX node的UI控件和所有布局容器的基类。它是一个可调整大小的父节点。一个Region有一个Background和一个Border,尽管这两个可能都是空的。区域的背景由零个或多个BackgroundFills和零个或多个BackgroundImages组成。同样地,Region的边界由它的border定义,它由零个或多个BorderStrokes和零个或多个BorderImages组成。所有的背景填充都是首先绘制的,其次是背景图像,边框,最后是边框图像。默认情况下,Region继承其超类Parent的布局行为,这意味着它会将任何可调整大小的子节点调整到它们首选的大小,但不会重新定位它们。如果一个应用程序需要更具体的布局行为,那么它应该使用Region的子类之一。
控件节点在JavaFX应用程序中提供某种功能。例如,按钮、单选按钮、表格、树等。控件节点通常嵌套在一些JavaFX布局节点中。
Text节点用于显示文本,JavaFX会根据以下规则对文本进行换行:
\n
ButtonBase是按钮类节点的基类,它提供了两个属性: