前言
官方文档:Client Technologies: Java Platform, Standard Edition (Java SE) 8 Release 8
p4 了解项目
主要结构: Main.java 启动类 Application 应用程序 Stage 舞台(窗口) Scene 场景 Node 节点 一个应用程序可以有多个舞台,舞台是固定不变的,上面可以布置不同的场景,场景上可以有多个节点,这些节点有一个root节点。
p5 添加标签Label
Node是所有节点的跟类,下面分
@Override
public void start(Stage primaryStage) throws Exception{
// 准备子节点
Label label = new Label("这是一个标签");
// 父节点
BorderPane root = new BorderPane();
root.setCenter(label);
// 场景
Scene scene = new Scene(root,400,400);
// 舞台
primaryStage.setScene(scene);
primaryStage.show();
}
p6 添加按钮Button
本节主要是学习事件
@Override
public void start(Stage primaryStage) throws Exception{
// 准备子节点
Button button = new Button("我是按钮");
button.setOnAction(new MyEventHandler());
// 父节点
BorderPane root = new BorderPane();
root.setCenter(button);
// 场景
Scene scene = new Scene(root,400,400);
// 舞台
primaryStage.setScene(scene);
primaryStage.show();
}
private static class MyEventHandler implements EventHandler<ActionEvent>{
@Override
public void handle(ActionEvent event) {
System.out.println("被点击了");
}
}
p7 添加图片ImageView
注意添加图片的方式,及其支持的格式
@Override
public void start(Stage primaryStage) throws Exception{
// 仅支持BMP GIF JPEG PNG四种格式
// 本地文件
//Image image = new Image("file:\\E:\\笔记\\source\\资源\\头像1.jpeg");
// 网络文件
Image image = new Image("https://cdn.nlark.com/yuque/0/2022/png/26420489/1667889759088-4bf78470-022f-4a4a-8dd6-85169994f04d.png");
double width = image.getWidth();
double height = image.getHeight();
ImageView imageView = new ImageView();
imageView.setImage(image);
// 父节点
BorderPane root = new BorderPane();
root.setCenter(imageView);
// 场景
Scene scene = new Scene(root,width,height);
// 舞台
primaryStage.setScene(scene);
primaryStage.setTitle("测试");
primaryStage.show();
}
p8 实战练习-相册
public class App extends Application {
List<Image> imageViewList = new ArrayList<>();
ImageView imageView = new ImageView();
private Integer index = 0;
@Override
public void init() throws Exception {
imageViewList.add(new Image("/p8/1.jpeg"));
imageViewList.add(new Image("/p8/2.png"));
imageViewList.add(new Image("/p8/3.jpg"));
imageView.setPreserveRatio(true);
}
@Override
public void start(Stage primaryStage) throws Exception {
BorderPane root = new BorderPane();
Button button = new Button("下一个");
button.setOnAction((event) -> {
next(primaryStage);
});
root.setTop(button);
root.setCenter(imageView);
// 场景
Scene scene = new Scene(root);
// 舞台
primaryStage.setScene(scene);
primaryStage.setTitle("测试");
next(primaryStage);
primaryStage.show();
}
private void next(Stage stage) {
Image image = imageViewList.get((index++) % 3);
imageView.setImage(image);
stage.setWidth(image.getWidth());
stage.setHeight(image.getHeight()+100);
System.out.println("被调用的第"+index +"次");
}
public static void main(String[] args) {
launch(args);
}
}
p10 边缘布局 BorderPane
支持五种位置
@Override
public void start(Stage primaryStage) throws Exception {
BorderPane root = new BorderPane();
root.setTop(new Label("顶部"));
root.setLeft(new Label("左部"));
root.setRight(new Label("右部"));
root.setCenter(new Label("中部"));
root.setBottom(new Label("底部"));
Scene scene = new Scene(root,400,400);
primaryStage.setScene(scene);
primaryStage.show();
}
p11 水平布局
@Override
public void start(Stage primaryStage) throws Exception {
HBox root = new HBox();
root.setAlignment(Pos.CENTER);
// 设置边缘距离
root.setPadding(new Insets(10));
TextField textField = new TextField();
root.getChildren().addAll(textField,new Button("选择文件"),new Button("开始上传"));
// 设置水平成长
HBox.setHgrow(textField, Priority.ALWAYS);
Scene scene = new Scene(root,400,400);
primaryStage.setScene(scene);
primaryStage.show();
}
p12 控件的尺寸
@Override
public void start(Stage primaryStage) throws Exception {
HBox root = new HBox();
Button b1 = new Button("中国");
// 最小宽度
b1.setMinWidth(100);
// 最大宽度
b1.setMaxWidth(400);
// 最佳宽度
b1.setPrefWidth(200);
// 以上并不能决定控件大小,最终是由容器决定使用哪个
Button b2 = new Button("中华人民共和国");
// 默认宽度
b2.setMaxHeight(Control.USE_COMPUTED_SIZE);
// 最佳宽度
b2.setMaxHeight(Control.USE_PREF_SIZE);
root.getChildren().setAll(b1,b2);
Scene scene = new Scene(root,400,400);
primaryStage.setScene(scene);
primaryStage.show();
}
p13 控件的布局
@Override
public void start(Stage primaryStage) throws Exception {
HBox root = new HBox();
TextField textField = new TextField();
root.getChildren().addAll(textField,new Button("选择文件"),new Button("开始上传"));
// 对齐
root.setAlignment(Pos.CENTER);
// 填充 子控件和父级的边距
root.setPadding(new Insets(10));
// 间距
root.setSpacing(10);
// 优先增长 注意是静态方法
HBox.setHgrow(textField,Priority.ALWAYS);
Scene scene = new Scene(root,400,400);
primaryStage.setScene(scene);
primaryStage.show();
}
- 精确布局
p14 自定义容器
主要是实现Pane容器接口
@Override
public void start(Stage primaryStage) throws Exception {
Image image = new Image("/p8/1.jpeg");
ImageView imageView = new ImageView(image);
ImageViewPane root = new ImageViewPane();
root.getChildren().add(imageView);
Scene scene = new Scene(root,400,400);
primaryStage.setScene(scene);
primaryStage.show();
}
private static class ImageViewPane extends Pane {
@Override
protected void layoutChildren() {
if (getChildren().isEmpty()){
return;
}
double width = getWidth();
double height = getHeight();
ImageView imageView = (ImageView) getChildren().get(0);
imageView.resizeRelocate(0,0,width,height);
imageView.setFitWidth(width);
imageView.setFitHeight(height);
imageView.setPreserveRatio(true);
}
}
p15 布局的嵌套
public class App extends Application {
HBox hBox = new HBox();
TextArea textArea = new TextArea();
@Override
public void init() throws Exception {
TextField textField = new TextField();
Button button = new Button("添加");
button.setOnAction(new EventHandler<ActionEvent>() {
@Override
public void handle(ActionEvent event) {
textArea.appendText(textField.getText() +"\r\n");
textField.clear();
}
});
hBox.getChildren().addAll(textField, button);
HBox.setHgrow(textField, Priority.ALWAYS);
}
@Override
public void start(Stage primaryStage) throws Exception {
BorderPane root = new BorderPane();
root.setTop(hBox);
root.setCenter(textArea);
Scene scene = new Scene(root, 400, 400);
primaryStage.setScene(scene);
primaryStage.show();
}
public static void main(String[] args) {
launch(args);
}
}
p16 列表控件
多项数据的表示方法: ListView 列表 TreeView 树 TableView 表格 TreeTableView 多列列表
public class App extends Application {
/**
* 列表控件
*/
ListView<Student> listView = new ListView<>();
/**
* 承载数据
*/
ObservableList<Student> listData = FXCollections.observableArrayList();
@Override
public void init() throws Exception {
}
@Override
public void start(Stage primaryStage) throws Exception {
listData.addAll(
Student.builder().id(1).name("make").age(18).build(),
Student.builder().id(1).name("ming").age(15).build(),
Student.builder().id(1).name("jen").age(20).build()
);
listView.setItems(listData);
listView.setCellFactory(new Callback<ListView<Student>, ListCell<Student>>() {
@Override
public ListCell<Student> call(ListView<Student> param) {
return new MyCell();
}
});
Button button = new Button("删除");
button.setOnAction(new EventHandler<ActionEvent>() {
@Override
public void handle(ActionEvent event) {
if (!listData.isEmpty()){
listData.remove(0);
}
}
});
BorderPane root = new BorderPane();
root.setTop(button);
root.setCenter(listView);
Scene scene = new Scene(root, 400, 400);
primaryStage.setScene(scene);
primaryStage.show();
}
/**
* 自定义单元格类
*/
private class MyCell extends ListCell<Student>{
@Override
protected void updateItem(Student item, boolean empty) {
// 必须先调用父方法
super.updateItem(item, empty);
// 为了刷新列表,当为空时要执行以下操作
if (empty || item == null){
setText(null);
setGraphic(null);
}else {
this.setText(item.getName());
}
}
}
@Data
@NoArgsConstructor
@AllArgsConstructor
@Builder
public static class Student {
private Integer id;
private String name;
private Integer age;
}
public static void main(String[] args) {
launch(args);
}
}
p17 列表项的操作
增删改操作
public class App extends Application {
/**
* 列表控件
*/
ListView<Student> listView = new ListView<>();
/**
* 承载数据
*/
ObservableList<Student> listData = FXCollections.observableArrayList();
HBox hBox = new HBox();
@Override
public void start(Stage primaryStage) throws Exception {
TextField textField = new TextField();
Button add = new Button("新增");
add.setOnAction(new EventHandler<ActionEvent>() {
@Override
public void handle(ActionEvent event) {
String text = textField.getText();
listData.add(Student.builder().name(text).build());
textField.clear();
}
});
Button del = new Button("删除");
del.setOnAction(new EventHandler<ActionEvent>() {
@Override
public void handle(ActionEvent event) {
int selectedIndex = listView.getSelectionModel().getSelectedIndex();
if (selectedIndex >= 0) {
listData.remove(selectedIndex);
}
}
});
Button update = new Button("修改");
update.setOnAction(new EventHandler<ActionEvent>() {
@Override
public void handle(ActionEvent event) {
int selectedIndex = listView.getSelectionModel().getSelectedIndex();
if (selectedIndex >= 0) {
String text = textField.getText();
listData.set(selectedIndex, Student.builder().name(text).build());
textField.clear();
}
}
});
hBox.getChildren().addAll(textField, add, del, update);
HBox.setHgrow(textField, Priority.ALWAYS);
listData.addAll(
Student.builder().id(1).name("make").age(18).build(),
Student.builder().id(1).name("ming").age(15).build(),
Student.builder().id(1).name("jen").age(20).build()
);
listView.setItems(listData);
listView.setCellFactory(new Callback<ListView<Student>, ListCell<Student>>() {
@Override
public ListCell<Student> call(ListView<Student> param) {
return new MyCell();
}
});
BorderPane root = new BorderPane();
root.setTop(hBox);
root.setCenter(listView);
Scene scene = new Scene(root, 400, 400);
primaryStage.setScene(scene);
primaryStage.show();
}
/**
* 自定义单元格类
*/
private class MyCell extends ListCell<Student> {
@Override
protected void updateItem(Student item, boolean empty) {
// 必须先调用父方法
super.updateItem(item, empty);
// 为了刷新列表,当为空时要执行以下操作
if (empty || item == null) {
setText(null);
setGraphic(null);
} else {
this.setText(item.getName());
}
}
}
@Data
@NoArgsConstructor
@AllArgsConstructor
@Builder
public static class Student {
private Integer id;
private String name;
private Integer age;
}
public static void main(String[] args) {
launch(args);
}
}
p18 多项选择
public class App extends Application {
/**
* 列表控件
*/
ListView<Student> listView = new ListView<>();
/**
* 承载数据
*/
ObservableList<Student> listData = FXCollections.observableArrayList();
HBox hBox = new HBox();
@Override
public void start(Stage primaryStage) throws Exception {
Button del = new Button("删除");
del.setOnAction(new EventHandler<ActionEvent>() {
@Override
public void handle(ActionEvent event) {
listData.removeIf(e -> e.isChecked());
}
});
hBox.getChildren().addAll( del );
listData.addAll(
Student.builder().id(1).name("make").age(18).build(),
Student.builder().id(1).name("ming").age(15).build(),
Student.builder().id(1).name("jen").age(20).build()
);
listView.setItems(listData);
listView.setCellFactory(new Callback<ListView<Student>, ListCell<Student>>() {
@Override
public ListCell<Student> call(ListView<Student> param) {
return new MyCell();
}
});
BorderPane root = new BorderPane();
root.setTop(hBox);
root.setCenter(listView);
Scene scene = new Scene(root, 400, 400);
primaryStage.setScene(scene);
primaryStage.show();
}
/**
* 自定义单元格类
*/
private class MyCell extends ListCell<Student> {
@Override
protected void updateItem(Student item, boolean empty) {
// 必须先调用父方法
super.updateItem(item, empty);
// 为了刷新列表,当为空时要执行以下操作
if (empty || item == null) {
setText(null);
setGraphic(null);
} else {
CheckBox checkBox = new CheckBox();
checkBox.setText(item.getName());
checkBox.setSelected(item.isChecked());
checkBox.selectedProperty().addListener(new MyChangeListener(item));
this.setGraphic(checkBox);
}
}
}
private class MyChangeListener implements ChangeListener<Boolean>{
private Student student;
public MyChangeListener(Student student) {
this.student = student;
}
@Override
public void changed(ObservableValue<? extends Boolean> observable, Boolean oldValue, Boolean newValue) {
student.setChecked(newValue);
}
}
@Data
@NoArgsConstructor
@AllArgsConstructor
@Builder
public static class Student {
private Integer id;
private String name;
private Integer age;
private boolean checked;
}
public static void main(String[] args) {
launch(args);
}
}