0

我做了一个RefreshablePanel扩展的类JPanel

public class RefreshablePanel extends JPanel {

static String description="";
static int x=10;
static int y=11;
    
protected void paintComponent(Graphics g){
       super.paintComponent(g);
    for (String line : description.split("\n"))
        g.drawString(line, x, y += g.getFontMetrics().getHeight());
}
void updateDescription(String dataToAppend){
        description = description.concat("\n").concat(dataToAppend);
        System.out.println("The description is "+description);
   }   
}

然后我像这样将它添加到我的GUI_class

JScrollPane scrollPane_2 = new JScrollPane();
scrollPane_2.setBounds(32, 603, 889, 90);
frmToolToMigrate.getContentPane().add(scrollPane_2);

descriptionPanel = new RefreshablePanel();
scrollPane_2.setViewportView(descriptionPanel);
descriptionPanel.setBackground(Color.WHITE);
descriptionPanel.setLayout(null);
    

我在创建 RefreshablePanel 实例的类中添加了滚动条,但没有出现滚动条。我试过添加

@Override
public Dimension getPreferredSize() {
    return new Dimension(400, 1010);
}

到可刷新的面板,但字符串像这样消失 在此处输入图像描述

当我向下滚动时什么都没有出现

4

1 回答 1

3
  1. 您正在使用null布局,所以没有什么可以按应有的方式工作。Swing 的核心设计是利用布局管理器。

  2. RefreshablePanel没有可辨别的大小,这意味着当您添加到滚动窗格时,滚动窗格可能会简单地认为它的大小应该0x0RefreshablePanel需要向滚动窗格提供某种大小提示,最好通过getPreferredSize方法

  3. 您可以使用JLabel(文本包装在 html 中)或不可编辑JTextArea来实现相同的结果

更新

快速检查您的代码。您将xandy值声明为static并且您正在增加方​​法y中的值paintComponent

static int x=10;
static int y=11;

protected void paintComponent(Graphics g){
   super.paintComponent(g);
    for (String line : description.split("\n"))
        g.drawString(line, x, y += g.getFontMetrics().getHeight());
}

这意味着两件事。

  1. 如果您有多个实例,RefreshablePanel它们都将共享相同的x/y值并更新它们
  2. y不断更新到新位置,因此如果面板被绘制两次,在第二次绘制时,该y位置将从第一次调用退出时的最后位置开始。

请记住,您无法控制绘画过程。绘制周期可以在系统决定它需要的任何时候执行...

x/y值局部变量设置为paintComponent方法...

更新

如果可用空间允许,滚动窗格将尝试匹配组件的首选大小。这可能意味着在您调整窗口大小之前可能不会出现滚动条...但是您使用的null布局对您不起作用...

要影响滚动窗格的大小,您可以改用Scrollable界面...

在此处输入图像描述

import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Rectangle;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.Scrollable;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;

public class Scrollable01 {

    public static void main(String[] args) {
        new Scrollable01();
    }

    public Scrollable01() {
        EventQueue.invokeLater(new Runnable() {
            @Override
            public void run() {
                try {
                    UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                }

                RefreshablePanel pane = new RefreshablePanel();
                pane.updateDescription("1. You're using null layouts, so nothing is going to work the way it should. Swing is designed at the core to utilise layout managers.");
                pane.updateDescription("2. You're RefreshablePanel has no discernible size, meaning that when you add to the scroll pane, the scroll pane is likely to simply think it's size should 0x0. RefreshablePanel needs to provide some kind of size hint back to the scrollpane, preferably via the getPreferredSize method");
                pane.updateDescription("3. You could use a JLabel (with text wrapped in html) or a non-editable JTextArea to achieve the same results");

                JFrame frame = new JFrame("Testing");
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                frame.setLayout(new BorderLayout());
                frame.add(new JScrollPane(pane));
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);
            }
        });
    }

    public class RefreshablePanel extends JPanel implements Scrollable {

        public String description = "";

        @Override
        public Dimension getPreferredSize() {
            return new Dimension(400, 1010);
        }

        @Override
        protected void paintComponent(Graphics g) {
            int x = 10;
            int y = 11;
            super.paintComponent(g);
            for (String line : description.split("\n")) {
                g.drawString(line, x, y += g.getFontMetrics().getHeight());
            }
        }

        void updateDescription(String dataToAppend) {
            description = description.concat("\n").concat(dataToAppend);
            System.out.println("The description is " + description);
            repaint();
        }

        @Override
        public Dimension getPreferredScrollableViewportSize() {
            return new Dimension(400, 400);
        }

        @Override
        public int getScrollableUnitIncrement(Rectangle visibleRect, int orientation, int direction) {
            return 64;
        }

        @Override
        public int getScrollableBlockIncrement(Rectangle visibleRect, int orientation, int direction) {
            return 64;
        }

        @Override
        public boolean getScrollableTracksViewportWidth() {
            return false;
        }

        @Override
        public boolean getScrollableTracksViewportHeight() {
            return false;
        }
    }
}
于 2013-10-03T04:29:53.513 回答