JFileChooser 在选择项目之前调用文件资源管理器两次

JFileChooser calls file explorer twice before item is selected

我正在尝试使用 JFileChooser 为我的库存控制软件获取数据库文件的目录。

问题是JFileChooser只有在文件资源管理器显示两次并选择文件两次后才获取文件的目录。

代码如下:

package groupassignment;
import java.io.File;
import java.sql.Connection;
import java.sql.*;
import java.sql.SQLException;
import javax.swing.*;

/**
 *
 * @author ashraf141298
 */ 
public class GetDatabase {
    static Connection con;
    static Statement st;
    static ResultSet rs;

    public GetDatabase() {
        connect();
    }

    public String getFileDirectory() {
        JFileChooser filechooser = new JFileChooser();
        File db = null;
        String directory;

        if(filechooser.showOpenDialog(null) == JFileChooser.APPROVE_OPTION) {
            db = filechooser.getSelectedFile();
            System.out.println("Opening file: " + db);
        } else {
            System.out.println("No file was chosen or an error occured");
            System.exit(0);
        };

        directory = db.toString();
        return directory;
    }

    public void connect() {
        try{
            String dbURL = "jdbc:ucanaccess://" + getFileDirectory();

            // Attempt to connect to the database
            con = DriverManager.getConnection(dbURL);

            // Extract data from the table using SQL sta
            st = con.createStatement();
            String query = "select * from ProductBarcodes";
            rs = st.executeQuery(query);
        } catch(SQLException e){
            JOptionPane.showMessageDialog(null, "Unable to connect to database", "Error", JOptionPane.ERROR_MESSAGE);
            System.exit(0);
        } 
    }

    public static void main(String[] args) {
        GetDatabase database = new GetDatabase();
        DisplayDatabase gui = new DisplayDatabase();
    }
}

显示数据库代码:

package groupassignment;
import static groupassignment.GetDatabase.rs;
import javax.swing.*;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.sql.SQLException;
import java.util.Vector;
import javax.swing.table.DefaultTableModel;

/**
 *
 * @author ashraf141298
 */
public class DisplayDatabase extends GetDatabase {
    public DisplayDatabase() {
        display();
    }

    public void display() {
        // It creates and displays the table
        JTable table = null;

        try {
            table = new JTable(buildTableModel(rs));
        } catch (SQLException ex) {
            System.out.println("Unable to create JTable");
        }

        // Closes the Connection
        JOptionPane.showMessageDialog(null, new JScrollPane(table), "Current Stocklist", JOptionPane.INFORMATION_MESSAGE);
    }

    public static DefaultTableModel buildTableModel(ResultSet rs) throws SQLException {
        ResultSetMetaData metaData = rs.getMetaData();

        // get the names of columns 
        Vector<String> columnNames = new Vector<String>();
        int columnCount = metaData.getColumnCount();
        for (int column = 1; column <= columnCount; column++) {
            columnNames.add(metaData.getColumnName(column));
        }

        // get the data of the table
        Vector<Vector<Object>> data = new Vector<Vector<Object>>();
        while (rs.next()) {
            Vector<Object> vector = new Vector<Object>();
            for (int columnIndex = 1; columnIndex <= columnCount; columnIndex++) {
                vector.add(rs.getObject(columnIndex));
            }
            data.add(vector);
        }

        // return the database in TableModel form
        return new DefaultTableModel(data, columnNames);

     }                

}

可能该函数被触发了不止一次,您调用文件选择器的代码似乎工作正常。

您已将 DisplayDatabase 扩展为 GetDatabase class

DisplayDatabase extends GetDatabase{
  ...
}

因此,当您创建 GetDatabase 的新实例时 class 超级 class 的构造函数 [GetDatabase] 被调用并再次调用连接方法。

所以你会得到另一个 jfilechooser 弹出窗口 window。

 GetDatabase database = new GetDatabase();

那么如何修复

如果您不想继承 GetDatabase class 的任何内容,您可以删除扩展部分。

但是如果你想继承 GetDatabase class 那么,

而不是从构造函数连接数据库,你可以从一个方法来完成。

public GetDatabase() {
   // connect();// not here
}

public void ConnectDatabase(){
    connect();
}

所以你调用这个方法。

public static void main(String[] args) {
    GetDatabase database = new GetDatabase();
    database.ConnectDatabase();
    DisplayDatabase gui = new DisplayDatabase();
}