Java의 Jcombobox에 분리기를 추가하려면 어떻게합니까?
-
02-07-2019 - |
문제
나는있다 Jcombobox 그리고 요소 목록에 분리기를 갖고 싶습니다. Java에서 어떻게해야합니까?
이것이 유용한 샘플 시나리오는 글꼴 주식 선택을위한 콤보 박스를 만들 때입니다. Word and Excel의 글꼴 가족 선택 통제와 유사합니다. 이 경우 상단에 가장 많이 사용되는 고기, 분리기와 마지막으로 모든 글꼴을 분리기 아래에 알파벳 순서로 표시하고 싶습니다.
누구 든지이 작업을 수행하는 방법을 도와 줄 수 있습니까? 아니면 Java에서는 불가능합니까?
해결책
Java2S에서 사용자 정의 ListCellrenderer를 사용하는 방법을 보여주는 예제가 포함 된 꽤 짧은 자습서가 있습니다. http://www.java2s.com/code/java/swing-components/blockcomboboxexample.htm
기본적으로 목록 모델에 알려진 자리 표시자를 삽입하는 것이 포함되며 ListCellrenderer에서 자리 표시자를 감지 할 때 '새 JSEPARATOR (jseparator.horizontal) 인스턴스를 반환합니다.
다른 팁
내가 아래 코드를 작성하고 테스트 할 때까지, 당신은 아마 더 나은 답을 얻었을 것입니다 ...
나는 실험/학습을 즐겼을 때 신경 쓰지 않습니다 (여전히 스윙 프론트에서 약간 녹색).
편집] 3 년 후, 나는 조금 덜 녹색이며 Bobndrew의 유효한 발언을 고려했습니다. 단지 작동하는 주요 탐색에 아무런 문제가 없습니다 (아마도 JVM 버전 문제일까요?). 그래도 렌더러를 개선하여 하이라이트를 표시했습니다. 그리고 더 나은 데모 코드를 사용합니다. 허용 된 대답은 아마도 더 좋을 것입니다 (더 많은 표준). 사용자 정의 분리기를 원한다면 내 것이 더 유연 할 것입니다 ...
기본 아이디어는 콤보 상자의 항목에 렌더러를 사용하는 것입니다. 대부분의 항목의 경우 항목 텍스트가있는 간단한 jlabel입니다. 최근/가장 많이 사용 된 아이템의 경우, jlabel을 바닥에 선을 그리는 맞춤형 테두리로 장식합니다.
import java.awt.*;
import javax.swing.*;
@SuppressWarnings("serial")
public class TwoPartsComboBox extends JComboBox
{
private int m_lastFirstPartIndex;
public TwoPartsComboBox(String[] itemsFirstPart, String[] itemsSecondPart)
{
super(itemsFirstPart);
m_lastFirstPartIndex = itemsFirstPart.length - 1;
for (int i = 0; i < itemsSecondPart.length; i++)
{
insertItemAt(itemsSecondPart[i], i);
}
setRenderer(new JLRenderer());
}
protected class JLRenderer extends JLabel implements ListCellRenderer
{
private JLabel m_lastFirstPart;
public JLRenderer()
{
m_lastFirstPart = new JLabel();
m_lastFirstPart.setBorder(new BottomLineBorder());
// m_lastFirstPart.setBorder(new BottomLineBorder(10, Color.BLUE));
}
@Override
public Component getListCellRendererComponent(
JList list,
Object value,
int index,
boolean isSelected,
boolean cellHasFocus)
{
if (value == null)
{
value = "Select an option";
}
JLabel label = this;
if (index == m_lastFirstPartIndex)
{
label = m_lastFirstPart;
}
label.setText(value.toString());
label.setBackground(isSelected ? list.getSelectionBackground() : list.getBackground());
label.setForeground(isSelected ? list.getSelectionForeground() : list.getForeground());
label.setOpaque(true);
return label;
}
}
}
분리기 클래스는 사용자 정의 색상 등으로 두껍게 될 수 있습니다.
import java.awt.*;
import javax.swing.border.AbstractBorder;
/**
* Draws a line at the bottom only.
* Useful for making a separator in combo box, for example.
*/
@SuppressWarnings("serial")
class BottomLineBorder extends AbstractBorder
{
private int m_thickness;
private Color m_color;
BottomLineBorder()
{
this(1, Color.BLACK);
}
BottomLineBorder(Color color)
{
this(1, color);
}
BottomLineBorder(int thickness, Color color)
{
m_thickness = thickness;
m_color = color;
}
@Override
public void paintBorder(Component c, Graphics g,
int x, int y, int width, int height)
{
Graphics copy = g.create();
if (copy != null)
{
try
{
copy.translate(x, y);
copy.setColor(m_color);
copy.fillRect(0, height - m_thickness, width - 1, height - 1);
}
finally
{
copy.dispose();
}
}
}
@Override
public boolean isBorderOpaque()
{
return true;
}
@Override
public Insets getBorderInsets(Component c)
{
return new Insets(0, 0, m_thickness, 0);
}
@Override
public Insets getBorderInsets(Component c, Insets i)
{
i.left = i.top = i.right = 0;
i.bottom = m_thickness;
return i;
}
}
테스트 클래스 :
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
@SuppressWarnings("serial")
public class TwoPartsComboBoxDemo extends JFrame
{
private TwoPartsComboBox m_combo;
public TwoPartsComboBoxDemo()
{
Container cont = getContentPane();
cont.setLayout(new FlowLayout());
cont.add(new JLabel("Data: ")) ;
String[] itemsRecent = new String[] { "ichi", "ni", "san" };
String[] itemsOther = new String[] { "one", "two", "three" };
m_combo = new TwoPartsComboBox(itemsRecent, itemsOther);
m_combo.setSelectedIndex(-1);
cont.add(m_combo);
m_combo.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent ae)
{
String si = (String) m_combo.getSelectedItem();
System.out.println(si == null ? "No item selected" : si.toString());
}
});
// Reference, to check we have similar behavior to standard combo
JComboBox combo = new JComboBox(itemsRecent);
cont.add(combo);
}
/**
* Start the demo.
*
* @param args the command line arguments
*/
public static void main(String[] args)
{
// turn bold fonts off in metal
UIManager.put("swing.boldMetal", Boolean.FALSE);
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
JFrame demoFrame = new TwoPartsComboBoxDemo();
demoFrame.setTitle("Test GUI");
demoFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
demoFrame.setSize(400, 100);
demoFrame.setVisible(true);
}
});
}
}