001 /*
002 * $Id: ComboBoxAdaptor.java 3100 2008-10-14 22:33:10Z rah003 $
003 *
004 * Copyright 2004 Sun Microsystems, Inc., 4150 Network Circle,
005 * Santa Clara, California 95054, U.S.A. All rights reserved.
006 *
007 * This library is free software; you can redistribute it and/or
008 * modify it under the terms of the GNU Lesser General Public
009 * License as published by the Free Software Foundation; either
010 * version 2.1 of the License, or (at your option) any later version.
011 *
012 * This library is distributed in the hope that it will be useful,
013 * but WITHOUT ANY WARRANTY; without even the implied warranty of
014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
015 * Lesser General Public License for more details.
016 *
017 * You should have received a copy of the GNU Lesser General Public
018 * License along with this library; if not, write to the Free Software
019 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
020 */
021 package org.jdesktop.swingx.autocomplete;
022
023 import java.awt.Rectangle;
024 import java.awt.event.ActionEvent;
025 import java.awt.event.ActionListener;
026
027 import javax.accessibility.Accessible;
028 import javax.swing.JComboBox;
029 import javax.swing.JList;
030 import javax.swing.plaf.basic.ComboPopup;
031 import javax.swing.text.JTextComponent;
032
033 /**
034 * An implementation of the AbstractAutoCompleteAdaptor that is suitable for JComboBox.
035 *
036 * @author Thomas Bierhance
037 * @author Karl Schaefer
038 */
039 public class ComboBoxAdaptor extends AbstractAutoCompleteAdaptor implements ActionListener {
040
041 /** the combobox being adapted */
042 private JComboBox comboBox;
043
044 /**
045 * Creates a new ComobBoxAdaptor for the given combobox.
046 * @param comboBox the combobox that should be adapted
047 */
048 public ComboBoxAdaptor(JComboBox comboBox) {
049 this.comboBox = comboBox;
050 // mark the entire text when a new item is selected
051 comboBox.addActionListener(this);
052 }
053
054 /**
055 * Implementation side effect - do not invoke.
056 * @param actionEvent -
057 */
058 // ActionListener (listening to comboBox)
059 public void actionPerformed(ActionEvent actionEvent) {
060 markEntireText();
061 }
062
063 public int getItemCount() {
064 return comboBox.getItemCount();
065 }
066
067 public Object getItem(int index) {
068 return comboBox.getItemAt(index);
069 }
070
071 public void setSelectedItem(Object item) {
072 //SwingX 834: avoid moving when already selected
073 if (item == getSelectedItem()) {
074 return;
075 }
076
077 // kgs - back door our way to finding the JList that displays the data.
078 // then we ask the list to scroll until the last cell is visible. this
079 // will cause the selected item to appear closest to the top.
080 //
081 // it is unknown whether this functionality will work outside of Sun's
082 // implementation, but the code is safe and will "fail gracefully" on
083 // other systems
084 Accessible a = comboBox.getUI().getAccessibleChild(comboBox, 0);
085
086 if (getItemCount() > 0 && a instanceof ComboPopup) {
087 JList list = ((ComboPopup) a).getList();
088 int lastIndex = list.getModel().getSize() - 1;
089
090 Rectangle rect = list.getCellBounds(lastIndex, lastIndex);
091
092 if (rect == null) {
093 throw new IllegalStateException(
094 "attempting to access index " + lastIndex + " for " + comboBox);
095 }
096
097 list.scrollRectToVisible(rect);
098 }
099
100 //setting the selected item should scroll it into the visible region
101 comboBox.setSelectedItem(item);
102 }
103
104 public Object getSelectedItem() {
105 return comboBox.getModel().getSelectedItem();
106 }
107
108 public JTextComponent getTextComponent() {
109 // returning the component of the combobox's editor
110 return (JTextComponent) comboBox.getEditor().getEditorComponent();
111 }
112 }