简体   繁体   English

对于JFrame中的搜索查询,JTable仅显示一次

[英]JTable gets displayed only once for search query in JFrame

So, after giving a layout to my controls, I find that my table doesn't seem to display. 因此,在为控件提供布局后,我发现我的表似乎没有显示。 Label (l1), the combobox and the submit button gets displayed in my desired manner, even the console messages workk fine. 标签(l1),组合框和提交按钮以我期望的方式显示,即使控制台消息也可以正常工作。 Just that the Jtable that should appear after the search doesn't get displayed. 只是搜索后应该出现的Jtable不会显示。

Where could the error lie and how should it be corrected. 错误可能出在哪里,应如何纠正。 This is my code:- 这是我的代码:


import java.awt.*;
import java.awt.event.*;
import java.io.File;
import java.sql.*;
import java.util.Vector;

import javax.swing.*;
import javax.swing.table.DefaultTableModel;

public class r_search_2 extends JFrame implements ActionListener {

    JFrame frame1;
    JLabel l0, l1, l2;
    JComboBox c1;
    JButton b1;
    Connection con;
    ResultSet rs, rs1;
    Statement st, st1;
    PreparedStatement pst;
    String ids;
    static JTable table  = new JTable();;
    String[] columnNames = {"SECTION NAME", "REPORT NAME", "CONTACT", "LINK"};
    String from;
    Vector v = new Vector();
    JMenuBar menu = new JMenuBar();


    JPanel mainPanel = new JPanel(new BorderLayout());
    JPanel topPanel = new JPanel(new FlowLayout(SwingConstants.LEADING, 60,25));


    r_search_2() 
    {

        b1 = new JButton("submit");

        //l0.setBounds(100, 50, 350, 40);
        l1.setBounds(75, 110, 75, 20);
        b1.setBounds(150, 150, 150, 20);
        b1.addActionListener(this);

        topPanel.add(l1);

        try 
        {

            File dbFile = new File("executive_db.accdb");
            String path = dbFile.getAbsolutePath();
            con = DriverManager.getConnection("jdbc:odbc:Driver={Microsoft Access Driver (*.mdb, *.accdb)}; DBQ= " + path);
            Class.forName("sun.jdbc.odbc.JdbcOdbcDriver");
            st = con.createStatement();
            rs = st.executeQuery("select index_name from Index1");
           while (rs.next())
           {
                ids = rs.getString(1);
                v.add(ids);

            }
            c1 = new JComboBox(v);
            c1.setEditable(true);c1.setSelectedItem("");
            c1.setBounds(150, 110, 150, 20);


            topPanel.add(c1);
            topPanel.add(b1);
            mainPanel.add(topPanel, BorderLayout.PAGE_START);

            st.close();
            rs.close();
        } catch (Exception e) {
        }
       // setVisible(true);
    }

    public void actionPerformed(ActionEvent ae) {
        if (ae.getSource() == b1) {
            showTableData();
        }
     }

    public void showTableData()
    {

        DefaultTableModel model = new DefaultTableModel();
        model.setColumnIdentifiers(columnNames);

        table.setModel(model);
        table.setAutoResizeMode(JTable.AUTO_RESIZE_ALL_COLUMNS);
        table.setFillsViewportHeight(true);
        JScrollPane scroll = new JScrollPane(table);
        scroll.setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_AS_NEEDED);
        scroll.setVerticalScrollBarPolicy( JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED);
        from = (String) c1.getSelectedItem();

        String section_name = "";
        String report_name = "";
        String contact_name = "";
        String link = "";


        try
        {

        pst = con.prepareStatement("select distinct Section.Section_Name,Report.Report_Name,Report.Link,Contact.Contact_Name "
                        + "FROM (( Section INNER JOIN Report ON Report.Section_ID=Section.Section_ID ) INNER JOIN Contact ON Contact.Contact_ID=Report.Contact_ID )  LEFT JOIN Metrics ON Metrics.Report_ID=Report.Report_ID  "
                        + " WHERE Section.Section_Name LIKE '%"+from+"%' OR Report.Report_Name LIKE '%"+from+"%' OR Metrics.Metric_Name LIKE '%"+from+"%' OR Contact.Contact_Name LIKE '%"+from+"%' ");
            ResultSet rs = pst.executeQuery();
            int i = 0;
            while (rs.next()) {
                section_name = rs.getString("Section_Name");
                report_name = rs.getString("Report_Name");
                contact_name = rs.getString("Contact_Name");
                link = rs.getString("Link");
                model.addRow(new Object[]{section_name, report_name, contact_name, link});
                i++;
            }
            if (i < 1) {
                JOptionPane.showMessageDialog(null, "No Record Found", "Error", JOptionPane.ERROR_MESSAGE);
            }
            if (i == 1) {
                System.out.println(i + " Record Found");
            } else {
                System.out.println(i + " Records Found");
            }
        } catch (Exception ex) {
            JOptionPane.showMessageDialog(null, ex.getMessage(), "Error", JOptionPane.ERROR_MESSAGE);
        }
        mainPanel.add(scroll);
        mainPanel.revalidate();
        mainPanel.repaint();

    }

    public static void main(String args[]) {


        r_search_2 s=new r_search_2();
        //new r_search_2();
        JFrame fr=new JFrame("Search Executive Reports");
        //fr.add(s.getUI());
        fr.add(s.mainPanel);
        fr.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
        fr.setLocationByPlatform(true);
        fr.setSize(1000, 400);
        //fr.pack();
        fr.setVisible(true);

      //  new r_search_2();
    }
}

