Skip to content

javaFx 入门个人笔记

javaFx 在国内感觉使用的人数还不是很多,可能是java的桌面一直不是很火吧。

最近在写一个桌面小工具的时候,就使用javafx制作的。

参考资料:
中文资料网站 http://www.javafxchina.net/blog/

与swing 对比

 

javafx 有很多swing的影子,很多写法很相近。

javafx 界面以xml文件(fxml)设计与存储,官方可以下载 javafx scene builder

javafx 通过1对1方式(fxml 绑定 controller)的方式进行界面与控制器分离

javafx 使用注解方式绑定界面元素与xml的关系、事件

javafx 元素支持css样式(这个就比swing好很多了)

以上是的暂时已知的。

java fx 基础扫盲

在JavaFx中:

  • 每个窗口可以理解为一个舞台(Stage);
  • 舞台必需有场景(Scene);
  • 场景中可以有各种控件(Control)、形状(Shape)等等。

基础的控件什么的就不做解释了。

你可能比较关注

1.控件与代码的绑定

2.场景的切换(就像舞台剧的场景切换一样)

实战:

一、我们现在先写一个启动类

public class FxMain extends Application {

    public static void main(String[] args) {
        launch(args);
    }

    @Override
    public void start(Stage primaryStage) throws Exception {
            
    }

}

三部完成:

1.通过直接继承Application类

2.写main方法,在方法中调用launch方法,

3.重写public void start(Stage primaryStage)方法

start方法为我们需要自己去写自己逻辑的地方。

首先传入一个舞台给你.

你需要将你自己的场景添加到舞台中。

场景中包含各种控件,你自己根据需求添加。

二、新建一个fxml配置界面

<?xml version="1.0" encoding="UTF-8"?>

<?import javafx.scene.text.*?>
<?import javafx.scene.control.*?>
<?import javafx.scene.layout.*?>


<AnchorPane maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="300.0" prefWidth="400.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1">
   <children>
      <Label layoutX="134.0" layoutY="34.0" prefHeight="23.0" prefWidth="134.0" text="欢迎使用JavaFx">
         <font>
            <Font size="18.0" />
         </font>
      </Label>
      <Label layoutX="86.0" layoutY="100.0" text="请输入账户:" />
      <Label layoutX="86.0" layoutY="161.0" text="请输入密码:" />
      <TextField layoutX="172.0" layoutY="95.0" />
      <PasswordField layoutX="172.0" layoutY="156.0" />
      <Button layoutX="295.0" layoutY="222.0" mnemonicParsing="false" text="登录" />
   </children>
</AnchorPane>

设计软件界面

scene builder
javafx scene builder

三、添加controller 绑定

<?xml version="1.0" encoding="UTF-8"?>

<?import java.lang.*?>
<?import javafx.scene.text.*?>
<?import javafx.scene.control.*?>
<?import javafx.scene.layout.*?>

<AnchorPane fx:controller="com.cqmaple.javafx.FxMain" maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="300.0" prefWidth="400.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1" >
   <children>
      <Label layoutX="134.0" layoutY="34.0" prefHeight="23.0" prefWidth="134.0" text="欢迎使用JavaFx">
         <font>
            <Font size="18.0" />
         </font>
      </Label>
      <Label layoutX="86.0" layoutY="100.0" text="请输入账户:" />
      <Label layoutX="86.0" layoutY="161.0" text="请输入密码:" />
      <TextField layoutX="172.0" layoutY="95.0" />
      <PasswordField layoutX="172.0" layoutY="156.0" />
      <Button layoutX="295.0" layoutY="222.0" mnemonicParsing="false" text="登录" />
   </children>
</AnchorPane>

红色部分为controller 绑定

注意:这里的controller 只要是一个java 类就可以。为了方便所以合成一个。

四、绑定控件到controller

我们这里只需要绑定三个元素就好了 其他的界面显示不需要。

1.绑定TextField 获取账户

2.绑定PasswordField 获取密码

3.绑定Button 触发事件切换到下一个场景

先在fxml 控件上添加id

<?xml version="1.0" encoding="UTF-8"?>

