Reputation: 5684
I created a JList
inside a JScrollPane
that uses a custom ListCellRenderer
. The ListCellRenderer
contains a Jlabel
that wraps its contents with HTML so the text automatically wraps. Without using the the JScrollPane
the wrapping works, but when I use the JScrollPane
the text is not wrapped and a horizontal scrollbar appears.
Excerpt of my ListCellRenderer
:
public class WorkableCellRenderer implements ListCellRenderer<Workable> {
@Override
public final Component getListCellRendererComponent(final JList<? extends Workable> list, final Workable value,
final int index, final boolean isSelected, final boolean isFocused) {
JPanel cell = new JPanel();
cell.setLayout(new BoxLayout(cell, BoxLayout.Y_AXIS));
// ...
JPanel pnlDescription = new JPanel();
cell.add(pnlDescription);
pnlDescription.setLayout(new BorderLayout());
JLabel lblDescription =
new JLabel("<html><p style=\"margin: 0; padding: 0;\">" + value.getDescription() + "</p></html>");
lblDescription.setFont(lblDescription.getFont().deriveFont(Font.PLAIN));
pnlDescription.add(lblDescription, BorderLayout.CENTER);
// ...
return cell;
}
}
The method that adds my list to the JFrame
:
private void addLoadedModulesPanel() {
pnlLoadedModulesWrapper = new JPanel();
pnlBottom.add(pnlLoadedModulesWrapper, BorderLayout.CENTER);
pnlLoadedModulesWrapper.setLayout(new MigLayout("insets 0 5 5 5", "[grow]", "[grow]"));
pnlLoadedModulesBox = new JPanel();
pnlLoadedModulesWrapper.add(pnlLoadedModulesBox, "cell 0 0,grow");
pnlLoadedModulesBox.setLayout(new MigLayout("insets 3", "[grow]", "[grow]"));
pnlLoadedModulesBox.setBorder(BorderFactory.createTitledBorder("Geladene Module"));
lstLoadedModules = new JList<Workable>(DefaultWorkableManager.getInstance());
lstLoadedModules.setCellRenderer(new WorkableCellRenderer());
final JScrollPane listScroller = new JScrollPane(lstLoadedModules);
pnlLoadedModulesBox.add(listScroller, "cell 0 0,grow");
}
I think that the problem is the viewport of the JScrollPane
because it is bigger than the JScrollPane
itself. How can I adjust the viewports width so that it has always the same width as the JScrollPane
?
Here is a MCVE which shows my problem:
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Component;
import java.awt.EventQueue;
import javax.swing.DefaultListModel;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JList;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.ListCellRenderer;
import javax.swing.border.EmptyBorder;
public class TestFrame extends JFrame {
private static final long serialVersionUID = -5281126214046039839L;
public static void main(final String[] args) {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
try {
final TestFrame frame = new TestFrame();
frame.setVisible(true);
} catch (final Exception e) {
e.printStackTrace();
}
}
});
}
public TestFrame() {
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setSize(200, 500);
getContentPane().setLayout(new BorderLayout());
final JPanel mainPanel = new JPanel();
mainPanel.setLayout(new BorderLayout());
mainPanel.setBorder(new EmptyBorder(5, 5, 5, 5));
getContentPane().add(mainPanel);
final DefaultListModel<String> lm = new DefaultListModel<>();
final JList<String> list = new JList<>(lm);
list.setCellRenderer(new MyListCellRenderer());
final JScrollPane scrollPane = new JScrollPane(list);
mainPanel.add(scrollPane);
for (int i = 1; i < 21; i++) {
lm.addElement(String.valueOf(i));
}
}
private class MyListCellRenderer implements ListCellRenderer<String> {
private final JPanel panel = new JPanel();
private final JLabel label = new JLabel();
public MyListCellRenderer() {
panel.setLayout(new BorderLayout());
panel.setBackground(new Color(16777215));
panel.add(label);
}
@Override
public Component getListCellRendererComponent(final JList<? extends String> list, final String val,
final int index, final boolean isSelected, final boolean hasFocus) {
label.setText("<html><p>Item number " + val
+ " contains some very long text, that ideally should wrap.</p></html>");
if (isSelected) {
panel.setBackground(new Color(5323));
} else {
panel.setBackground(new Color(16777215));
}
return panel;
}
}
}
Upvotes: 0
Views: 964
Reputation: 324207
think that the problem is the viewport of the JScrollPane because it is bigger than the JScrollPane itself. How can I adjust the viewports width so that it has always the same width as the JScrollPane?
You need to implement the Scrollable
interface on your panel to limit the width of the panel to the width of the scroll pane.
Or you can use the Scrollable Panel which provides a couple of methods that allow you to control this behaviour.
Upvotes: 1
Reputation: 109823
everything depends ..., then JList
in JScrollPane
can returns proper getPreferredSize
(or directly by using JList.setPrototypeCellValue) for used LayoutManager
whats is value for getPreferredSize
returns ListCellRenderer
, is this PreferredSize
the same for all Items or not
how is set for JList.setLayoutOrientation()
is there used limits for visible row or not JList.setVisibleRowCount()
Upvotes: 2