JList with custom renderer
I have a JList that shows multiple JPanels on them , i have created a custom renderer that returns a new JPanel. The JPanels are displayed开发者_JS百科 in the JList but they are not accessible, i cant select them and if i have a button or a text area in it i can not press it. I want to try if this works in a JList because i want to do further pagination. I managed to get it work by adding panels to a Jscroll pane, but would love to make the JList thing work.
Thanks
This is the normal behavior of the JList
(and JTabel
, JComboBox
, etc...).
The JPanel
that your custom renderer returns is not added to the Swing hierarchy. Only its paint
method is used by the JList
, to draw the renderer at the right place. The renderer just acts as a stamp, and what you see in the JList
are not components, but images of components.
This is an efficient way of displaying many components on the screen, without having the overhead of real instantiated components. Note that your renderer can return always the same instance (it's even preferable).
See the Swing tutorial for more details.
If you want the entries of the JList
to act like real components, you can do the following. First, use a JTable
instead of a JList
. A JTable
with one column and no header is roughly the same as a JList
. Why use a JTable
? Because JTable
provides Editors. Editors are registered on the JTable
, just like Renderers are. An Editor appears generally when a user clicks on a JTable's cell. The Editor is superimposed over the renderer, and this time it's a real component. If the Renderer and the Editor components are identical, then the user has the feeling that the JTable's cells are real components.
The Swing tutorial has examples for this technique.
i cant select them and if i have a button or a text area in it i can not press it
A renderer is just a painting of a component. It is not a real component so no you can't click a button or enter text into a text area.
You need to use real components for this. So it is probably better to create a custom panel with you components and then add the panel to another panel that has been added to a scroll pane.
Here's my solution:
public class AccountRenderer extends DefaultListCellRenderer {
private static final long serialVersionUID = 1L;
@Override
public Component getListCellRendererComponent(JList list, Object value,
int index, boolean isSelected, boolean cellHasFocus) {
JLabel renderer = (JLabel) super.getListCellRendererComponent(list, value, index, isSelected, cellHasFocus);
if (value != null) {
Account entry = (Account) value;
renderer.setText(entry.getName());
}
return renderer;
}
}
精彩评论