在那里,我实现了JList
,其中包含JLabel
个元素。我的目标是实现服务器/客户端聊天应用程序的联系人列表。因此,当客户端连接到服务器时,JList将构建以显示他/她的联系人列表。我选择使用JLabel,因为他们也可以拥有图标和文本。但是,我在重写cellrenderer方法时遇到了一些麻烦。每当客户端上线/下线时,JList就会更新其状态,并将所有项目设置为与上次添加的项目类似。就像这样,
这是第一次将离线状态客户端添加到某人的好友列表中;
之后,这是第二次添加不同的客户端
最后第三次......
此外,我记得在教程中它提到了JList覆盖痛苦方法并在列表中发生更改时一次又一次地绘制整个元素。实际上我是这个渲染主题的新手,这件事非常烦人。在这里你可以看到我的渲染器类; RendererSample
并在我的主类
中以这种方式将一个元素添加到模型中labelSetText = tempon.getNickName();
onlineStatus = tempon.isIsOnline();
model.addElement(createPanel());
并且createPanel()
也返回一个类似的JLabel;
public static JLabel createPanel() {
JLabel panel = new JLabel();
return panel;
}
我希望我能清楚自己的问题。当联系人改变他/她的状态或添加联系人时,我必须实现这一点,这个动作不应该影响其他元素。我将非常感谢每一个答案(如果你能简单解释一下你做了什么以及为什么我会感激不尽。)非常感谢
答案 0 :(得分:4)
您不应将JLabel
等组件放入JList
。而是使用模型来保存数据并添加渲染器以自定义演示文稿。有关示例,请参阅How to Use Lists。
以下是添加图标的渲染器的一个非常基本的示例:
import java.awt.BorderLayout;
import java.awt.Component;
import javax.swing.*;
public class TestUserList {
public static class UserRenderer extends DefaultListCellRenderer {
@Override
public Component getListCellRendererComponent(JList list, Object value,
int index, boolean isSelected, boolean hasFocus) {
if (value instanceof UserEntry) {
UserEntry user = (UserEntry) value;
JLabel label = (JLabel) super.getListCellRendererComponent(
list, user.getName(), index, isSelected, hasFocus);
if (user.isOnline())
label.setIcon(UIManager
.getIcon("OptionPane.informationIcon"));
else
label.setIcon(UIManager.getIcon("OptionPane.errorIcon"));
return label;
}
return super.getListCellRendererComponent(list, value, index,
isSelected, hasFocus);
}
}
public TestUserList() {
JFrame frame = new JFrame("User List");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
final JList list = new JList();
JScrollPane scrollPane = new JScrollPane(list);
JPanel content = new JPanel(new BorderLayout());
content.add(scrollPane, BorderLayout.CENTER);
final DefaultListModel model = new DefaultListModel();
model.addElement(new UserEntry("John", true));
model.addElement(new UserEntry("Jesse", false));
list.setModel(model);
list.setCellRenderer(new UserRenderer());
frame.add(content);
frame.setLocationByPlatform(true);
frame.pack();
frame.setVisible(true);
}
public class UserEntry {
private String name;
private boolean online;
public UserEntry(String name, boolean online) {
super();
this.name = name;
this.online = online;
}
public String getName() {
return name;
}
public Boolean isOnline() {
return online;
}
}
public static void main(String args[]) {
SwingUtilities.invokeLater(new Runnable() {
@Override
public void run() {
new TestUserList();
}
});
}
}