/* This file is part of leafdigital leafChat. leafChat is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. leafChat 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 Public License for more details. You should have received a copy of the GNU General Public License along with leafChat. If not, see <http://www.gnu.org/licenses/>. Copyright 2011 Samuel Marshall. */ package com.leafdigital.ui; import java.awt.*; import java.awt.event.*; import javax.swing.*; import util.PlatformUtils; import com.leafdigital.ui.api.*; import leafchat.core.api.BugException; /** Combo box */ public class DropdownImp extends JComponent implements BaseGroup { private String onSelectionChange; private boolean selecting; private String baseGroup=null; private JComboBox b=new JComboBox(); private int topOffset=0; DropdownImp() { b.setOpaque(false); b.addItemListener(new ItemListener() { @Override public void itemStateChanged(ItemEvent ie) { if(ie.getStateChange()!=ItemEvent.SELECTED && onSelectionChange!=null && !selecting) { getInterface().getOwner().getCallbackHandler().callHandleErrors(onSelectionChange); } } }); add(b); } @Override public void setBounds(int x,int y,int width,int height) { super.setBounds(x,y,width,height); relayout(); } private void relayout() { int preferredHeight=b.getPreferredSize().height; b.setBounds(0,topOffset,getWidth(),preferredHeight); } private static class KeyWrapper { Object key; String value; @Override public String toString() { return value; } public KeyWrapper(Object key,String value) { this.key=key; this.value=value; } } /** @return Combo interface */ public Dropdown getInterface() { return cInterface; } /** Combo interface */ Dropdown cInterface=new ComboInterface(); /** Class implementing combo interface */ class ComboInterface extends BasicWidget implements Dropdown, InternalWidget { @Override public int getContentType() { return CONTENT_NONE; } @Override public void addXMLChild(String sSlotName, Widget wChild) { throw new BugException("Combos cannot contain children"); } @Override public JComponent getJComponent() { return DropdownImp.this; } @Override public int getPreferredWidth() { return b.getPreferredSize().width; } @Override public int getPreferredHeight(int iWidth) { return b.getPreferredSize().height; } public String getValue() { String sValue=(String)b.getSelectedItem(); if(sValue==null) return ""; else return sValue; } @Override public void clear() { UISingleton.runInSwing(new Runnable() { @Override public void run() { try { selecting=true; b.removeAllItems(); } finally { selecting=false; } } }); } @Override public void addValue(Object key,String value) { final KeyWrapper wrapper=new KeyWrapper(key,value); UISingleton.runInSwing(new Runnable() { @Override public void run() { try { selecting=true; b.addItem(wrapper); } finally { selecting=false; } } }); } @Override public Object getSelected() { KeyWrapper kw=(KeyWrapper)b.getSelectedItem(); if(kw==null) return null; else return kw.key; } @Override public void setSelected(final Object key) { UISingleton.runInSwing(new Runnable() { @Override public void run() { try { selecting=true; for(int i=0;i<b.getItemCount();i++) { KeyWrapper kw=(KeyWrapper)b.getItemAt(i); if(kw.key==null) { if(key==null) b.setSelectedIndex(i); } else if(kw.key.equals(key)) { b.setSelectedIndex(i); } } } finally { selecting=false; } } }); } @Override public void setOnChange(String sCallback) { getInterface().getOwner().getCallbackHandler().check(sCallback); onSelectionChange=sCallback; } @Override public void setBaseGroup(String group) { if(baseGroup!=null) { BaseGroup.Updater.removeFromGroup(DropdownImp.this,baseGroup); baseGroup=null; } if(group!=null) { baseGroup=group; BaseGroup.Updater.addToGroup(DropdownImp.this,baseGroup); } } @Override public boolean isEnabled() { return b.isEnabled(); } @Override public void setEnabled(boolean enabled) { b.setEnabled(enabled); } } // BaseGroup methods //////////////////// @Override public int getBaseline() { FontMetrics fm=b.getFontMetrics(b.getFont()); int border=(b.getPreferredSize().height-fm.getHeight())/2; int bestGuess=border+fm.getAscent(); if(PlatformUtils.isMac()) bestGuess-=1; return bestGuess; } @Override public InternalWidgetOwner getInternalWidgetOwner() { return (InternalWidgetOwner)cInterface.getOwner(); } @Override public void setTopOffset(int topOffset) { if(this.topOffset==topOffset) return; this.topOffset=topOffset; relayout(); } // Debugging @Override protected void paintChildren(Graphics g) { super.paintChildren(g); BaseGroup.Debug.paint(g,this,topOffset); } }