1

第一个问题...

我已经阅读了http://www.orbital-computer.de/JComboBox/上的教程,并在此基础上进行了修改以创建一个您传递现有 JComboBox 的类以使其可搜索。

我已经设法让 JComboBox 修改了结果,但是我打破的插入符号似乎发生了一些事情。

具体来说,我希望将任何 JComboBox 传递给此类,以自动选择列表中为我的 .indexOf 语句返回 true 的任何现有项目。

代码:

public class SearchableJComboBox extends PlainDocument {
    JComboBox comboBox;
    ComboBoxModel model;
    JTextComponent editor;
    // flag to indicate if setSelectedItem has been called
    // subsequent calls to remove/insertString should be ignored
    boolean selecting=false;
    boolean hidePopupOnFocusLoss;
    boolean hitBackspace=false;
    boolean hitBackspaceOnSelection;

    public SearchableJComboBox(final JComboBox comboBox) {
        this.comboBox = comboBox;
        model = comboBox.getModel();
        editor = (JTextComponent) comboBox.getEditor().getEditorComponent();
        editor.setDocument(this);
        comboBox.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {

            }
        });
        editor.addKeyListener(new KeyAdapter() {
            public void keyPressed(KeyEvent e) {
                if (comboBox.isDisplayable()) comboBox.setPopupVisible(true);
                hitBackspace=false;              
            }
        });
        // Bug 5100422 on Java 1.5: Editable JComboBox won't hide popup when tabbing out
        hidePopupOnFocusLoss=System.getProperty("java.version").startsWith("1.5");
        // Highlight whole text when gaining focus
        editor.addFocusListener(new FocusAdapter() {

            public void focusLost(FocusEvent e) {
                // Workaround for Bug 5100422 - Hide Popup on focus loss
                if (hidePopupOnFocusLoss) comboBox.setPopupVisible(false);
            }
        });

        // Handle initially selected object
        Object selected = comboBox.getSelectedItem();
        if (selected!=null) setText(selected.toString());

    }


    void setPrototypeValue(Object value, JList list) {
        comboBox.setPrototypeDisplayValue(value);
        list.setPrototypeCellValue(value);
    }



    JList getListBox() {
        JList listBox;
        try {
            Field field = JComponent.class.getDeclaredField("ui");
            field.setAccessible(true);
            BasicComboBoxUI ui = (BasicComboBoxUI) field.get(comboBox);
            field = BasicComboBoxUI.class.getDeclaredField("listBox");
            field.setAccessible(true);
            listBox = (JList) field.get(ui);
        } catch (NoSuchFieldException nsfe) {
            throw new RuntimeException(nsfe);
        } catch (IllegalAccessException iae) {
            throw new RuntimeException(iae);
        }
        return listBox;
    }

    public void remove(int offs, int len) throws BadLocationException {
        // return immediately when selecting an item
        if (selecting) return;
        if (hitBackspace) {
            // user hit backspace => move the selection backwards
            // old item keeps being selected
            if (offs>0) {
                if (hitBackspaceOnSelection) offs--;
            } else {
                // User hit backspace with the cursor positioned on the start => beep
                comboBox.getToolkit().beep(); // when available use: UIManager.getLookAndFeel().provideErrorFeedback(comboBox);
            }

        } else {
            super.remove(offs, len);
        }
    }


    private void setText(String text) {
        try {
            super.remove(0, getLength());
            super.insertString(0, text, null);
        } catch (BadLocationException e) {
            throw new RuntimeException(e.toString());
        }
    }


    public void insertString(int offs, String str, AttributeSet a) throws BadLocationException {
        // return immediately when selecting an item
        if (selecting) return;
        // insert the string into the document
        super.insertString(offs, str, a);
        // lookup and select a matching item
        Object item = lookupItem(getText(0, getLength()));
        if (item != null) 
        setSelectedItem(item);
    }

    private void setSelectedItem(Object item) {
        selecting = true;
        model.setSelectedItem(item);
        selecting = false;
    }

    private Object findStringWithin(String pattern) {

        for(int i=0; i<model.getSize();i++)
        {
            if(model.getElementAt(i).toString().toLowerCase().indexOf(pattern.toLowerCase())!=-1)
            return  model.getElementAt(i);  
        }

        return null;
    }



    private Object lookupItem(String pattern) {
       return this.findStringWithin(pattern);
    }


}
4

1 回答 1

1

我检查了您的代码和您引用的网站。

不,您在哪里包含“光标”部分的行:

editor.setCaretPosition(getLength());

这会导致您的插入符号在开头卡住,并且基本上在您键入时会覆盖以前的字符。

试试看 ...

于 2013-05-27T11:14:21.873 回答