<?import java.lang.*?>
<?import javafx.scene.text.*?>
<?import javafx.scene.control.*?>
<?import javafx.scene.layout.*?>

<AnchorPane maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="300.0" prefWidth="400.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1" fx:controller="com.cqmaple.javafx.FxMain">
   <children>
      <Label layoutX="134.0" layoutY="34.0" prefHeight="23.0" prefWidth="134.0" text="欢迎使用JavaFx">
         <font>
            <Font size="18.0" />
         </font>
      </Label>
      <Label layoutX="86.0" layoutY="100.0" text="请输入账户:" />
      <Label layoutX="86.0" layoutY="161.0" text="请输入密码:" />
      <TextField fx:id="account" layoutX="172.0" layoutY="95.0" />
      <PasswordField fx:id="password" layoutX="172.0" layoutY="156.0" />
      <Button fx:id="login" layoutX="295.0" layoutY="222.0" mnemonicParsing="false" text="登录" />
   </children>
</AnchorPane>

然后在controller中添加代码

package com.cqmaple.javafx;

import javafx.application.Application;
import javafx.fxml.FXML;
import javafx.scene.control.Button;
import javafx.scene.control.PasswordField;
import javafx.scene.control.TextField;
import javafx.stage.Stage;

/**
 * Created by maple on 2017/6/18.
 */
public class FxMain extends Application {
    /**
     * 账户输入框
     */
    @FXML
    private TextField account;
    /**
     * 密码输入框
     */
    @FXML
    private PasswordField password;
    /**
     * 登录按钮
     */
    @FXML
    private Button login;

    public static void main(String[] args) {
        launch(args);
    }

    @Override
    public void start(Stage primaryStage) throws Exception {

    }

}

通过@fxml 进行绑定 注意:属性类型与名称(对应id) 必须一致。

五、将场景绑定到舞台中

 

package com.cqmaple.javafx;

import javafx.application.Application;
import javafx.fxml.FXML;
import javafx.fxml.FXMLLoader;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.control.PasswordField;
import javafx.scene.control.TextField;
import javafx.scene.layout.Pane;
import javafx.stage.Stage;

/**
 * Created by maple on 2017/6/18.
 */
public class FxMain extends Application {
    /**
     * 账户输入框
     */
    @FXML
    private TextField account;
    /**
     * 密码输入框
     */
    @FXML
    private PasswordField password;
    /**
     * 登录按钮
     */
    @FXML
    private Button login;

    public static void main(String[] args) {
        launch(args);
    }

    @Override
    public void start(Stage primaryStage) throws Exception {
        //加载FXML资源文件
        FXMLLoader loader = new FXMLLoader(getClass().getResource("/index.fxml"));
        Pane tempPane =  loader.load();

        //构造对应的场景
        Scene tempScene = new Scene(tempPane);

        //添加场景到舞台中
        primaryStage.setScene(tempScene);

        //显示舞台
        primaryStage.show();
    }

}

六、添加事件

事件添加需要修改 fxml 与 controller

fxml

<?xml version="1.0" encoding="UTF-8"?>

<?import java.lang.*?>
<?import javafx.scene.text.*?>
<?import javafx.scene.control.*?>
<?import javafx.scene.layout.*?>

<AnchorPane maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="300.0" prefWidth="400.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1" fx:controller="com.cqmaple.javafx.FxMain">
   <children>
      <Label layoutX="134.0" layoutY="34.0" prefHeight="23.0" prefWidth="134.0" text="欢迎使用JavaFx">
         <font>
            <Font size="18.0" />
         </font>
      </Label>
      <Label layoutX="86.0" layoutY="100.0" text="请输入账户:" />
      <Label layoutX="86.0" layoutY="161.0" text="请输入密码:" />
      <TextField fx:id="account" layoutX="172.0" layoutY="95.0" />
      <PasswordField fx:id="password" layoutX="172.0" layoutY="156.0" />
      <Button onAction="#doLogin" fx:id="login" layoutX="295.0" layoutY="222.0" mnemonicParsing="false"  text="登录" />
   </children>
</AnchorPane>

新增的 home.fxml(成功后的场景)

<?xml version="1.0" encoding="UTF-8"?>

