1
2
3
4 package edu.stanford.suif.keepresident;
5
6 import org.eclipse.jface.preference.FieldEditor;
7 import org.eclipse.swt.SWT;
8 import org.eclipse.swt.events.DisposeEvent;
9 import org.eclipse.swt.events.DisposeListener;
10 import org.eclipse.swt.events.SelectionAdapter;
11 import org.eclipse.swt.events.SelectionEvent;
12 import org.eclipse.swt.layout.GridData;
13 import org.eclipse.swt.widgets.Composite;
14 import org.eclipse.swt.widgets.Control;
15 import org.eclipse.swt.widgets.Label;
16 import org.eclipse.swt.widgets.Scale;
17
18 /***
19 * LabelledScaleFieldEditor
20 *
21 * @author John Whaley
22 * @version $Id: LabelledScaleFieldEditor.java,v 1.5 2004/08/18 07:28:32 jwhaley Exp $
23 */
24 public class LabelledScaleFieldEditor extends FieldEditor {
25 /***
26 * Value that will feed Scale.setIncrement(int).
27 */
28 private int incrementValue;
29 /***
30 * Value that will feed Scale.setMaximum(int).
31 */
32 private int maxValue;
33 /***
34 * Value that will feed Scale.setMinimum(int).
35 */
36 private int minValue;
37 /***
38 * Old integer value.
39 */
40 private int oldValue;
41 /***
42 * Value that will feed Scale.setPageIncrement(int).
43 */
44 private int pageIncrementValue;
45 /***
46 * The scale, or <code>null</code> if none.
47 */
48 protected Scale scale;
49 protected Label myLabel;
50
51 /***
52 * Creates a scale field editor.
53 *
54 * @param name
55 * the name of the preference this field editor works on
56 * @param labelText
57 * the label text of the field editor
58 * @param parent
59 * the parent of the field editor's control
60 */
61 public LabelledScaleFieldEditor(String name, String labelText, Composite parent) {
62 super(name, labelText, parent);
63 setDefaultValues();
64 }
65
66 /***
67 * Creates a scale field editor with particular scale values.
68 *
69 * @param name
70 * the name of the preference this field editor works on
71 * @param labelText
72 * the label text of the field editor
73 * @param parent
74 * the parent of the field editor's control
75 * @param min
76 * the value used for Scale.setMinimum(int).
77 * @param max
78 * the value used for Scale.setMaximum(int).
79 * @param increment
80 * the value used for Scale.setIncrement(int).
81 * @param pageIncrement
82 * the value used for Scale.setPageIncrement(int).
83 */
84 public LabelledScaleFieldEditor(String name, String labelText, Composite parent, int min, int max,
85 int increment, int pageIncrement) {
86 super(name, labelText, parent);
87 setValues(min, max, increment, pageIncrement);
88 }
89
90
91
92
93
94
95 protected void adjustForNumColumns(int numColumns) {
96 ((GridData) scale.getLayoutData()).horizontalSpan = numColumns - 2;
97 ((GridData) myLabel.getLayoutData()).horizontalSpan = 1;
98 }
99
100
101
102
103
104
105
106 protected void doFillIntoGrid(Composite parent, int numColumns) {
107 Control control = getLabelControl(parent);
108 GridData gd = new GridData();
109 control.setLayoutData(gd);
110
111 scale = getScaleControl(parent);
112 gd = new GridData(GridData.FILL_HORIZONTAL);
113 gd.verticalAlignment = GridData.FILL;
114 gd.horizontalSpan = numColumns - 2;
115
116 scale.setLayoutData(gd);
117
118 myLabel = getMyLabelControl(parent);
119 gd = new GridData();
120 gd.horizontalSpan = 1;
121 myLabel.setLayoutData(gd);
122
123 updateScale();
124 }
125
126
127
128
129
130
131 protected void doLoad() {
132 if (scale != null) {
133 int value = getPreferenceStore().getInt(getPreferenceName());
134 value = Math.max(value, minValue);
135 value = Math.min(value, maxValue);
136 scale.setSelection(value);
137 myLabel.setText(decorateLabel(value));
138 oldValue = value;
139 }
140 }
141
142
143
144
145
146
147 protected void doLoadDefault() {
148 if (scale != null) {
149 int value = getPreferenceStore().getDefaultInt(getPreferenceName());
150 value = Math.max(value, minValue);
151 value = Math.min(value, maxValue);
152 scale.setSelection(value);
153 myLabel.setText(decorateLabel(value));
154 }
155 valueChanged();
156 }
157
158
159
160
161
162
163 protected void doStore() {
164 getPreferenceStore().setValue(getPreferenceName(), scale.getSelection());
165 }
166
167 /***
168 * Returns the value that will be used for Scale.setIncrement(int).
169 *
170 * @return the value.
171 * @see org.eclipse.swt.widgets.Scale#setIncrement(int)
172 */
173 public int getIncrement() {
174 return incrementValue;
175 }
176
177 /***
178 * Returns the value that will be used for Scale.setMaximum(int).
179 *
180 * @return the value.
181 * @see org.eclipse.swt.widgets.Scale#setMaximum(int)
182 */
183 public int getMaximum() {
184 return maxValue;
185 }
186
187 /***
188 * Returns the value that will be used for Scale.setMinimum(int).
189 *
190 * @return the value.
191 * @see org.eclipse.swt.widgets.Scale#setMinimum(int)
192 */
193 public int getMinimum() {
194 return minValue;
195 }
196
197
198
199
200
201
202 public int getNumberOfControls() {
203 return 3;
204 }
205
206 /***
207 * Returns the value that will be used for Scale.setPageIncrement(int).
208 *
209 * @return the value.
210 * @see org.eclipse.swt.widgets.Scale#setPageIncrement(int)
211 */
212 public int getPageIncrement() {
213 return pageIncrementValue;
214 }
215
216 /***
217 * Returns this field editor's scale control.
218 *
219 * @return the scale control, or <code>null</code> if no scale field is
220 * created yet
221 */
222 public Scale getScaleControl() {
223 return scale;
224 }
225
226 /***
227 * Returns this field editor's scale control. The control is created if it
228 * does not yet exist.
229 *
230 * @param parent
231 * the parent
232 * @return the scale control
233 */
234 private Scale getScaleControl(Composite parent) {
235 if (scale == null) {
236 scale = new Scale(parent, SWT.HORIZONTAL);
237 scale.setFont(parent.getFont());
238 scale.addSelectionListener(new SelectionAdapter() {
239 public void widgetSelected(SelectionEvent event) {
240 valueChanged();
241 }
242 });
243 scale.addDisposeListener(new DisposeListener() {
244 public void widgetDisposed(DisposeEvent event) {
245 scale = null;
246 }
247 });
248 } else {
249 checkParent(scale, parent);
250 }
251 return scale;
252 }
253
254 private Label getMyLabelControl(Composite parent) {
255 if (myLabel == null) {
256 myLabel = new Label(parent, SWT.HORIZONTAL);
257 myLabel.setFont(parent.getFont());
258 myLabel.addDisposeListener(new DisposeListener() {
259 public void widgetDisposed(DisposeEvent event) {
260 myLabel = null;
261 }
262 });
263 } else {
264 checkParent(myLabel, parent);
265 }
266 return myLabel;
267 }
268
269 /***
270 * Set default values for the various scale fields. These defaults are: <br>
271 * <ul>
272 * <li>Minimum = 0
273 * <li>Maximim = 10
274 * <li>Increment = 1
275 * <li>Page Increment = 1
276 * </ul>
277 */
278 private void setDefaultValues() {
279 setValues(0, 10, 1, 1);
280 }
281
282
283
284
285
286
287 public void setFocus() {
288 if (scale != null && !scale.isDisposed()) {
289 scale.setFocus();
290 }
291 }
292
293 /***
294 * Set the value to be used for Scale.setIncrement(int) and update the
295 * scale.
296 *
297 * @param increment
298 * a value greater than 0.
299 * @see org.eclipse.swt.widgets.Scale#setIncrement(int)
300 */
301 public void setIncrement(int increment) {
302 this.incrementValue = increment;
303 updateScale();
304 }
305
306 /***
307 * Set the value to be used for Scale.setMaximum(int) and update the scale.
308 *
309 * @param max
310 * a value greater than 0.
311 * @see org.eclipse.swt.widgets.Scale#setMaximum(int)
312 */
313 public void setMaximum(int max) {
314 this.maxValue = max;
315 updateScale();
316 }
317
318 /***
319 * Set the value to be used for Scale.setMinumum(int) and update the scale.
320 *
321 * @param min
322 * a value greater than 0.
323 * @see org.eclipse.swt.widgets.Scale#setMinimum(int)
324 */
325 public void setMinimum(int min) {
326 this.minValue = min;
327 updateScale();
328 }
329
330 /***
331 * Set the value to be used for Scale.setPageIncrement(int) and update the
332 * scale.
333 *
334 * @param pageIncrement
335 * a value greater than 0.
336 * @see org.eclipse.swt.widgets.Scale#setPageIncrement(int)
337 */
338 public void setPageIncrement(int pageIncrement) {
339 this.pageIncrementValue = pageIncrement;
340 updateScale();
341 }
342
343 /***
344 * Set all Scale values.
345 *
346 * @param min
347 * the value used for Scale.setMinimum(int).
348 * @param max
349 * the value used for Scale.setMaximum(int).
350 * @param increment
351 * the value used for Scale.setIncrement(int).
352 * @param pageIncrement
353 * the value used for Scale.setPageIncrement(int).
354 */
355 private void setValues(int min, int max, int increment, int pageIncrement) {
356 this.incrementValue = increment;
357 this.maxValue = max;
358 this.minValue = min;
359 this.pageIncrementValue = pageIncrement;
360 updateScale();
361 }
362
363 /***
364 * Update the scale particulars with set values.
365 */
366 private void updateScale() {
367 if (scale != null && !scale.isDisposed()) {
368 scale.setMinimum(getMinimum());
369 scale.setMaximum(getMaximum());
370 scale.setMinimum(getMinimum());
371 scale.setIncrement(getIncrement());
372 scale.setPageIncrement(getPageIncrement());
373 }
374 }
375
376 /***
377 * Informs this field editor's listener, if it has one, about a change to
378 * the value (<code>VALUE</code> property) provided that the old and new
379 * values are different.
380 * <p>
381 * This hook is <em>not</em> called when the scale is initialized (or
382 * reset to the default value) from the preference store.
383 * </p>
384 */
385 protected void valueChanged() {
386 setPresentsDefaultValue(false);
387 int newValue = scale.getSelection();
388 if (newValue != oldValue) {
389 fireStateChanged(IS_VALID, false, true);
390 fireValueChanged(VALUE, new Integer(oldValue), new Integer(newValue));
391 myLabel.setText(decorateLabel(newValue));
392 oldValue = newValue;
393 }
394 }
395
396 /***
397 * Converts the given number to a readable form.
398 * Patch due to Erich Haltenwanger.
399 */
400 private String decorateLabel(int size) {
401 final int kb_min = 1024;
402 final int kb_max = 1024 * 1024;
403 final int mb_min = kb_max;
404 final int mb_max = 1024 * 1024 * 1024;
405 int newValueDisplayed;
406 String appendix;
407 if (size < kb_min) {
408 appendix = " Byte";
409 newValueDisplayed = size;
410 } else if (size >= kb_min && size < kb_max) {
411 appendix = " KB";
412 newValueDisplayed = size / kb_min;
413 } else if (size >= mb_min && size < mb_max) {
414 appendix = " MB";
415 newValueDisplayed = size / mb_min;
416 } else {
417 newValueDisplayed = size;
418 appendix = " ???";
419 }
420 StringBuffer buffy = new StringBuffer();
421 buffy.append(newValueDisplayed);
422 buffy.append(appendix);
423 pad(buffy, PADDING);
424 return buffy.toString();
425 }
426
427 public static final int PADDING = 10;
428
429 private void pad(StringBuffer sb, int k) {
430 while (sb.length() < k) {
431 sb.append(' ');
432 }
433 }
434 }