Как позиционировать компоненты Java Swing при наличии JScrollPane

Я новичок в создании графических интерфейсов и Java Swing, и я пытаюсь создать графический интерфейс, который отображает таблицу из базы данных SQL. Таблица отображается с помощью JScrollPane. Сначала я подумал, что другие мои компоненты (JLabel и JTextField) не добавляются на панель содержимого, но на самом деле они были просто скрыты под ScrollPane. После уменьшения размеров ScrollPane теперь отображаются эти другие компоненты, но их нельзя позиционировать с помощью метода setBounds, и они всегда появляются в одном и том же месте, так что последний добавленный компонент полностью закрывает другие. Помимо кода, я также включил скриншот того, как выглядит графический интерфейс.

import java.awt.BorderLayout;
import java.awt.Dimension;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;


import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.JTextField;
import javax.swing.event.TableModelListener;
import javax.swing.table.DefaultTableModel;

public class LibraryAppGUI extends JFrame {
    String sql;
    String DB_PATH = LibraryAppGUI.class.getResource("LibraryManagement3.sqlite").getFile();
    
    private JTable table;
    private String columns[] = {"PatronFirstName", "PatronLastName"};
    private TableModelListener tableModelListener;
    
    public LibraryAppGUI () {
        DefaultTableModel model = new DefaultTableModel(columns, 0);
        table = new JTable(model);
        
        try{populateSQL(table);} catch(Exception e1) {e1.printStackTrace();}
        table.setCellSelectionEnabled(true);
        table.setPreferredScrollableViewportSize(new Dimension(600, 300));
        table.setFillsViewportHeight(false);
        
        
        JScrollPane scrollPane = new JScrollPane(table);
        scrollPane.setVisible(true);
        getContentPane().add(scrollPane, BorderLayout.PAGE_START);
    }
    

    
    public void createSQL() throws ClassNotFoundException, SQLException {
        Class.forName("org.sqlite.jdbc");
        Connection connection = DriverManager.getConnection("jdbc:sqlite:" + DB_PATH);
        PreparedStatement stmt = connection.prepareStatement("");
        
    }
    public void populateSQL(JTable table) throws ClassNotFoundException, SQLException {
        sql = "select PatronFirstName, PatronLastName\r\n" + 
                "FROM Patron\r\n";
        Class.forName("org.sqlite.JDBC");
        Connection connection = DriverManager.getConnection("jdbc:sqlite:" + DB_PATH);
        PreparedStatement stmt = connection.prepareStatement(sql);
        ResultSet res = stmt.executeQuery();
        
        while(res.next()) {
            Object[] row = new Object[columns.length];
            for (int i = 1; i <= columns.length; i++) {
                row[i-1] = res.getObject(i);
            }
            ((DefaultTableModel) table.getModel()).insertRow(res.getRow()-1, row);  
        }
        res.close();
        connection.close();
    }
    
    
    public static void main(String[] args) {
        LibraryAppGUI window = new LibraryAppGUI();
        //label to prompt user
        JLabel welcome = new JLabel("Welcome to the library. Choose your patron: ");
        welcome.setBounds(50,50, 100, 30);
        window.getContentPane().add(welcome);
        
        JTextField user = new JTextField("Enter the full name in this box.");
        user.setBounds(150,150,100,30);
        window.getContentPane().add(user);
        
        window.setDefaultCloseOperation(EXIT_ON_CLOSE);
        window.pack();
        window.setLocationRelativeTo(null);
        window.setVisible(true);
        
    }
} 

Как позиционировать компоненты Java Swing при наличии JScrollPane

Изображения могут отображаться только при загрузке на этот сайт, а не на сторонний сайт.

camickr 11.12.2020 02:30
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
Как вычислять биты и понимать побитовые операторы в Java - объяснение с примерами
Как вычислять биты и понимать побитовые операторы в Java - объяснение с примерами
В компьютерном программировании биты играют важнейшую роль в представлении и манипулировании данными на двоичном уровне. Побитовые операции...
Поднятие тревоги для долго выполняющихся методов в Spring Boot
Поднятие тревоги для долго выполняющихся методов в Spring Boot
Приходилось ли вам сталкиваться с требованиями, в которых вас могли попросить поднять тревогу или выдать ошибку, когда метод Java занимает больше...
Полный курс Java для разработчиков веб-сайтов и приложений
Полный курс Java для разработчиков веб-сайтов и приложений
Получите сертификат Java Web и Application Developer, используя наш курс.
1
1
113
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Почему вы создаете свои компоненты Swing в двух разных местах?

  1. Не создавайте компоненты в методе main().
  2. Метка, текстовое поле и таблица должны быть созданы и добавлены во фрейм в конструкторе так же, как вы создаете и добавляете область прокрутки/таблицу.

В вашем коде ниже:

JLabel welcome = new JLabel("Welcome to the library. Choose your patron: ");
welcome.setBounds(50,50, 100, 30);
window.getContentPane().add(welcome);

JTextField user = new JTextField("Enter the full name in this box.");
user.setBounds(150,150,100,30);
window.getContentPane().add(user);

Операторы setBounds(...) НЕ ДОЛЖНЫ использоваться. По умолчанию панель содержимого фрейма использует BorderLayout. Менеджер компоновки установит размер/расположение компонентов на основе правил менеджера компоновки.

Если вы не указываете ограничение при добавлении компонентов, используется BorderLayout.CENTER. Однако вы можете добавить только один компонент в ЦЕНТР, поэтому только текстовое поле имеет правильный размер/местоположение. Метка игнорируется.

Итак, если вы переместите код графического интерфейса из метода main() в конструктор, правильным дизайном будет что-то вроде:

JPanel top = new JPanel();
top.add(welcome);
top.add(user);

add(top, BorderLayot.PAGE_START);

то вы также использовали бы:

//getContentPane().add(scrollPane, BorderLayout.PAGE_START);
add(scrollPane, BorderLayout.CENTER);

Теперь это будет отображать метку и текстовое поле в верхней части фрейма и область прокрутки в центре. Полосы прокрутки автоматически настраиваются при изменении размера кадра.

Другие вопросы по теме