有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

尽管使用了:setVerticalScrollBarPolicy(JScrollPane.VERTICAL\u SCROLLBAR\u ALWAYS),但JScrollPane滚动条未显示的java奇怪问题;

因此,在下面的代码中,我在左侧有一个JTextArea。右上侧的JScrollPane看起来不错。使用相同的代码,我还在右下角添加了一个JScrollPane,但尽管代码相同,但保存了首选大小和绝对位置,垂直滚动条似乎没有显示出来

我将在代码之后添加GUI的屏幕截图。提前感谢您为解决此问题提供的任何帮助

    frame = new JFrame("Title");
    frame.setLayout(null);
    frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
    frame.getContentPane().setPreferredSize(new Dimension(width, height));      
    frame.pack();

    Dimension dim = Toolkit.getDefaultToolkit().getScreenSize();
    frame.setLocation(dim.width/2-frame.getSize().width/2, dim.height/2-frame.getSize().height/2);
    frame.setResizable(false);
    frame.addKeyListener(this);

    //scroll and text area
        textArea = new JTextArea();
        textArea.setText("Static Text\n");
        textArea.setFont(new Font("Consolas", 0, 12));      
        textArea.setColumns(50);
        textArea.setLineWrap(true);
        textArea.setEditable(false);
        scrollPane = new JScrollPane(textArea);
        scrollPane.setPreferredSize(new Dimension(width/2, height * 4 / 5));
        scrollPane.setBounds(width/2, 0, width/2, height * 4 / 5);
        scrollPane.setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS);
        frame.add(scrollPane);
        inputTextArea = new JTextArea();
        inputTextArea.setText(">");
        inputTextArea.setFont(new Font("Consolas", 0, 12));     
        inputTextArea.setColumns(50);
        inputTextArea.setLineWrap(true);
        inputScrollPane = new JScrollPane(inputTextArea);
        inputScrollPane.setPreferredSize(new Dimension(width/2, height / 5));               
        inputScrollPane.setBounds(width/2, height * 4 / 5, width, height);
        inputScrollPane.setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS);
        frame.add(inputScrollPane);
    //map
        mapView = new JTextArea();
        mapView.setFont(new Font("Consolas", 0, 8));        
        mapView.setEditable(false);
        mapView.setPreferredSize(new Dimension(width/2, height));
        mapView.setText(state.getCurrentMap().toString());
        mapView.addKeyListener(this);
        mapView.setBounds(0, 0, width/2, height);
        frame.add(mapView);

    frame.pack();
    frame.setVisible(true);

As you can see, the lower right JScrollPane is missing the vertical scroll bar


共 (1) 个答案

  1. # 1 楼答案

    该代码有几个重要问题,包括

    • 使用空布局。虽然空布局和setBounds()可能会像创建复杂GUI的最简单和最好的方式一样吸引新手,但您创建的Swing GUI越多,在使用它们时会遇到越严重的困难。当GUI调整大小时,它们不会调整您的组件的大小,它们是一个需要增强或维护的皇家女巫,它们在滚动窗格中完全失败,在所有平台或屏幕分辨率与原始分辨率不同的情况下查看时,它们看起来非常糟糕。相信我,这会让你的调试工作变得更加困难。因此,学习和使用布局管理器要好得多。你可以在这里找到布局管理器教程:Layout Manager Tutorial,你可以在这里找到Swing教程和其他Swing资源的链接:Swing Info
    • 您正在设置JTextAreas的大小/边界。这会阻止它们在添加文本时进行适当扩展,并会阻止周围JScrollBars中的滚动条出现。改为设置JTextArea列和行属性
    • 向文本组件添加KeyListener。虽然这不会导致您当前的错误,但这是应该避免的,并且经常会干扰组件的功能。最好使用更高级别的侦听器,如DocumentListener或DocumentFilter

    例如,下面的代码显示了如何使用简单的布局、文本区域列和行属性,以及使用键绑定来捕获用户按enter键的情况,如果需要的话:

    import java.awt.BorderLayout;
    import java.awt.Font;
    import java.awt.GridLayout;
    import java.awt.event.ActionEvent;
    import java.awt.event.KeyEvent;
    
    import javax.swing.*;
    
    @SuppressWarnings("serial")
    public class LayoutExample extends JPanel {
        private static final int MV_ROWS = 65;
        private static final int MV_COLS = 100;
        private static final int TA_ROWS = 34;
        private static final int TA_COLS = 54;
        private static final int ITA_ROWS = 8;
        private static final Font MV_FONT = new Font("Consolas", 0, 8);
        private static final Font TA_FONT = new Font("Consolas", 0, 12);
    
        private JTextArea mapView = new JTextArea(MV_ROWS, MV_COLS);
        private JTextArea textArea = new JTextArea("Static Text\n", TA_ROWS, TA_COLS);
        private JTextArea inputTextArea = new JTextArea(ITA_ROWS, TA_COLS);
    
        public LayoutExample() {
            mapView.setFont(MV_FONT);
            mapView.setEditable(false);
            mapView.setFocusable(false);
            JScrollPane mvScrollPane = new JScrollPane(mapView);
    
            textArea.setFont(TA_FONT);
            textArea.setLineWrap(true);
            textArea.setWrapStyleWord(true);
            textArea.setEditable(false);
            textArea.setFocusable(false);
            JScrollPane taScrollPane = new JScrollPane(textArea);
            taScrollPane.setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS);
    
            setEnterKeyBindings(inputTextArea);
            inputTextArea.setFont(TA_FONT);
            inputTextArea.setLineWrap(true);
            inputTextArea.setWrapStyleWord(true);
            JScrollPane itaScrollPane = new JScrollPane(inputTextArea);
            itaScrollPane.setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS);
    
            JPanel rightPanel = new JPanel(new BorderLayout());
            rightPanel.add(taScrollPane, BorderLayout.CENTER);
            rightPanel.add(itaScrollPane, BorderLayout.PAGE_END);
    
            setLayout(new GridLayout(1, 0));
            add(mvScrollPane);
            add(rightPanel);
    
            inputTextArea.setText(">");
        }
    
        // to capture the "enter" key being pressed without having to use a
        // KeyListener
        private void setEnterKeyBindings(final JTextArea textComponent) {
            // only accept input when this component is focused
            int condition = WHEN_FOCUSED; 
            InputMap inputMap = textComponent.getInputMap(condition);
            ActionMap actionMap = textComponent.getActionMap();
    
            // only will bind one keystroke   that for enter key
            KeyStroke enterKeyStroke = KeyStroke.getKeyStroke(KeyEvent.VK_ENTER, 0);
            inputMap.put(enterKeyStroke, enterKeyStroke.toString());
    
            // action to take if enter is pressed
            actionMap.put(enterKeyStroke.toString(), new AbstractAction() {
    
                @Override
                public void actionPerformed(ActionEvent e) {
                    // get text from input text area, and then clear text
                    String text = textComponent.getText();
                    textComponent.setText(">");
    
                    // append this text to the upper text area
                    textArea.append(text + "\n");
    
                    // TODO: send text elsewhere via chat?
                }
            });
        }
    
        private static void createAndShowGui() {
            LayoutExample mainPanel = new LayoutExample();
    
            JFrame frame = new JFrame("Title");
            frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            frame.getContentPane().add(mainPanel);
            frame.pack();
            frame.setLocationRelativeTo(null);
            frame.setVisible(true);
        }
    
        public static void main(String[] args) {
            SwingUtilities.invokeLater(() -> createAndShowGui());
        }
    }