<?import javafx.scene.text.*?>
<?import javafx.scene.control.*?>
<?import java.lang.*?>
<?import javafx.scene.layout.*?>


<AnchorPane maxHeight="-Infinity" maxWidth="-Infinity" minHeight="-Infinity" minWidth="-Infinity" prefHeight="400.0" prefWidth="600.0" xmlns="http://javafx.com/javafx/8" xmlns:fx="http://javafx.com/fxml/1">
   <children>
      <Label layoutX="228.0" layoutY="186.0" text="恭喜成功登录">
         <font>
            <Font size="24.0" />
         </font>
      </Label>
   </children>
</AnchorPane>

controller代码:

package com.cqmaple.javafx;

import javafx.application.Application;
import javafx.event.ActionEvent;
import javafx.fxml.FXML;
import javafx.fxml.FXMLLoader;
import javafx.scene.Scene;
import javafx.scene.control.Alert;
import javafx.scene.control.Button;
import javafx.scene.control.PasswordField;
import javafx.scene.control.TextField;
import javafx.scene.layout.Pane;
import javafx.stage.Stage;

import java.io.IOException;

/**
 * Created by Maple on 2017/6/18.
 */
public class FxMain extends Application {
    /**
     * 将舞台设置到类中 事件使用
     */
    private static Stage stage;
    /**
     * 账户输入框
     */
    @FXML
    private TextField account;
    /**
     * 密码输入框
     */
    @FXML
    private PasswordField password;
    /**
     * 登录按钮
     */
    @FXML
    private Button login;

    public static void main(String[] args) {
        launch(args);
    }

    @Override
    public void start(Stage primaryStage) throws Exception {
        //加载FXML资源文件
        FXMLLoader loader = new FXMLLoader(getClass().getResource("/index.fxml"));
        Pane tempPane =  loader.load();

        //构造对应的场景
        Scene tempScene = new Scene(tempPane);

        //添加场景到舞台中
        primaryStage.setScene(tempScene);

        //显示舞台
        primaryStage.show();

        //将舞台放到类中
        stage=primaryStage;

    }

    /**
     * 登录事件
     * @param event 事件信息
     */
    @FXML
    public void doLogin(ActionEvent event){
        String accountStr=account.getText();
        String passwordStr=password.getText();
        if(isEmpty(accountStr)||isEmpty(passwordStr)){
            Alert alert = new Alert(Alert.AlertType.WARNING);
            alert.setTitle("Warning");
            alert.setHeaderText("验证错误");
            alert.setContentText("请输入账户及密码");
            alert.show();
        }
        //加载FXML资源文件
        FXMLLoader loader = new FXMLLoader(getClass().getResource("/home.fxml"));
        Pane tempPane = null;
        try {
            tempPane = loader.load();

            //构造对应的场景
            Scene tempScene = new Scene(tempPane);

            //设置场景
            stage.setScene(tempScene);
        } catch (IOException e) {
            e.printStackTrace();
            //TODO 如果失败的提示
        }


    }

    /**
     * 判断字符串是否为空
     * @param str
     * @return
     */
    private boolean isEmpty(String str){
        if(str==null){
            return false;
        }
        if(str.trim().length()==0){
            return false;
        }
        return true;
    }
}

好啦,结束。

入门差不多也就这样了。

另外api 地址:http://docs.oracle.com/javafx/2/api/

One Comment

  1. private boolean isEmpty(String str){
    if(str==null){
    return false;
    }
    if(str.trim().length()==0){
    return false;
    }
    return true;
    }
    反了,应改为
    private boolean isEmpty(String str){
    if(str==null){
    return true;
    }
    if(str.trim().length()==0){
    return true;
    }
    return false;
    }
    另外:
    if(isEmpty(accountStr)||isEmpty(passwordStr)){
    Alert alert = new Alert(Alert.AlertType.WARNING);
    alert.setTitle(“Warning”);
    alert.setHeaderText(“验证错误”);
    alert.setContentText(“请输入账户及密码”);
    alert.show();
    return; // 这里需要加一个 return 更加严谨
    }

发表评论

电子邮件地址不会被公开。 必填项已用*标注