001: package org.gui4j.core.swing;
002:
003: import java.awt.event.FocusEvent;
004: import java.lang.reflect.Field;
005:
006: import javax.swing.CellEditor;
007: import javax.swing.ComboBoxModel;
008: import javax.swing.JComboBox;
009: import javax.swing.JScrollBar;
010: import javax.swing.JScrollPane;
011: import javax.swing.JWindow;
012: import javax.swing.plaf.ComboBoxUI;
013: import javax.swing.plaf.basic.BasicComboBoxUI;
014: import javax.swing.plaf.basic.BasicComboPopup;
015: import javax.swing.plaf.basic.ComboPopup;
016:
017: import org.apache.commons.logging.Log;
018: import org.apache.commons.logging.LogFactory;
019:
020: import org.gui4j.core.listener.Gui4jActionListenerComboBox;
021:
022: /**
023: * ComboBox which supports vertical and horizontal scrollbars.
024: */
025: public class ComboBoxHorizontalScroll extends JComboBox {
026: private static final Log log = LogFactory
027: .getLog(ComboBoxHorizontalScroll.class);
028:
029: private CellEditor cellEditor;
030: private Gui4jActionListenerComboBox actionListener;
031:
032: /**
033: * @param model
034: */
035: public ComboBoxHorizontalScroll(ComboBoxModel model) {
036: super (model);
037: }
038:
039: public ComboBoxHorizontalScroll() {
040: super ();
041: }
042:
043: public void updateUI() {
044: super .updateUI();
045: enableHorizontalScrollbar(getUI());
046: }
047:
048: public CellEditor getCellEditor() {
049: return cellEditor;
050: }
051:
052: protected void processFocusEvent(FocusEvent e) {
053: super .processFocusEvent(e);
054: if (e.getID() == FocusEvent.FOCUS_LOST && cellEditor != null
055: && !(e.getOppositeComponent() instanceof JWindow)
056: && !(e.getOppositeComponent() instanceof JScrollBar)) {
057: cellEditor.stopCellEditing();
058: }
059: }
060:
061: public void setCellEditor(CellEditor cellEditor) {
062: this .cellEditor = cellEditor;
063: }
064:
065: public void setActionListener(Gui4jActionListenerComboBox listener) {
066: actionListener = listener;
067: addActionListener(actionListener);
068: }
069:
070: public Gui4jActionListenerComboBox getActionListener() {
071: return actionListener;
072: }
073:
074: private void enableHorizontalScrollbar(ComboBoxUI comboUI) {
075: if (comboUI instanceof BasicComboBoxUI) {
076: try {
077: Field popupField = BasicComboBoxUI.class
078: .getDeclaredField("popup");
079: popupField.setAccessible(true);
080: ComboPopup popup = (ComboPopup) popupField.get(comboUI);
081: if (popup instanceof BasicComboPopup) {
082: Field scrollerField = BasicComboPopup.class
083: .getDeclaredField("scroller");
084: scrollerField.setAccessible(true);
085: JScrollPane scroller = (JScrollPane) scrollerField
086: .get(popup);
087: scroller
088: .setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_AS_NEEDED);
089: if (scroller.getHorizontalScrollBar() == null) {
090: // workaround for JDK 1.5 Comboboxes that explicitly set their horizontal scrollbars to null
091: JScrollBar scrollBar = new JScrollBar(
092: JScrollBar.HORIZONTAL);
093: scroller.setHorizontalScrollBar(scrollBar);
094: }
095: scroller.getHorizontalScrollBar().setFocusable(
096: false);
097: }
098: } catch (Exception e) {
099: log
100: .warn(
101: "Could not enable horizontal scrollbar for combobox.",
102: e);
103: }
104: }
105: }
106:
107: }
|