All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.nuiton.jaxx.widgets.extra.JComboBoxAutoCompletionKit Maven / Gradle / Ivy

Go to download

Widgets graphiques utiles pour tous les développements (pour le moment sans lien avec JAXX).

There is a newer version: 3.0-alpha-17
Show newest version
/*
 * #%L
 * JAXX :: Extra Widgets
 * %%
 * Copyright (C) 2004 - 2017 CodeLutin
 * %%
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Lesser General Public License as 
 * published by the Free Software Foundation, either version 3 of the 
 * License, or (at your option) any later version.
 * 
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Lesser Public License for more details.
 * 
 * You should have received a copy of the GNU General Lesser Public 
 * License along with this program.  If not, see
 * .
 * #L%
 */

/* *
 * JComboBoxAutoCompletionKit.java
 *
 * Created: Nov 12, 2004
 *
 * @author Cédric Pineau 
 * @version $Revision$
 *
 * Last update : $Date$
 * by : $Author$
 */

package org.nuiton.jaxx.widgets.extra;

import javax.swing.ComboBoxModel;
import javax.swing.DefaultListCellRenderer;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JList;
import javax.swing.ListCellRenderer;
import javax.swing.event.ListDataEvent;
import javax.swing.event.ListDataListener;
import java.awt.Component;

/**
 *
 */
public class JComboBoxAutoCompletionKit {

    public static void main(String[] args) {
        JFrame frame = new JFrame();
        String[] petStrings = {"Bird", "Cat", "Cot", "Dog", "Dog", "Dog1",
                "Dog2", "Dog3", "Dog4", "Dog5", "Dog6", "Dog7", "Dog", "Dog8",
                "Dog9", "Dog10", "Rabbit", "Pig"};
        JComboBox combo = new JComboBox(petStrings);
        combo.setRenderer(new TestCellRenderer());
        JComboBoxAutoCompletionKit.setAutoCompleted(combo);
        frame.getContentPane().add(combo);
        frame.setSize(800, 50);
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.setVisible(true);
    }

    public static void setAutoCompleted(JComboBox comboBox) {
        AutoCompletionManager autoCompletionManager = new AutoCompletionManager(
                comboBox);
        AutoCompletionModelListener autoCompletionModelListener = new AutoCompletionModelListener(
                autoCompletionManager);
        AutoCompletionCellRenderer autoCompletionCellRenderer = new AutoCompletionCellRenderer(
                autoCompletionManager, comboBox.getRenderer());
        comboBox.setKeySelectionManager(autoCompletionManager);
        comboBox.getModel().addListDataListener(autoCompletionModelListener);
        comboBox.setRenderer(autoCompletionCellRenderer);
    }

    private static class AutoCompletionManager implements
            JComboBox.KeySelectionManager {

        private static final String EMPTY_PREFIX = "";

        private static final int NO_SELECTION = -1;

        private JComboBox _comboBox = null;

        private int _currentSelection = NO_SELECTION;

        private String _prefix = EMPTY_PREFIX;

        public AutoCompletionManager(JComboBox comboBox) {
            setComboBox(comboBox);
        }

        @Override
        public int selectionForKey(char key, ComboBoxModel model) {
            // TODO change allowed chars to include *, -, ...
            System.out.println("" + Integer.toString(key)); // TODO remove this
            if (((key == 8) && (getPrefix().length() > 0))
                    || (Character.isLetterOrDigit(key))) {

                // Build the new prefix and set it
                String prefix = getPrefix();
                if ((key == 8) && (prefix.length() > 0)) {
                    prefix = prefix.substring(0, prefix.length() - 1);
                } else {
                    prefix = getPrefix() + key;
                }
                setPrefix(prefix);

                // Look for the first model item with given prefix
                boolean prefixedItemFound = false;
                for (int i = 0; i < model.getSize(); i++) {
                    Object element = model.getElementAt(i);
                    if (element.toString().startsWith(prefix)) {
                        // Found it, this is the newly selected item
                        setCurrentSelection(i);
                        prefixedItemFound = true;
                        break;
                    }
                }

                // Reset AutoCompletion if prefix can't be found
                if (!prefixedItemFound) {
                    reset();
                }
                // Ensure popup is shown
                getComboBox().showPopup();
                // Force a repaint
                model.setSelectedItem(null);
            }

            return getCurrentSelection();
        }

        public void reset() {
            setPrefix(EMPTY_PREFIX);
            setCurrentSelection(NO_SELECTION);
        }

        /**
         * Called by the model listener when model has changed.
         */
        public void modelChanged() {
            // reset();
        }

        protected JComboBox getComboBox() {
            return _comboBox;
        }

        protected void setComboBox(JComboBox comboBox) {
            _comboBox = comboBox;
        }

        protected int getCurrentSelection() {
            return _currentSelection;
        }

        protected void setCurrentSelection(int currentSelection) {
            _currentSelection = currentSelection;
        }

        protected String getPrefix() {
            return _prefix;
        }

        protected void setPrefix(String prefix) {
            this._prefix = prefix;
        }
    }