General comments: 普通的留言:

  1. Use reasonable variable names if you want people to take the time to read your code. 如果您希望人们花时间阅读代码,请使用合理的变量名。 "b1", "l1" mean nothing. “ b1”,“ l1”没有任何意义。
  2. Get rid of all the setBounds() statements. 摆脱所有setBounds()语句。 Your panel uses a FlowLayout and the FlowLayout will determine the size/location of the components. 您的面板使用FlowLayout,FlowLayout将确定组件的大小/位置。

It doesn't appear the next time I type anything to search. 下次输入任何要搜索的内容时,它不会出现。

You are adding the table to the CENTER of the BorderLayout. 您将表添加到BorderLayout的CENTER。 So you now have two tables displayed in the CENTER. 因此,您现在在CENTER中显示了两个表。 Swing paints the tables in reverse order to how the table were added. Swing按与添加表相反的顺序绘制表。 So the second table gets painted first, and the first table added gets painted second. 因此,第二张表首先绘制,第二张表首先绘制。 So the first table is painted on top of the second table. 因此,第一个表被绘制在第二个表的顶部。

So you would need to remove the old scollpane first before adding the second scrollpane. 因此,在添加第二个滚动窗格之前,您需要先删除旧的scollpane。

However there is an easier solution. 但是,有一个更简单的解决方案。 As Sergiy has already suggested just create a new TableModel and replace the TableModel in the existing table: 正如Sergiy已经建议的那样,只需创建一个新的TableModel并替换现有表中的TableModel即可:

table.setModel( theNewModel );

So really you should create the JTable and scrollpane and add it to your frame when you create the initial GUI. 因此,实际上,您应该创建JTable和滚动窗格,并在创建初始GUI时将其添加到框架中。 Then your search logic will just create a new DefaultTableModel and you update the table with the code from above. 然后,您的搜索逻辑将仅创建一个新的DefaultTableModel,并使用上面的代码更新该表。

Edit: 编辑:

In the constructor where you create all the Swing components the basic code might be something like: 在创建所有Swing组件的构造函数中,基本代码可能类似于:

mainPanel.add(topPanel, BorderLayout.PAGE_START);
JScrollPane scrollPane = new JScrollPane(table); // added
mainPanel.add(scrollPane, BorderLayout.CENTER); // added

Now you have created and added an empty table to your GUI. 现在,您已经创建了一个空表并将其添加到GUI。 The model is empty so there is nothing to display. 该模型为空,因此没有任何显示。

Now in your showTableData() method you don't need to create any more Swing components, So delete all those line of code that create the scrollpane and add the scrollpane to the frame. 现在,在showTableData()方法中,您无需再创建任何Swing组件,因此,请删除所有创建滚动窗格的代码行,并将滚动窗格添加到框架中。

The remaining code creates the model and adds it to the table and then adds data to the model so it should work as is. 剩下的代码创建模型并将其添加到表中,然后将数据添加到模型中,这样它应该可以正常工作。 Although to be more efficient, you may want to move the table.setModel(...) statement to the end of the method so the table is only updated once after all the data has been loaded into the model. 尽管效率更高,但您可能希望将table.setModel(...)语句移到方法的末尾,因此,在将所有数据加载到模型中之后,该表仅更新一次。

It's a bad practice, but you can do following 这是一个不好的做法,但是您可以按照以下步骤进行操作

    mainPanel.add(scroll);
    mainPanel.revalidate()
    mainPanel.repaint();

Good practice is to use CardLayout with empty panel when no search results must be shown. 优良作法是在不必显示搜索结果的情况下,将CardLayout与空白面板一起使用。

Just a quick redesign of what you have done 只是快速重新设计您所做的

Improvements: I quickly tried to divide the interface from the code bit, hope this help 改进:我很快尝试将接口与代码位分开,希望对您有所帮助

public class r_search_2 extends JFrame implements ActionListener {

r_search_2(String Title) 
{
    super(Title);

    init();
}

private void init(){
    b1 = new JButton("submit");
    b1.addActionListener(this);


    c1 = new JComboBox(v);
    c1.setEditable(true);c1.setSelectedItem("");
    c1.setBounds(150, 110, 150, 20);

    topPanel.add(c1);
    topPanel.add(b1);
    mainPanel.add(topPanel, BorderLayout.PAGE_START);

    DefaultTableModel model = new DefaultTableModel();
    model.setColumnIdentifiers(columnNames);

    table.setModel(model);
    table.setAutoResizeMode(JTable.AUTO_RESIZE_ALL_COLUMNS);
    table.setFillsViewportHeight(true);
    JScrollPane scroll = new JScrollPane(table);
    scroll.setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_AS_NEEDED);
    scroll.setVerticalScrollBarPolicy( JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED);
    from = (String) c1.getSelectedItem();

    String section_name = "";
    String report_name = "";
    String contact_name = "";
    String link = "";

    mainPanel.add(scroll);
    this.add(mainPanel);
    this.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
    this.setLocationByPlatform(true);
    this.setSize(1000, 400);
    this.setVisible(true);

}   


public static void main(String args[]) {


    r_search_2 s=new r_search_2("Search Executive Reports");

}
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM