从 table JavaFX 打开文件

Open file from table JavaFX

我在 JavaFX 应用程序中从 table 打开文件时遇到问题。当用户单击该行时,新的 window 应该打开,因为在 table 中我有专业文件的路径,例如:

1  document  C:/Users/document.docx

用户单击此行后,新办公室 window 将打开。下面我添加我的代码:

private void configureTableClick() {
    TableView<String[]> contentTable = contentPaneController.getContentTable();
    contentTable.addEventHandler(MouseEvent.MOUSE_CLICKED, mouseEvent -> {
            if (mouseEvent.getClickCount() == 1) {
                int selectedIndex = contentTable.getSelectionModel().getSelectedIndex();
                String fileToOpen;
                if (selectedIndex > 0) {
                    try {
                        Desktop.getDesktop().open(new File(fileToOpen));
                    } catch (IOException e) {
                        log.error(e.getMessage());
                    }
                }
            }
    });
}

注意 class Desktop belongs to AWT and according to this other Whosebug question – Is it OK to use AWT with JavaFx? – it is not recommended to mix the two. There is also an open bug: JDK-8240572

我提出两种选择。

  1. 如果您想使用 JavaFX,则使用 class ProcessBuilder 而不是 class Desktop 启动文件。这是示例代码。 (请注意,我在 Windows 10。)
import java.io.IOException;

import javafx.application.Application;
import javafx.beans.property.SimpleIntegerProperty;
import javafx.beans.property.SimpleStringProperty;
import javafx.beans.value.ObservableValue;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.scene.Scene;
import javafx.scene.control.SelectionModel;
import javafx.scene.control.TableColumn;
import javafx.scene.control.TableView;
import javafx.scene.layout.BorderPane;
import javafx.stage.Stage;

public class TableTst extends Application {
    private TableView<FileObj>  table;

    @Override
    public void start(Stage primaryStage) throws Exception {
        FileObj row = new FileObj(1, "document", "C:/Users/document.docx");
        ObservableList<FileObj> items = FXCollections.observableArrayList(row);
        table = new TableView<>(items);
        TableColumn<FileObj, Number> indexColumn = new TableColumn<>("Index");
        indexColumn.setCellValueFactory(param -> param.getValue().indexProperty());
        table.getColumns().add(indexColumn);
        TableColumn<FileObj, String> typeColumn = new TableColumn<>("Type");
        typeColumn.setCellValueFactory(param -> param.getValue().fileTypeProperty());
        table.getColumns().add(typeColumn);
        TableColumn<FileObj, String> pathColumn = new TableColumn<>("Path");
        pathColumn.setCellValueFactory(param -> param.getValue().filePathProperty());
        table.getColumns().add(pathColumn);
        SelectionModel<FileObj> tableSelectionModel = table.getSelectionModel();
        tableSelectionModel.selectedItemProperty().addListener(this::handleTableSelection);
        BorderPane root = new BorderPane(table);
        Scene scene = new Scene(root);
        primaryStage.setScene(scene);
        primaryStage.show();
    }

    private void handleTableSelection(ObservableValue<? extends FileObj> property,
                                      FileObj oldValue,
                                      FileObj newValue) {
        if (newValue != null) {
            String path = newValue.getFilePath();
            ProcessBuilder pb = new ProcessBuilder("cmd.exe", "/C", path);
            try {
                Process p = pb.start();
                p.waitFor();
            }
            catch (InterruptedException | IOException x) {
                x.printStackTrace();
            }
        }
    }

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

class FileObj {
    private SimpleIntegerProperty  index;
    private SimpleStringProperty  fileType;
    private SimpleStringProperty  filePath;

    public FileObj(int ndx, String type, String path) {
        index = new SimpleIntegerProperty(this, "index", ndx);
        fileType = new SimpleStringProperty(this, "fileType", type);
        filePath = new SimpleStringProperty(this, "filePath", path);
    }

    public int getIndex() {
        return index.get();
    }

    public SimpleIntegerProperty indexProperty() {
        return index;
    }

    public String getFileType() {
        return fileType.get();
    }

    public SimpleStringProperty fileTypeProperty() {
        return fileType;
    }

    public String getFilePath() {
        return filePath.get();
    }

    public SimpleStringProperty filePathProperty() {
        return filePath;
    }
}
  1. AWT 可与 Swing 一起使用,因此如果您愿意使用 Swing[=31],则可以使用 class Desktop =] 而不是 JavaFX。这是示例代码。
import java.awt.Desktop;
import java.awt.EventQueue;
import java.io.File;
import java.io.IOException;

import javax.swing.JFrame;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.event.ListSelectionEvent;

public class TesTable {
    private JFrame  frame;
    private JTable  table;

    private JScrollPane createTable() {
        String[] columns = new String[]{"Index", "Type", "Path"};
        String[][] data = new String[][]{{"1", "document", "C:/Users/document.docx"}};
        table = new JTable(data, columns);
        table.setAutoResizeMode(JTable.AUTO_RESIZE_OFF);
        table.getSelectionModel().addListSelectionListener(this::handleTableSelection);
        JScrollPane scrollPane = new JScrollPane(table);
        return scrollPane;
    }

    private void showGui() {
        frame = new JFrame();
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.add(createTable());
        frame.pack();
        frame.setLocationByPlatform(true);
        frame.setVisible(true);
    }

    private void handleTableSelection(ListSelectionEvent event) {
        if (Desktop.isDesktopSupported()) {
            Desktop desktop = Desktop.getDesktop();
            int ndx = event.getFirstIndex();
            if (ndx >= 0) {
                String path = (String) table.getValueAt(ndx, 2);
                File f = new File(path);
                try {
                    desktop.open(f);
                }
                catch (IOException xIo) {
                    xIo.printStackTrace();
                }
            }
        }
    }

    public static void main(String[] args) {
        final TesTable instance = new TesTable();
        EventQueue.invokeLater(() -> instance.showGui());
    }
}

请注意,以上两个代码示例都使用了 method references