Java通过制表符通过自定义JCheckBoxList进行导航

时间:2018-09-20 14:32:31

标签: java swing focus jlist jcheckbox

我用JList作为项目构建了一个自定义JCheckBox。一切都很好,但是现在我希望只能使用键盘输入来选择CheckBox。另外,我也不想为每个CheckBox项目使用助记符。

是否可以实现某种FocusListener或其他方式,以便我可以使用制表键进行导航?

我尝试设置setFocusPainted(true)等,但是对我没有任何帮助。

感谢您的时间和帮助。

我的代码:

public class JCheckBoxList extends JList<Object>{

private DefaultListModel<Object> model = null;
private JCheckBoxList selfPointer = null;
private boolean enabled = true;

@SuppressWarnings("unchecked")
/**
 * Constructor.
 */
public JCheckBoxList() {
    super();
    model = new DefaultListModel<Object>();
    selfPointer = this;
    this.setModel(model);
    this.setCellRenderer(new CheckBoxListCellRenderer());
    this.addMouseListener(new MouseAdapter() {
        @Override
        public void mouseClicked(MouseEvent evt) {
            int clicked_index = selfPointer.locationToIndex(evt.getPoint());
            if (evt.getModifiers() == MouseEvent.BUTTON3_MASK) {
                //right clicked
            }else {
                //left clicked
                if (enabled) {
                    setSelected(clicked_index, !isSelected(clicked_index));
                    selfPointer.repaint(selfPointer.getCellBounds(clicked_index, clicked_index));
                }
            }
        }
    });
    this.setVisibleRowCount(50);
    this.setSelectionMode(ListSelectionModel.MULTIPLE_INTERVAL_SELECTION);
}

/**
 * Add new CheckBoxListItem to the JCheckBoxList.
 * @param name Name of new Item.
 */
public void addElement(String name) {
    model.addElement(new CheckBoxListItem(name));
}

/**
 * Add new CheckBoxListItem to the JCheckBoxList.
 * @param name Name of new Item.
 * @param isSelected Boolean if new Item should be selected or not after creating.
 */
public void addElement(String name, boolean isSelected) {
    CheckBoxListItem item = new CheckBoxListItem(name);
    item.setSelected(isSelected);
    model.addElement(item);
}

/**
 * Get all selected Values from JCheckBoxList.
 * @return ArrayList of type String with all selected values.
 */
public List<String> getSelectedValueList() {
    List<String> returnList = new ArrayList<String>();
    for(int i = 0; i < model.getSize(); i++) {
        if (((CheckBoxListItem)model.getElementAt(i)).isSelected == true) {
            returnList.add(model.getElementAt(i).toString());
        }
    }
    if (returnList.isEmpty()){
        return null;
    }
    return returnList;
}

/**
 * Replaces Element at an specific index. Removes the old and creates a new one.
 * @param index Integer index to identify object to replace.
 * @param name Name of new item.
 */
public void replaceElementAt(int index, String name) {
    model.removeElementAt(index);
    model.insertElementAt(new CheckBoxListItem(name), index);;
}

/**
 * Removes all Elements from JCheckBoxList.
 */
public void removeAll() {
    model.removeAllElements();
}

/**
 * Custom getElementAt method. Same functionality as List method.
 * @param index Integer index of Element to get.
 * @return Return String name of Element.
 */
public String getElementAt(int index) {
    return model.getElementAt(index).toString();
}

/**
 * Check if an Element is Selected.
 * @param index Integer Index to identify Element.
 * @return Returns whether Element is selected or not.
 */
public boolean isSelected(int index) {
     return ((CheckBoxListItem)model.getElementAt(index)).isSelected;
}

/**
 * Set the selected state of Element.
 * @param index Integer Index of identify Element.
 * @param isSelected Boolean value to set.
 */
public void setSelected(int index, boolean isSelected) {
    ((CheckBoxListItem)model.getElementAt(index)).setSelected(isSelected);
}   

@Override
/*
 * (non-Javadoc)
 * @see javax.swing.JComponent#setEnabled(boolean)
 */
public void setEnabled(boolean arg0) {
    enabled = arg0;
}

@Override
/*
 * (non-Javadoc)
 * @see java.awt.Component#isEnabled()
 */
public boolean isEnabled() {
    return enabled;
}

/**
 * Get all Values from JCheckBoxList as ArrayList.
 * @return Returns ArrayList of type String with content of JCheckBoxList.
 */
public List<String> getValues() {
    List<String> returnList = new ArrayList<String>();
    for (int i = 0; i < model.getSize(); i++) {
        returnList.add(model.getElementAt(i).toString());
    }
    return returnList;
}

private class CheckBoxListItem {
    private String label;
    private boolean isSelected = false;

    private CheckBoxListItem(String label) {
        this.label = label;
    }

    private boolean isSelected() {
        return isSelected;
    }

    private void setSelected(boolean isSelected) {
        this.isSelected = isSelected;
    }

    @Override
    /*
     * (non-Javadoc)
     * @see java.lang.Object#toString()
     */
    public String toString() {
        return label;
    }
}

@SuppressWarnings("rawtypes")
private class CheckBoxListCellRenderer extends JCheckBox implements ListCellRenderer {

    public Component getListCellRendererComponent(JList list, Object value, int index, 
            boolean isSelected, boolean cellHasFocus) {

        setComponentOrientation(list.getComponentOrientation());
        setFont(list.getFont());
        setBackground(list.getBackground());
        setForeground(list.getForeground());
        setSelected(((CheckBoxListItem) value).isSelected());
        setEnabled(enabled);
        setText(value == null ? "" : value.toString());  

        return this;
    }
}

}

2 个答案:

答案 0 :(得分:2)

  

我已经使用JCheckBox作为项目构建了自定义JList。

使用单列JTable。

JTable已经支持复选框,您可以使用键盘或鼠标来更改复选框的状态。它还支持在单元格之间切换。

请阅读How to Use Tables的Swing教程中的部分,以获取入门的基本示例。

如果您不想要表头,则可以将表头设置为null。

否则,只需将JPanel与复选框一起使用即可。 JList仅设计用于显示数据,而不会对事件或更改正在渲染的对象的状态做出反应。

答案 1 :(得分:0)

使用方法

setFocusTraversalKeysEnabled(boolean);

在组件上允许(禁止)遍历键(例如TAB)作为键输入