Java Swing GridBagLayout 在其他组件之间添加组件

标签 java swing jscrollpane

我想要实现的目标:我希望能够将组件添加到已添加组件之间的滚动 Pane 中。换句话说,我想以某种方式将索引向上移动,并在旧组件所在的位置放置一些新组件。我创建了一个简短的程序来说明我的问题,它替换了未添加的组件。有人可以帮忙吗?

为什么我想实现它(为了回答与此相关的不可避免的问题,只有感兴趣时才阅读这篇文章):我有一个滚动 Pane ,我需要在其中显示大量组件,大约150000 个 JTable。这需要太多的内存和处理时间。所以我所做的就是加载带有 150000 个文本字段的滚动 Pane ,并且一次只显示 100 个表格。如果滚动到文本字段 200,它将加载接下来的 100 个表格,并用表格替换之前创建的文本字段。如果您移动到文本字段 300,它将加载接下来的 100 个表格,并删除前 100 个表格,再次用文本字段替换它。我的想法是,文本字段比表格占用的资源要少得多,到目前为止,这种想法似乎是正确的。所以这一切似乎都工作得很好(在我较小的测试文件上 - 大约 5000 条记录)。问题是创建 150000 个文本字段也需要大量时间。我想到了一个解决方案。不为每个表创建一个文本字段,而是为每 100 个表创建 1 个文本字段。这个想法是,当您滚动到文本字段 2(而不是 200)时,它会加载接下来的 100 个表,将文本字段 nr 2 替换为表 nr 200 - 299。所以不知何故,我需要将文本字段 3 及其下面的所有内容按顺序向下移动插入所有表。唷,希望这是有道理的

因此,看看下面的示例,我实际上想要实现的是将文本字段 20 替换为 5 个新文本字段,但不替换文本字段 21 - 25。

    import javax.swing.*;
    import java.awt.*;

    public class Example {
    public static void main(String args[]) {

        SwingUtilities.invokeLater(new Runnable() {
            public void run() {
                ExampleScreen ex = null;
                    ex = new ExampleScreen();
                    ex.setVisible(true);
            }
        });
    }

    private static class ExampleScreen extends JFrame{

        GridBagConstraints gc = new GridBagConstraints();
        JPanel panel = new JPanel(new GridBagLayout());
        JScrollPane scrollPane = new JScrollPane(panel);

        public ExampleScreen() {
            setDefaultCloseOperation(EXIT_ON_CLOSE);
            this.add(scrollPane, BorderLayout.CENTER);
            setupFields();
            createExtraFieldsInbetween(20);
            this.pack();
            scrollPane.getVerticalScrollBar().setUnitIncrement(16);
            scrollPane.getViewport().setScrollMode(JViewport.BLIT_SCROLL_MODE);
        }    

        //after this happens i need to add components somewhere in the middle, like after textfield 20 for example
        private void setupFields() {    
            gc.gridy = 0;
            gc.gridx = 0;
            for(int k = 0; k < 50; k++) {
                JTextField textField = new JTextField();
                textField.setPreferredSize(new Dimension(1500,36));
                textField.setText(new Integer(k).toString());
                panel.add(textField, gc, k);
                gc.gridy++;
            }
        }

        //this is to create extra fields inbetween those already created
        //this does not work, it overwrites the existing components, doesnt move them up
        private void createExtraFieldsInbetween(int i) {    
            gc.gridy = i;    
            //create 5 extra
            for(int k = i; k < i + 5; k++) {
                JTextField textField = new JTextField();
                textField.setPreferredSize(new Dimension(1500,36));
                textField.setText("Extra Field : " + new Integer(k).toString());
                panel.add(textField, gc, k);
                gc.gridy++;
            }
        }
    }
}

最佳答案

每当我看到像 150,000 这样的数字时,我认为用户不会费心滚动所有这些组件,因此您需要更好的 UI。

无论如何,如果您对 GridBagLayout 有问题,请不要使用 GridBagLayout。

在我看来,您只是垂直显示组件,因此请尝试 BoxLayout。然后,您可以使用 add(...) 方法来指定要删除/添加组件的索引。

关于Java Swing GridBagLayout 在其他组件之间添加组件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21328297/

相关文章:

java - 如何使用replaceAll函数来屏蔽数字? (Java 图形用户界面)

java - 在 Java 中加载时镜像动画 gif - ImageIcon

javascript - jScrollPane 停止使用 .append() 插入子元素

Java Swing JTextArea 行号

java - 在使用Gradle构建的Java控制台应用程序中使用system.in的任何替代方法?

java - 使用 Java 将 PDF 转换为 Swf

java - 将Word文件保存在特定位置

java - 如何在多页中打印一个大的 JPanel

Java 克隆数组作为构造函数中的参数

java - 不同结构的Jtable