Squiz Matrix  4.12.2
 All Data Structures Namespaces Functions Variables Pages
GenericDialog.java
1 package ij.gui;
2 import java.awt.*;
3 import java.awt.event.*;
4 import java.util.*;
5 import ij.*;
6 import ij.plugin.frame.Recorder;
7 import ij.plugin.ScreenGrabber;
8 import ij.util.Tools;
9 import javax.swing.*;
10 
33 public class GenericDialog extends JDialog implements ActionListener,
34 TextListener, FocusListener, ItemListener, KeyListener, AdjustmentListener {
35 
36  protected Vector numberField, stringField, checkbox, choice, slider;
37  protected TextArea textArea1, textArea2;
38  protected Vector defaultValues,defaultText;
39  protected Component theLabel;
40  private Button cancel, okay;
41  private boolean wasCanceled;
42  private int y;
43  private int nfIndex, sfIndex, cbIndex, choiceIndex;
44  private GridBagLayout grid;
45  private GridBagConstraints c;
46  private boolean firstNumericField=true;
47  private boolean firstSlider=true;
48  private boolean invalidNumber;
49  private String errorMessage;
50  private boolean firstPaint = true;
51  private Hashtable labels;
52 
57  public GenericDialog(String title) {
58  super();
59  setModal(true);
60  setSize(350, 230);
61  setTitle(title);
62  grid = new GridBagLayout();
63  c = new GridBagConstraints();
64  getContentPane().setLayout(grid);
65  addKeyListener(this);
66  GUI.center(this);
67  }
68 
69  public GenericDialog(String title, ij.ImageJ parent) {
70  this(title);
71  }
72 
74  public GenericDialog(String title, JApplet parent) {
75  this(title);
76  }
77 
78  //void showFields(String id) {
79  // String s = id+": ";
80  // for (int i=0; i<maxItems; i++)
81  // if (numberField[i]!=null)
82  // s += i+"='"+numberField[i].getText()+"' ";
83  // IJ.write(s);
84  //}
85 
92  public void addNumericField(String label, double defaultValue, int digits) {
93  addNumericField(label, defaultValue, digits, 6, null);
94  }
95 
104  public void addNumericField(String label, double defaultValue, int digits, int columns, String units) {
105  String label2 = label;
106  if (label2.indexOf('_')!=-1)
107  label2 = label2.replace('_', ' ');
108  Label theLabel = makeLabel(label2);
109  c.gridx = 0; c.gridy = y;
110  c.anchor = GridBagConstraints.EAST;
111  c.gridwidth = 1;
112  if (firstNumericField)
113  c.insets = new Insets(5, 0, 3, 0);
114  else
115  c.insets = new Insets(0, 0, 3, 0);
116  grid.setConstraints(theLabel, c);
117  getContentPane().add(theLabel);
118 
119  if (numberField==null) {
120  numberField = new Vector(5);
121  defaultValues = new Vector(5);
122  defaultText = new Vector(5);
123  }
124  if (IJ.isWindows()) columns -= 2;
125  if (columns<1) columns = 1;
126  TextField tf = new TextField(IJ.d2s(defaultValue, digits), columns);
127  tf.addActionListener(this);
128  tf.addTextListener(this);
129  tf.addFocusListener(this);
130  tf.addKeyListener(this);
131  numberField.addElement(tf);
132  defaultValues.addElement(new Double(defaultValue));
133  defaultText.addElement(tf.getText());
134  c.gridx = 1; c.gridy = y;
135  c.anchor = GridBagConstraints.WEST;
136  tf.setEditable(true);
137  if (firstNumericField) tf.selectAll();
138  firstNumericField = false;
139  if (units==null||units.equals("")) {
140  grid.setConstraints(tf, c);
141  getContentPane().add(tf);
142  } else {
143  Panel panel = new Panel();
144  panel.setLayout(new FlowLayout(FlowLayout.LEFT, 0, 0));
145  panel.add(tf);
146  panel.add(new Label(" "+units));
147  grid.setConstraints(panel, c);
148  getContentPane().add(panel);
149  }
150  y++;
151  }
152 
153  private Label makeLabel(String label) {
154  if (IJ.isMacintosh())
155  label += " ";
156  return new Label(label);
157  }
158 
159  private void saveLabel(Component component, String label) {
160  if (labels==null)
161  labels = new Hashtable();
162  labels.put(component, label);
163  }
164 
169  public void addStringField(String label, String defaultText) {
170  addStringField(label, defaultText, 8);
171  }
172 
178  public void addStringField(String label, String defaultText, int columns) {
179  Label theLabel = makeLabel(label);
180  c.gridx = 0; c.gridy = y;
181  c.anchor = GridBagConstraints.EAST;
182  c.gridwidth = 1;
183  if (stringField==null) {
184  stringField = new Vector(4);
185  c.insets = new Insets(5, 0, 5, 0);
186  } else
187  c.insets = new Insets(0, 0, 5, 0);
188  grid.setConstraints(theLabel, c);
189  getContentPane().add(theLabel);
190 
191  TextField tf = new TextField(defaultText, columns);
192  tf.addActionListener(this);
193  tf.addTextListener(this);
194  tf.addFocusListener(this);
195  tf.addKeyListener(this);
196  c.gridx = 1; c.gridy = y;
197  c.anchor = GridBagConstraints.WEST;
198  grid.setConstraints(tf, c);
199  tf.setEditable(true);
200  getContentPane().add(tf);
201  stringField.addElement(tf);
202  y++;
203  }
204 
209  public void addCheckbox(String label, boolean defaultValue) {
210  if (checkbox==null) {
211  checkbox = new Vector(4);
212  c.insets = new Insets(15, 20, 0, 0);
213  } else
214  c.insets = new Insets(0, 20, 0, 0);
215  c.gridx = 0; c.gridy = y;
216  c.gridwidth = 2;
217  c.anchor = GridBagConstraints.WEST;
218  Checkbox cb = new Checkbox(label);
219  grid.setConstraints(cb, c);
220  cb.setState(defaultValue);
221  cb.addItemListener(this);
222  cb.addKeyListener(this);
223  getContentPane().add(cb);
224  checkbox.addElement(cb);
225  //ij.IJ.write("addCheckbox: "+ y+" "+cbIndex);
226  y++;
227  }
228 
235  public void addCheckboxGroup(int rows, int columns, String[] labels, boolean[] defaultValues) {
236  Panel panel = new Panel();
237  panel.setLayout(new GridLayout(rows,columns,10,0));
238  int startCBIndex = cbIndex;
239  int i1 = 0;
240  int[] index = new int[labels.length];
241  if (checkbox==null)
242  checkbox = new Vector(12);
243  boolean addListeners = labels.length<=4;
244  for (int row=0; row<rows; row++) {
245  for (int col=0; col<columns; col++) {
246  int i2 = col*rows+row;
247  if (i2>=labels.length)
248  break;
249  index[i1] = i2;
250  Checkbox cb = new Checkbox(labels[i1]);
251  checkbox.addElement(cb);
252  cb.setState(defaultValues[i1]);
253  if (addListeners) cb.addItemListener(this);
254  panel.add(cb);
255  i1++;
256  }
257  }
258  c.gridx = 0; c.gridy = y;
259  c.gridwidth = 2;
260  c.anchor = GridBagConstraints.WEST;
261  c.insets = new Insets(10, 0, 0, 0);
262  grid.setConstraints(panel, c);
263  getContentPane().add(panel);
264  y++;
265  }
266 
272  public void addChoice(String label, String[] items, String defaultItem) {
273  Label theLabel = makeLabel(label);
274  c.gridx = 0; c.gridy = y;
275  c.anchor = GridBagConstraints.EAST;
276  c.gridwidth = 1;
277  if (choice==null) {
278  choice = new Vector(4);
279  c.insets = new Insets(5, 0, 5, 0);
280  } else
281  c.insets = new Insets(0, 0, 5, 0);
282  grid.setConstraints(theLabel, c);
283  getContentPane().add(theLabel);
284  Choice thisChoice = new Choice();
285  thisChoice.addKeyListener(this);
286  thisChoice.addItemListener(this);
287  for (int i=0; i<items.length; i++)
288  thisChoice.addItem(items[i]);
289  thisChoice.select(defaultItem);
290  c.gridx = 1; c.gridy = y;
291  c.anchor = GridBagConstraints.WEST;
292  grid.setConstraints(thisChoice, c);
293  getContentPane().add(thisChoice);
294  choice.addElement(thisChoice);
295  y++;
296  }
297 
299  public void addMessage(String text) {
300  if (text.indexOf('\n')>=0)
301  theLabel = new MultiLineLabel(text);
302  else
303  theLabel = new Label(text);
304  //theLabel.addKeyListener(this);
305  c.gridx = 0; c.gridy = y;
306  c.gridwidth = 2;
307  c.anchor = GridBagConstraints.WEST;
308  c.insets = new Insets(text.equals("")?0:10, 20, 0, 0);
309  grid.setConstraints(theLabel, c);
310  getContentPane().add(theLabel);
311  y++;
312  }
313 
320  public void addTextAreas(String text1, String text2, int rows, int columns) {
321  if (textArea1!=null)
322  return;
323  Panel panel = new Panel();
324  textArea1 = new TextArea(text1,rows,columns,TextArea.SCROLLBARS_NONE);
325  //textArea1.setBackground(Color.white);
326  //textArea1.append(text1);
327  panel.add(textArea1);
328  if (text2!=null) {
329  textArea2 = new TextArea(text2,rows,columns,TextArea.SCROLLBARS_NONE);
330  //textArea2.setBackground(Color.white);
331  //textArea2.append(text2);
332  panel.add(textArea2);
333  }
334  c.gridx = 0; c.gridy = y;
335  c.gridwidth = 2;
336  c.anchor = GridBagConstraints.WEST;
337  c.insets = new Insets(15, 20, 0, 0);
338  grid.setConstraints(panel, c);
339  getContentPane().add(panel);
340  y++;
341  }
342 
343  public void addSlider(String label, double minValue, double maxValue, double defaultValue) {
344  int columns = 4;
345  int digits = 0;
346  String label2 = label;
347  if (label2.indexOf('_')!=-1)
348  label2 = label2.replace('_', ' ');
349  Label theLabel = makeLabel(label2);
350  c.gridx = 0; c.gridy = y;
351  c.anchor = GridBagConstraints.EAST;
352  c.gridwidth = 1;
353  c.insets = new Insets(0, 0, 3, 0);
354  grid.setConstraints(theLabel, c);
355  getContentPane().add(theLabel);
356 
357  if (slider==null)
358  slider = new Vector(5);
359  Scrollbar s = new Scrollbar(Scrollbar.HORIZONTAL, (int)defaultValue, 1, (int)minValue, (int)maxValue+1);
360  slider.addElement(s);
361  s.addAdjustmentListener(this);
362  s.setUnitIncrement(1);
363 
364  if (numberField==null) {
365  numberField = new Vector(5);
366  defaultValues = new Vector(5);
367  defaultText = new Vector(5);
368  }
369  if (IJ.isWindows()) columns -= 2;
370  if (columns<1) columns = 1;
371  TextField tf = new TextField(IJ.d2s(defaultValue, digits), columns);
372  tf.addActionListener(this);
373  tf.addTextListener(this);
374  tf.addFocusListener(this);
375  tf.addKeyListener(this);
376  numberField.addElement(tf);
377  defaultValues.addElement(new Double(defaultValue));
378  defaultText.addElement(tf.getText());
379  tf.setEditable(true);
380  if (firstNumericField && firstSlider) tf.selectAll();
381  firstSlider = false;
382 
383  Panel panel = new Panel();
384  GridBagLayout pgrid = new GridBagLayout();
385  GridBagConstraints pc = new GridBagConstraints();
386  panel.setLayout(pgrid);
387  // label
388  //pc.insets = new Insets(5, 0, 0, 0);
389  //pc.gridx = 0; pc.gridy = 0;
390  //pc.gridwidth = 1;
391  //pc.anchor = GridBagConstraints.EAST;
392  //pgrid.setConstraints(theLabel, pc);
393  //panel.add(theLabel);
394  // slider
395  pc.gridx = 0; pc.gridy = 0;
396  pc.gridwidth = 1;
397  pc.ipadx = 75;
398  pc.anchor = GridBagConstraints.WEST;
399  pgrid.setConstraints(s, pc);
400  panel.add(s);
401  pc.ipadx = 0; // reset
402  // text field
403  pc.gridx = 1;
404  pc.insets = new Insets(5, 5, 0, 0);
405  pc.anchor = GridBagConstraints.EAST;
406  pgrid.setConstraints(tf, pc);
407  panel.add(tf);
408 
409  grid.setConstraints(panel, c);
410  c.gridx = 1; c.gridy = y;
411  c.gridwidth = 1;
412  c.anchor = GridBagConstraints.WEST;
413  c.insets = new Insets(0, 0, 0, 0);
414  grid.setConstraints(panel, c);
415  getContentPane().add(panel);
416  y++;
417  }
418 
420  public void addPanel(Panel panel) {
421  addPanel(panel , GridBagConstraints.WEST, new Insets(5, 0, 0, 0));
422  }
423 
427  public void addPanel(Panel panel, int contraints, Insets insets) {
428  c.gridx = 0; c.gridy = y;
429  c.gridwidth = 2;
430  c.anchor = contraints;
431  c.insets = insets;
432  grid.setConstraints(panel, c);
433  getContentPane().add(panel);
434  y++;
435  }
436 
438  public boolean wasCanceled() {
439  return wasCanceled;
440  }
441 
443  public double getNextNumber() {
444  if (numberField==null)
445  return -1.0;
446  TextField tf = (TextField)numberField.elementAt(nfIndex);
447  String theText = tf.getText();
448  String label=null;
449  String originalText = (String)defaultText.elementAt(nfIndex);
450  double defaultValue = ((Double)(defaultValues.elementAt(nfIndex))).doubleValue();
451  double value;
452  if (theText.equals(originalText))
453  value = defaultValue;
454  else {
455  Double d = getValue(theText);
456  if (d!=null)
457  value = d.doubleValue();
458  else {
459  invalidNumber = true;
460  errorMessage = "\""+theText+"\" is an invalid number";
461  value = 0.0;
462  }
463  }
464  if (Recorder.record)
465  recordOption(tf, trim(theText));
466  nfIndex++;
467  return value;
468  }
469 
470  private String trim(String value) {
471  if (value.endsWith(".0"))
472  value = value.substring(0, value.length()-2);
473  if (value.endsWith(".00"))
474  value = value.substring(0, value.length()-3);
475  return value;
476  }
477 
478  private void recordOption(Component component, String value) {
479  String label = (String)labels.get((Object)component);
480  Recorder.recordOption(label, value);
481  }
482 
483  private void recordCheckboxOption(Checkbox cb) {
484  String label = (String)labels.get((Object)cb);
485  if (label!=null) {
486  if (cb.getState()) // checked
487  Recorder.recordOption(label);
488  else // unchecked
489  Recorder.recordOption(" ");
490  }
491  }
492 
493  protected Double getValue(String theText) {
494  Double d;
495  try {d = new Double(theText);}
496  catch (NumberFormatException e){
497  d = null;
498  }
499  return d;
500  }
501 
504  public boolean invalidNumber() {
505  boolean wasInvalid = invalidNumber;
506  invalidNumber = false;
507  return wasInvalid;
508  }
509 
512  public String getErrorMessage() {
513  return errorMessage;
514  }
515 
517  public String getNextString() {
518  String theText;
519  if (stringField==null)
520  return "";
521  TextField tf = (TextField)(stringField.elementAt(sfIndex));
522  theText = tf.getText();
523  if (Recorder.record)
524  recordOption(tf, theText);
525  sfIndex++;
526  return theText;
527  }
528 
530  public boolean getNextBoolean() {
531  if (checkbox==null)
532  return false;
533  Checkbox cb = (Checkbox)(checkbox.elementAt(cbIndex));
534  if (Recorder.record)
535  recordCheckboxOption(cb);
536  boolean state = cb.getState();
537  cbIndex++;
538  return state;
539  }
540 
542  public String getNextChoice() {
543  if (choice==null)
544  return "";
545  Choice thisChoice = (Choice)(choice.elementAt(choiceIndex));
546  String item = thisChoice.getSelectedItem();
547  if (Recorder.record)
548  recordOption(thisChoice, item);
549  choiceIndex++;
550  return item;
551  }
552 
554  public int getNextChoiceIndex() {
555  if (choice==null)
556  return -1;
557  Choice thisChoice = (Choice)(choice.elementAt(choiceIndex));
558  int index = thisChoice.getSelectedIndex();
559  if (Recorder.record)
560  recordOption(thisChoice, thisChoice.getSelectedItem());
561  choiceIndex++;
562  return index;
563  }
564 
566  public String getNextText() {
567  String text;
568  if (textArea1!=null) {
569  textArea1.selectAll();
570  text = textArea1.getText();
571  textArea1 = null;
572  if (Recorder.record)
573  Recorder.recordOption("text1", text.replace('\n',' '));
574  } else if (textArea2!=null) {
575  textArea2.selectAll();
576  text = textArea2.getText();
577  textArea2 = null;
578  if (Recorder.record)
579  Recorder.recordOption("text2", text.replace('\n',' '));
580  } else
581  text = null;
582  return text;
583  }
584 
586  public void showDialog() {
587  nfIndex = 0;
588  sfIndex = 0;
589  cbIndex = 0;
590  choiceIndex = 0;
591  if (stringField!=null&&numberField==null) {
592  TextField tf = (TextField)(stringField.elementAt(0));
593  tf.selectAll();
594  }
595  Panel buttons = new Panel();
596  buttons.setLayout(new FlowLayout(FlowLayout.CENTER, 5, 0));
597  cancel = new Button("Cancel");
598  cancel.addActionListener(this);
599  okay = new Button(" OK ");
600  okay.addActionListener(this);
601  if (IJ.isMacintosh()) {
602  buttons.add(cancel);
603  buttons.add(okay);
604  } else {
605  buttons.add(okay);
606  buttons.add(cancel);
607  }
608  c.gridx = 0; c.gridy = y;
609  c.anchor = GridBagConstraints.EAST;
610  c.gridwidth = 2;
611  c.insets = new Insets(15, 0, 0, 0);
612  grid.setConstraints(buttons, c);
613  getContentPane().add(buttons);
614  if (IJ.isMacintosh() && !IJ.isJava14())
615  setResizable(false);
616  show();
617  IJ.wait(250); // work around for Sun/WinNT bug
618  //EventQueue.invokeLater(new Runnable () {
619  // public void run () {
620  // show();
621  //}});
622 
623  }
624 
626  public Vector getNumericFields() {
627  return numberField;
628  }
629 
631  public Vector getStringFields() {
632  return stringField;
633  }
634 
636  public Vector getCheckboxes() {
637  return checkbox;
638  }
639 
641  public Vector getChoices() {
642  return choice;
643  }
644 
646  public Vector getSliders() {
647  return slider;
648  }
649 
651  public TextArea getTextArea1() {
652  return textArea1;
653  }
654 
656  public TextArea getTextArea2() {
657  return textArea2;
658  }
659 
660  protected void setup() {
661  }
662 
663  public void actionPerformed(ActionEvent e) {
664  Object source = e.getSource();
665  if (source==okay || source==cancel) {
666  wasCanceled = source==cancel;
667  closeDialog();
668  }
669  }
670 
671  void closeDialog() {
672  setVisible(false);
673  dispose();
674  }
675 
676  public void textValueChanged(TextEvent e) {
677  if (slider==null || slider.size()!=numberField.size())
678  return;
679  Object source = e.getSource();
680  for (int i=0; i<numberField.size(); i++) {
681  if (source==numberField.elementAt(i)) {
682  TextField tf = (TextField)numberField.elementAt(i);
683  double value = Tools.parseDouble(tf.getText());
684  if (!Double.isNaN(value)) {
685  Scrollbar sb = (Scrollbar)slider.elementAt(i);
686  sb.setValue((int)value);
687  }
688  //IJ.log(i+" "+tf.getText());
689  }
690  }
691  }
692 
693  public void itemStateChanged(ItemEvent e) {
694  }
695 
696  public void focusGained(FocusEvent e) {
697  Component c = e.getComponent();
698  if (c instanceof TextField)
699  ((TextField)c).selectAll();
700  }
701 
702  public void focusLost(FocusEvent e) {
703  Component c = e.getComponent();
704  if (c instanceof TextField)
705  ((TextField)c).select(0,0);
706  }
707 
708  public void keyPressed(KeyEvent e) {
709  int keyCode = e.getKeyCode();
710  IJ.setKeyDown(keyCode);
711  if (keyCode==KeyEvent.VK_ENTER && textArea1==null)
712  closeDialog();
713  }
714 
715  public void keyReleased(KeyEvent e) {
716  int keyCode = e.getKeyCode();
717  IJ.setKeyUp(keyCode);
718  int flags = e.getModifiers();
719  boolean control = (flags & KeyEvent.CTRL_MASK) != 0;
720  boolean meta = (flags & KeyEvent.META_MASK) != 0;
721  boolean shift = (flags & e.SHIFT_MASK) != 0;
722  if (keyCode==KeyEvent.VK_G && shift && (control||meta) && IJ.isJava2())
723  new ScreenGrabber().run("");
724  }
725 
726  public void keyTyped(KeyEvent e) {}
727 
728  public Insets getInsets() {
729  Insets i= super.getInsets();
730  return new Insets(i.top+10, i.left+10, i.bottom+10, i.right+10);
731  }
732 
733  public synchronized void adjustmentValueChanged(AdjustmentEvent e) {
734  Object source = e.getSource();
735  for (int i=0; i<slider.size(); i++) {
736  if (source==slider.elementAt(i)) {
737  Scrollbar sb = (Scrollbar)source;
738  TextField tf = (TextField)numberField.elementAt(i);
739  tf.setText(""+sb.getValue());
740  }
741  }
742  }
743 
744  public void paint(Graphics g) {
745  super.paint(g);
746  if (firstPaint && numberField!=null) {
747  TextField tf = (TextField)(numberField.elementAt(0));
748  tf.requestFocus();
749  firstPaint = false;
750  }
751  }
752 
753 }