2

这是我的代码:-

public class MyRender extends JPanel implements ListCellRenderer {

    ImageIcon on_img;
    JLabel name = new JLabel();
    JLabel icn = new JLabel();
    JLabel img = new JLabel();

    public MyRender(Atalk) {
        setOpaque(true);
        setBackground(Color.WHITE);
        setForeground(Color.black);
        on_img = new ImageIcon(MyCls.class.getClassLoader().getResource("imgPath"));
    }

    @Override
    public Component getListCellRendererComponent(JList list, Object value,
            int index, boolean isSelected, boolean cellHasFocus) {
        if (value != null) {
            removeAll();
            setLayout(new BorderLayout());
            User user = (User) value;
            String pres = user.getPresence().toLowerCase();
            img.setIcon(default_img);
            if (pres.contains("unavailable"))
                icn.setIcon(off_img);
            else
                icn.setIcon(on_img);
            name.setText(user.getName());
            JPanel panel = new JPanel();
            panel.setLayout(new BorderLayout());

            add(img, BorderLayout.EAST);
            add(icn, BorderLayout.WEST);

            panel.add(st, BorderLayout.CENTER);
            panel.add(name, BorderLayout.NORTH);

            add(panel, BorderLayout.CENTER);

            JLabel lbl = new JLabel(" ");
            lbl.setSize(100, 5);
            add(lbl, BorderLayout.AFTER_LAST_LINE);

            if (isSelected) {
                setBackground(Color.lightGray);
                panel.setBackground(Color.lightGray);
            } else {
                setBackground(Color.white);
                panel.setBackground(Color.white);
            }

            return this;
        }
        return null;
    }
}

如您所见,我调用了removeAll()方法。如果我删除该行,数据将无法正确显示。所有数据相互重叠。如果我添加removeAll()所有工作正常。为什么会发生这种情况?有必要打电话removeAll()吗?

4

3 回答 3

4

您必须重组您的类,以便MyRender在构建时创建和添加的所有子级。

getListCellRendererComponent()只能用于更改现有组件的值或视觉属性(例如背景)。

不要忘记它getListCellRendererComponent()应该尽可能快(它可以被非常频繁地调用),因此它不应该创建组件而只修改现有的组件。

通常,您的getListCellRendererComponent()方法应如下所示:

@Override
public Component getListCellRendererComponent(
    JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) {
    if (value != null) {
        User user = (User) value;
        String pres = user.getPresence().toLowerCase();
        img.setIcon(default_img);
        if (pres.contains("unavailable"))
            icn.setIcon(off_img);
        else
            icn.setIcon(on_img);
        name.setText(user.getName());
        if (isSelected) {
            setBackground(Color.lightGray);
            panel.setBackground(Color.lightGray);
        } else {
            setBackground(Color.white);
            panel.setBackground(Color.white);
        }
    }
    return this;
}
于 2011-05-18T11:45:34.073 回答
1

不,您不必调用 removeAll()。我认为您的问题是每次在此处调用该方法时,您都在 getListCellRendererComponent 方法中创建了一个新的 JPanel:

JPanel panel = new JPanel();
panel.setLayout(new BorderLayout());

如果将此 JPanel 设为类字段,则可能不必调用 removeAll。

编辑:jfpoilpret 回答得更好。1+给他。

于 2011-05-18T13:08:13.817 回答
0

也可以revalidate()在面板上使用

于 2011-05-18T10:19:40.320 回答