1 package prefuse.util.ui; 2 3 import java.awt.Color ; 4 import java.awt.Dimension ; 5 import java.awt.Font ; 6 import java.awt.FontMetrics ; 7 import java.awt.Graphics ; 8 import java.awt.event.ActionEvent ; 9 import java.awt.event.MouseAdapter ; 10 import java.awt.event.MouseEvent ; 11 import java.util.ArrayList ; 12 import java.util.Iterator ; 13 import java.util.List ; 14 15 import javax.swing.AbstractAction ; 16 import javax.swing.BoxLayout ; 17 import javax.swing.JComponent ; 18 import javax.swing.JLabel ; 19 import javax.swing.JSlider ; 20 import javax.swing.JTextField ; 21 import javax.swing.event.ChangeEvent ; 22 import javax.swing.event.ChangeListener ; 23 24 import prefuse.util.StringLib; 25 26 32 public class JValueSlider extends JComponent { 33 34 private Number m_min, m_max, m_value; 35 private boolean m_ignore = false; 36 37 private JLabel m_label; 38 private JSlider m_slider; 39 private JTextField m_field; 40 private List m_listeners; 41 42 private int m_smin = 0; 43 private int m_srange = 100; 44 45 52 public JValueSlider(String title, double min, double max, double value) { 53 this(title, new Double (min), new Double (max), new Double (value)); 54 } 55 56 63 public JValueSlider(String title, float min, float max, float value) { 64 this(title, new Float (min), new Float (max), new Float (value)); 65 } 66 67 74 public JValueSlider(String title, int min, int max, int value) { 75 this(title, new Integer (min), new Integer (max), new Integer (value)); 76 m_smin = min; 77 m_srange = max-min; 78 m_slider.setMinimum(min); 79 m_slider.setMaximum(max); 80 setValue(new Integer (value)); 81 } 82 83 90 public JValueSlider(String title, long min, long max, long value) { 91 this(title, new Long (min), new Long (max), new Long (value)); 92 } 93 94 101 public JValueSlider(String title, Number min, Number max, Number value) { 102 m_min = min; 103 m_max = max; 104 m_value = value; 105 m_slider = new JSlider (); 106 m_label = new JLabel (title); 107 m_field = new JTextField (); 108 m_listeners = new ArrayList (); 109 110 m_field.setBorder(null); 111 112 setSliderValue(); 113 setFieldValue(); 114 115 initUI(); 116 } 117 118 121 protected void initUI() { 122 m_slider.addChangeListener(new ChangeListener () { 123 public void stateChanged(ChangeEvent e) { 124 if ( m_ignore ) return; 125 m_ignore = true; 126 m_value = getSliderValue(); 128 setFieldValue(); 130 fireChangeEvent(); 132 m_ignore = false; 133 } 134 }); 135 m_field.addActionListener(new AbstractAction () { 136 public void actionPerformed(ActionEvent e) { 137 if ( m_ignore ) return; 138 m_ignore = true; 139 Number v = getFieldValue(); 140 if ( v != m_value ) { 141 m_value = v; 143 setSliderValue(); 145 } 146 fireChangeEvent(); 148 m_ignore = false; 149 } 150 }); 151 m_field.addMouseListener(new MouseAdapter () { 152 public void mouseEntered(MouseEvent e) { 153 String s = m_field.getText(); 154 if ( isTextObscured(m_field, s) ) 155 m_field.setToolTipText(s); 156 } 157 public void mouseExited(MouseEvent e) { 158 m_field.setToolTipText(null); 159 } 160 }); 161 m_label.addMouseListener(new MouseAdapter () { 162 public void mouseEntered(MouseEvent e) { 163 String s = m_label.getText(); 164 if ( isTextObscured(m_label, s) ) 165 m_label.setToolTipText(s); 166 } 167 public void mouseExited(MouseEvent e) { 168 m_label.setToolTipText(null); 169 } 170 }); 171 172 setLayout(new BoxLayout (this, BoxLayout.X_AXIS)); 173 add(m_label); 174 add(m_slider); 175 add(m_field); 176 } 177 178 181 private static boolean isTextObscured(JComponent c, String s) { 182 Graphics g = c.getGraphics(); 183 FontMetrics fm = g.getFontMetrics(c.getFont()); 184 int sw = fm.stringWidth(s); 185 return ( sw > c.getWidth() ); 186 } 187 188 190 194 public Number getValue() { 195 return m_value; 196 } 197 198 202 public void setValue(Number value) { 203 m_value = value; 204 setSliderValue(); 205 setFieldValue(); 206 } 207 208 212 private Number getSliderValue() { 213 if ( m_value instanceof Integer ) { 214 int val = m_slider.getValue(); 215 int min = m_min.intValue(); 216 int max = m_max.intValue(); 217 return new Integer (min + (val-m_smin)*(max-min)/m_srange); 218 } else if ( m_value instanceof Long ) { 219 int val = m_slider.getValue(); 220 long min = m_min.longValue(); 221 long max = m_max.longValue(); 222 return new Long (min + (val-m_smin)*(max-min)/m_srange); 223 } else { 224 double f = (m_slider.getValue()-m_smin)/(double)m_srange; 225 double min = m_min.doubleValue(); 226 double max = m_max.doubleValue(); 227 double val = min + f*(max-min); 228 return (m_value instanceof Double ? (Number )new Double (val) 229 : new Float ((float)val)); 230 } 231 } 232 233 236 private void setSliderValue() { 237 int val; 238 if ( m_value instanceof Double || m_value instanceof Float ) { 239 double value = m_value.doubleValue(); 240 double min = m_min.doubleValue(); 241 double max = m_max.doubleValue(); 242 val = m_smin + (int)Math.round(m_srange*((value-min)/(max-min))); 243 } else { 244 long value = m_value.longValue(); 245 long min = m_min.longValue(); 246 long max = m_max.longValue(); 247 val = m_smin + (int)((m_srange*(value-min))/(max-min)); 248 } 249 m_slider.setValue(val); 250 } 251 252 256 private Number getFieldValue() { 257 if ( m_value instanceof Double || m_value instanceof Float ) { 258 double v; 259 try { 260 v = Double.parseDouble(m_field.getText()); 261 } catch ( Exception e ) { 262 return m_value; 264 } 265 if ( v < m_min.doubleValue() || v > m_max.doubleValue() ) { 266 return m_value; 268 } 269 return m_value instanceof Double ? (Number )new Double (v) 270 : new Float ((float)v); 271 } else { 272 long v; 273 try { 274 v = Long.parseLong(m_field.getText()); 275 } catch ( Exception e ) { 276 return m_value; 278 } 279 if ( v < m_min.longValue() || v > m_max.longValue() ) { 280 return m_value; 282 } 283 return m_value instanceof Long ? (Number )new Long (v) 284 : new Integer ((int)v); 285 } 286 } 287 288 291 private void setFieldValue() { 292 String text; 293 if ( m_value instanceof Double || m_value instanceof Float ) 294 text = StringLib.formatNumber(m_value.doubleValue(),3); 295 else 296 text = String.valueOf(m_value.longValue()); 297 m_field.setText(text); 298 } 299 300 302 306 public void addChangeListener(ChangeListener cl) { 307 if ( !m_listeners.contains(cl) ) 308 m_listeners.add(cl); 309 } 310 311 315 public void removeChangeListener(ChangeListener cl) { 316 m_listeners.remove(cl); 317 } 318 319 322 protected void fireChangeEvent() { 323 Iterator iter = m_listeners.iterator(); 324 ChangeEvent evt = new ChangeEvent (this); 325 while ( iter.hasNext() ) { 326 ChangeListener cl = (ChangeListener )iter.next(); 327 cl.stateChanged(evt); 328 } 329 } 330 331 333 336 public void setBackground(Color c) { 337 m_field.setBackground(c); 338 m_label.setBackground(c); 339 m_slider.setBackground(c); 340 super.setBackground(c); 341 } 342 343 346 public void setForeground(Color c) { 347 m_field.setForeground(c); 348 m_label.setForeground(c); 349 m_slider.setForeground(c); 350 super.setForeground(c); 351 } 352 353 356 public void setFont(Font f) { 357 m_field.setFont(f); 358 m_label.setFont(f); 359 m_slider.setFont(f); 360 super.setFont(f); 361 } 362 363 366 public void setPreferredSize(Dimension d) { 367 int fw = Math.min(40, d.width/5); 368 int lw = Math.min(100, (d.width-fw)/2); 369 int sw = d.width-fw-lw; 370 super.setPreferredSize(d); 371 Dimension dd = new Dimension (lw, d.height); 372 m_label.setPreferredSize(dd); 373 dd = new Dimension (sw, d.height); 374 m_slider.setPreferredSize(dd); 375 dd = new Dimension (fw, d.height); 376 m_field.setPreferredSize(dd); 377 } 378 379 } | Popular Tags |