    private static class TestCellRenderer extends DefaultListCellRenderer {

        private static final long serialVersionUID = 1L;

        @Override
        public Component getListCellRendererComponent(JList list, Object value,
                                                      int index, boolean isSelected, boolean cellHasFocus) {
            // Ask to default renderer to do the job for us
            Component component = super.getListCellRendererComponent(list,
                                                                     value, index, isSelected, cellHasFocus);

            if (value != null) {
                // Can we trick the rendered thing to reflect current prefix ?
                if (component instanceof JLabel) {
                    // Everything's fine. Let's have a closer look.
                    JLabel label = (JLabel) component;
                    String text = label.getText();
                    text = "J" + text;
                    label.setText(text);
                }
            }

            return component;
        }

    }

    private static class AutoCompletionCellRenderer extends
            DefaultListCellRenderer {

        private static final long serialVersionUID = 1L;

        private ListCellRenderer _existingRenderer = null;
        private AutoCompletionManager _manager = null;

        public AutoCompletionCellRenderer(AutoCompletionManager manager,
                                          ListCellRenderer existingRenderer) {
            setManager(manager);
            setExistingRenderer(existingRenderer);
        }

        @Override
        public Component getListCellRendererComponent(JList list, Object value,
                                                      int index, boolean isSelected, boolean cellHasFocus) {
            // Ask to default renderer to do the job for us
            Component component = getExistingRenderer()
                    .getListCellRendererComponent(list, value, index,
                                                  isSelected, cellHasFocus);

            if (value != null) {
                // Can we trick the rendered thing to reflect current prefix ?
                String prefix = getManager().getPrefix();
                if ((prefix != null) && (component instanceof JLabel)) {
                    // Everything's fine. Let's have a closer look.
                    JLabel label = (JLabel) component;
                    if (value.toString().startsWith(prefix)) {
                        // We're going trick the label a little bit
                        String text = label.getText();
                        text = "" + prefix
                                + "" + text.substring(prefix.length())
                                + "";
                        label.setText(text);
                    }
                }
            }

            return component;
        }

        protected AutoCompletionManager getManager() {
            return this._manager;
        }

        protected void setManager(AutoCompletionManager manager) {
            this._manager = manager;
        }

        /**
         * @return Returns the _existingRenderer.
         */
        protected ListCellRenderer getExistingRenderer() {
            return this._existingRenderer;
        }

        /**
         * @param renderer The _existingRenderer to set.
         */
        protected void setExistingRenderer(ListCellRenderer existingRenderer) {
            this._existingRenderer = existingRenderer;
        }
    }

    private static class AutoCompletionModelListener implements
            ListDataListener {

        private AutoCompletionManager _manager = null;

        public AutoCompletionModelListener(AutoCompletionManager manager) {
            setManager(manager);
        }

        @Override
        public void intervalAdded(ListDataEvent e) {
            // To be optimized...
            getManager().modelChanged();
        }

        @Override
        public void intervalRemoved(ListDataEvent e) {
            // To be optimized...
            getManager().modelChanged();
        }

        @Override
        public void contentsChanged(ListDataEvent e) {
            // To be optimized...
            getManager().modelChanged();
        }

        protected AutoCompletionManager getManager() {
            return _manager;
        }

        protected void setManager(AutoCompletionManager manager) {
            this._manager = manager;
        }
    }

}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy