项目第二天 :表

关于制作表的学习:https://docs.oracle.com/javase/8/javafx/api/javafx/scene/control/TableView.html

<S>表中对象的类

先构造对象:

public class Student {

    public int id;
    public int age;
    public String name;
    public String gender;

    public Student(int id, int age, String name, String gender) {
        this.id = id;
        this.age = age;
        this.name = name;
        this.gender = gender;
    }

}

然后在Main方法中的可视化代码的结构中添加表

这样就把表的结构建立好了:

接下来就是往表中添加内容:

点击一下,往表里面添加一行数据,

发生了点击事件,然后从输入框读取文字,然后调用addStudent,读取的内容为学生姓名,id自增,年龄,性别,随机生成。只有主线程执行,不需要考虑线程安全问题,最终拿到tableView.getItems,也就是学生的所有项,用尾插的方式往表里添加就可以了。

tableView是创建的时候赋值的,可以认为是拿到真实的tableView。

内容已经添加进去,但是没有显示:

原因就是缺少映射关系:每个对象的属性所对应的表头。TableView不能自己处理,需要手动添加一一映射关系。

所以现在要令表中数据显示出来,对表中数据添加映射关系:

其他三列数据同理,结果就可以看到表中数据了:

数据的可视化代码优化:把数据处理放在Student(模型层)中,可以减少代码,令代码更具有条理

以上是代码方式,fxml方式比较简单,单排查问题难:

<?import javafx.geometry.Insets?>
<?import javafx.scene.layout.GridPane?>

<?import javafx.scene.control.Button?>
<?import javafx.scene.control.Label?>

<?import javafx.scene.control.TextField?>
<?import javafx.scene.control.TableView?>
<?import javafx.scene.control.TableColumn?>
<?import javafx.scene.control.cell.PropertyValueFactory?>
<GridPane fx:controller="sample.Controller"
          xmlns:fx="http://javafx.com/fxml"
          alignment="center"
          hgap="10"
          vgap="10">
    <TextField fx:id="inputField" GridPane.rowIndex="0" GridPane.columnIndex="0" />
    <Button text="点击我" GridPane.rowIndex="1" GridPane.columnIndex="0" onMouseClicked="#点击事件"/>
    <Label fx:id="outputLabel" GridPane.rowIndex="2" GridPane.columnIndex="0" prefWidth="200" style="-fx-border-color: black; -fx-border-width: 1; -fx-border-radius: 5" />


    <TableView fx:id="tableView" GridPane.rowIndex="3" GridPane.columnIndex="0">
        <columns>
            <TableColumn text="#ID">
                <cellValueFactory>
                    <PropertyValueFactory property="id"/>
                </cellValueFactory>
            </TableColumn>
            <TableColumn text="姓名">
                <cellValueFactory>
                    <PropertyValueFactory property="name"/>
                </cellValueFactory>
            </TableColumn>
            <TableColumn text="年龄">
                <cellValueFactory>
                    <PropertyValueFactory property="age"/>
                </cellValueFactory>
            </TableColumn>
            <TableColumn text="性别">
                <cellValueFactory>
                    <PropertyValueFactory property="gender"/>
                </cellValueFactory>
            </TableColumn>
        </columns>
    </TableView>


</GridPane>

至此,项目前期的如何制作界面的内容准备好了。

 

开始后端逻辑的处理:

选择一个文件夹作为根文件夹,根据文件名搜索该文件下的符合条件的文件;

文件夹路径 ->  List<文件路径>

文件系统是树形结构组织

给定根节点,遍历以该节点为跟的树。

遍历问题:深度优先遍历、广度优先遍历

文件=元信息+内容

       =Meta(文件名/文件路径/文件大小/权限/属性)+Content

java.io.File类

三种遍历方法:

深度优先遍历:

广度优先遍历:

    //广度优先 -层序遍历-队列
    private static void traversalBroadcast(File root) {
        //所有文件都放入队列
        Queue<File> queue = new LinkedList<>();
        queue.offer(root);//先把root放进去

        while (!queue.isEmpty()) {
            File file = queue.poll();
            boolean directory = file.isDirectory();
            if (directory) {
                System.out.println("文件夹:" + file);
            }else {
                System.out.println("普通文件:" + file);
            }

            File[] files = file.listFiles();
            if (files == null) {
                continue;
            }
            if (files.length == 0) {
                continue;
            }
            for (File child : files) {
                queue.offer(child);
            }
        }
    }

实际项目中用哪个都可以,找东西层序遍历(广度优先遍历)比较好。

然后在fxml里添加对话框,以供用户选择文件夹进行索引。

在Controller中实现

此时就可以索引文件夹中的内容,在idea中出现结果,但还没有在表单中显示。

把结果放入表中:新建一个file-scan.fxml

?import javafx.geometry.Insets?>
<?import javafx.scene.layout.GridPane?>

<?import javafx.scene.control.Button?>
<?import javafx.scene.control.Label?>

<?import javafx.scene.control.TextField?>
<?import javafx.scene.control.TableView?>
<?import javafx.scene.control.TableColumn?>
<?import javafx.scene.control.cell.PropertyValueFactory?>
<GridPane fx:controller="sample.FileScanController"
          xmlns:fx="http://javafx.com/fxml"
          alignment="center"
          hgap="10"
          vgap="10"
          fx:id="rootGridPane">

    <Button text="选择文件夹" GridPane.rowIndex="1" GridPane.columnIndex="0" onMouseClicked="#选择文件夹"/>

    <TableView fx:id="tableView" GridPane.rowIndex="3" GridPane.columnIndex="0" prefWidth="1000">
        <columns>
            <TableColumn text="文件 OR 文件夹">
                <cellValueFactory>
                    <PropertyValueFactory property="directory" />
                </cellValueFactory>
            </TableColumn>

            <TableColumn text="路径">
                <cellValueFactory>
                    <PropertyValueFactory property="path" />
                </cellValueFactory>
            </TableColumn>
        </columns>
    </TableView>


</GridPane>

新建一个FileScanController类与上面关联

package sample;

import javafx.application.Platform;
import javafx.fxml.FXML;
import javafx.scene.control.TableView;
import javafx.scene.input.MouseEvent;
import javafx.scene.layout.GridPane;
import javafx.stage.DirectoryChooser;

import java.io.File;

/**
 * Created with IntelliJ IDEA.
 * Description:
 * User: 联想
 * Date: 2021-01-19
 * Time: 1:59
 */
public class FileScanController {
    @FXML
    public GridPane rootGridPane;
    @FXML
    public TableView tableView;
    @FXML
    public void 选择文件夹(MouseEvent mouseEvent) {
        DirectoryChooser chooser = new DirectoryChooser();
        File root = chooser.showDialog(rootGridPane.getScene().getWindow());
        if(root == null) {
            return;
        }

        Thread t = new Thread(() -> {
            scan(root);
        });
        t.setDaemon(true);
        t.start();
    }
    //调用该方法,既有文件夹,又有普通文件
    private void scan(File root) {
        Platform.runLater(() -> {
            FileMeta fileMeta = new FileMeta(root);
            tableView.getItems().add(fileMeta); // 涉及 UI 部分的,放到主线程执行
        });

        if (!root.isDirectory()) {
            return;
        }

        File[] children = root.listFiles();
        if (children == null) {
            return;
        }

        for (File child : children) {
            scan(child);
        }
    }
}

然后构建文件夹所对应的对象,现在要搜索的是文件夹而不是学生类。

package sample;

import java.io.File;

/**
 * Created with IntelliJ IDEA.
 * Description:
 * User: 联想
 * Date: 2021-01-19
 * Time: 2:03
 */
public class FileMeta {
    private final File file;

    public FileMeta(File file) {
        this.file = file;
    }
    public String getDirectory() {
        if (file.isDirectory()) {
            return "文件夹";
        }else {
            return "普通文件";
        }
    }

    public String getPath() {
        return file.getAbsolutePath();
    }

    @Override
    public String toString() {
        return file.toString();
    }
}

在Main方法中修改路径:

启动后就可以实现文件搜索了。

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值