Mercurial > projects > dwt2
comparison org.eclipse.swt.win32.win32.x86/src/org/eclipse/swt/widgets/ScrollBar.d @ 0:6dd524f61e62
add dwt win and basic java stuff
author | Frank Benoit <benoit@tionex.de> |
---|---|
date | Mon, 02 Mar 2009 14:44:16 +0100 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 0:6dd524f61e62 |
---|---|
1 /******************************************************************************* | |
2 * Copyright (c) 2000, 2008 IBM Corporation and others. | |
3 * All rights reserved. This program and the accompanying materials | |
4 * are made available under the terms of the Eclipse Public License v1.0 | |
5 * which accompanies this distribution, and is available at | |
6 * http://www.eclipse.org/legal/epl-v10.html | |
7 * | |
8 * Contributors: | |
9 * IBM Corporation - initial API and implementation | |
10 * Port to the D programming language: | |
11 * Frank Benoit <benoit@tionex.de> | |
12 *******************************************************************************/ | |
13 module org.eclipse.swt.widgets.ScrollBar; | |
14 | |
15 import org.eclipse.swt.SWT; | |
16 import org.eclipse.swt.SWTException; | |
17 import org.eclipse.swt.events.SelectionEvent; | |
18 import org.eclipse.swt.events.SelectionListener; | |
19 import org.eclipse.swt.graphics.Point; | |
20 import org.eclipse.swt.graphics.Rectangle; | |
21 import org.eclipse.swt.internal.win32.OS; | |
22 | |
23 import org.eclipse.swt.widgets.Widget; | |
24 import org.eclipse.swt.widgets.TypedListener; | |
25 import org.eclipse.swt.widgets.Event; | |
26 import org.eclipse.swt.widgets.Scrollable; | |
27 | |
28 import java.lang.all; | |
29 | |
30 /** | |
31 * Instances of this class are selectable user interface | |
32 * objects that represent a range of positive, numeric values. | |
33 * <p> | |
34 * At any given moment, a given scroll bar will have a | |
35 * single 'selection' that is considered to be its | |
36 * value, which is constrained to be within the range of | |
37 * values the scroll bar represents (that is, between its | |
38 * <em>minimum</em> and <em>maximum</em> values). | |
39 * </p><p> | |
40 * Typically, scroll bars will be made up of five areas: | |
41 * <ol> | |
42 * <li>an arrow button for decrementing the value</li> | |
43 * <li>a page decrement area for decrementing the value by a larger amount</li> | |
44 * <li>a <em>thumb</em> for modifying the value by mouse dragging</li> | |
45 * <li>a page increment area for incrementing the value by a larger amount</li> | |
46 * <li>an arrow button for incrementing the value</li> | |
47 * </ol> | |
48 * Based on their style, scroll bars are either <code>HORIZONTAL</code> | |
49 * (which have a left facing button for decrementing the value and a | |
50 * right facing button for incrementing it) or <code>VERTICAL</code> | |
51 * (which have an upward facing button for decrementing the value | |
52 * and a downward facing buttons for incrementing it). | |
53 * </p><p> | |
54 * On some platforms, the size of the scroll bar's thumb can be | |
55 * varied relative to the magnitude of the range of values it | |
56 * represents (that is, relative to the difference between its | |
57 * maximum and minimum values). Typically, this is used to | |
58 * indicate some proportional value such as the ratio of the | |
59 * visible area of a document to the total amount of space that | |
60 * it would take to display it. SWT supports setting the thumb | |
61 * size even if the underlying platform does not, but in this | |
62 * case the appearance of the scroll bar will not change. | |
63 * </p><p> | |
64 * Scroll bars are created by specifying either <code>H_SCROLL</code>, | |
65 * <code>V_SCROLL</code> or both when creating a <code>Scrollable</code>. | |
66 * They are accessed from the <code>Scrollable</code> using | |
67 * <code>getHorizontalBar</code> and <code>getVerticalBar</code>. | |
68 * </p><p> | |
69 * Note: Scroll bars are not Controls. On some platforms, scroll bars | |
70 * that appear as part of some standard controls such as a text or list | |
71 * have no operating system resources and are not children of the control. | |
72 * For this reason, scroll bars are treated specially. To create a control | |
73 * that looks like a scroll bar but has operating system resources, use | |
74 * <code>Slider</code>. | |
75 * </p> | |
76 * <dl> | |
77 * <dt><b>Styles:</b></dt> | |
78 * <dd>HORIZONTAL, VERTICAL</dd> | |
79 * <dt><b>Events:</b></dt> | |
80 * <dd>Selection</dd> | |
81 * </dl> | |
82 * <p> | |
83 * Note: Only one of the styles HORIZONTAL and VERTICAL may be specified. | |
84 * </p><p> | |
85 * IMPORTANT: This class is <em>not</em> intended to be subclassed. | |
86 * </p> | |
87 * | |
88 * @see Slider | |
89 * @see Scrollable | |
90 * @see Scrollable#getHorizontalBar | |
91 * @see Scrollable#getVerticalBar | |
92 * @see <a href="http://www.eclipse.org/swt/examples.php">SWT Example: ControlExample</a> | |
93 * @see <a href="http://www.eclipse.org/swt/">Sample code and further information</a> | |
94 */ | |
95 | |
96 public class ScrollBar : Widget { | |
97 Scrollable parent; | |
98 int increment, pageIncrement; | |
99 | |
100 /** | |
101 * Constructs a new instance of this class given its parent | |
102 * and a style value describing its behavior and appearance. | |
103 * <p> | |
104 * The style value is either one of the style constants defined in | |
105 * class <code>SWT</code> which is applicable to instances of this | |
106 * class, or must be built by <em>bitwise OR</em>'ing together | |
107 * (that is, using the <code>int</code> "|" operator) two or more | |
108 * of those <code>SWT</code> style constants. The class description | |
109 * lists the style constants that are applicable to the class. | |
110 * Style bits are also inherited from superclasses. | |
111 * </p> | |
112 * | |
113 * @param parent a composite control which will be the parent of the new instance (cannot be null) | |
114 * @param style the style of control to construct | |
115 * | |
116 * @exception IllegalArgumentException <ul> | |
117 * <li>ERROR_NULL_ARGUMENT - if the parent is null</li> | |
118 * </ul> | |
119 * @exception SWTException <ul> | |
120 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the parent</li> | |
121 * <li>ERROR_INVALID_SUBCLASS - if this class is not an allowed subclass</li> | |
122 * </ul> | |
123 * | |
124 * @see SWT#HORIZONTAL | |
125 * @see SWT#VERTICAL | |
126 * @see Widget#checkSubclass | |
127 * @see Widget#getStyle | |
128 */ | |
129 this (Scrollable parent, int style) { | |
130 super (parent, checkStyle (style)); | |
131 this.parent = parent; | |
132 createWidget (); | |
133 } | |
134 | |
135 /** | |
136 * Adds the listener to the collection of listeners who will | |
137 * be notified when the user changes the receiver's value, by sending | |
138 * it one of the messages defined in the <code>SelectionListener</code> | |
139 * interface. | |
140 * <p> | |
141 * When <code>widgetSelected</code> is called, the event object detail field contains one of the following values: | |
142 * <code>SWT.NONE</code> - for the end of a drag. | |
143 * <code>SWT.DRAG</code>. | |
144 * <code>SWT.HOME</code>. | |
145 * <code>SWT.END</code>. | |
146 * <code>SWT.ARROW_DOWN</code>. | |
147 * <code>SWT.ARROW_UP</code>. | |
148 * <code>SWT.PAGE_DOWN</code>. | |
149 * <code>SWT.PAGE_UP</code>. | |
150 * <code>widgetDefaultSelected</code> is not called. | |
151 * </p> | |
152 * | |
153 * @param listener the listener which should be notified when the user changes the receiver's value | |
154 * | |
155 * @exception IllegalArgumentException <ul> | |
156 * <li>ERROR_NULL_ARGUMENT - if the listener is null</li> | |
157 * </ul> | |
158 * @exception SWTException <ul> | |
159 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
160 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
161 * </ul> | |
162 * | |
163 * @see SelectionListener | |
164 * @see #removeSelectionListener | |
165 * @see SelectionEvent | |
166 */ | |
167 public void addSelectionListener (SelectionListener listener) { | |
168 checkWidget(); | |
169 if (listener is null) error (SWT.ERROR_NULL_ARGUMENT); | |
170 TypedListener typedListener = new TypedListener(listener); | |
171 addListener (SWT.Selection,typedListener); | |
172 addListener (SWT.DefaultSelection,typedListener); | |
173 } | |
174 | |
175 static int checkStyle (int style) { | |
176 return checkBits (style, SWT.HORIZONTAL, SWT.VERTICAL, 0, 0, 0, 0); | |
177 } | |
178 | |
179 void createWidget () { | |
180 increment = 1; | |
181 pageIncrement = 10; | |
182 /* | |
183 * Do not set the initial values of the maximum | |
184 * or the thumb. These values normally default | |
185 * to 100 and 10 but may have been set already | |
186 * by the widget that owns the scroll bar. For | |
187 * example, a scroll bar that is created for a | |
188 * list widget, setting these defaults would | |
189 * override the initial values provided by the | |
190 * list widget. | |
191 */ | |
192 } | |
193 | |
194 override void destroyWidget () { | |
195 auto hwnd = hwndScrollBar (); | |
196 auto type = scrollBarType (); | |
197 static if (OS.IsWinCE) { | |
198 SCROLLINFO info; | |
199 info.cbSize = SCROLLINFO.sizeof; | |
200 info.fMask = OS.SIF_RANGE | OS.SIF_PAGE; | |
201 info.nPage = 101; | |
202 info.nMax = 100; | |
203 info.nMin = 0; | |
204 OS.SetScrollInfo (hwnd, type, &info, true); | |
205 } else { | |
206 OS.ShowScrollBar (hwnd, type, false); | |
207 } | |
208 parent.destroyScrollBar (style); | |
209 releaseHandle (); | |
210 //This code is intentionally commented | |
211 //parent.sendEvent (SWT.Resize); | |
212 } | |
213 | |
214 Rectangle getBounds () { | |
215 // checkWidget (); | |
216 parent.forceResize (); | |
217 RECT rect; | |
218 OS.GetClientRect (parent.scrolledHandle (), &rect); | |
219 int x = 0, y = 0, width, height; | |
220 if ((style & SWT.HORIZONTAL) !is 0) { | |
221 y = rect.bottom - rect.top; | |
222 width = rect.right - rect.left; | |
223 height = OS.GetSystemMetrics (OS.SM_CYHSCROLL); | |
224 } else { | |
225 x = rect.right - rect.left; | |
226 width = OS.GetSystemMetrics (OS.SM_CXVSCROLL); | |
227 height = rect.bottom - rect.top; | |
228 } | |
229 return new Rectangle (x, y, width, height); | |
230 } | |
231 | |
232 /** | |
233 * Returns <code>true</code> if the receiver is enabled, and | |
234 * <code>false</code> otherwise. A disabled control is typically | |
235 * not selectable from the user interface and draws with an | |
236 * inactive or "grayed" look. | |
237 * | |
238 * @return the receiver's enabled state | |
239 * | |
240 * @exception SWTException <ul> | |
241 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
242 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
243 * </ul> | |
244 * | |
245 * @see #isEnabled | |
246 */ | |
247 public bool getEnabled () { | |
248 checkWidget(); | |
249 return (state & DISABLED) is 0; | |
250 } | |
251 | |
252 /** | |
253 * Returns the amount that the receiver's value will be | |
254 * modified by when the up/down (or right/left) arrows | |
255 * are pressed. | |
256 * | |
257 * @return the increment | |
258 * | |
259 * @exception SWTException <ul> | |
260 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
261 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
262 * </ul> | |
263 */ | |
264 public int getIncrement () { | |
265 checkWidget(); | |
266 return increment; | |
267 } | |
268 | |
269 /** | |
270 * Returns the maximum value which the receiver will allow. | |
271 * | |
272 * @return the maximum | |
273 * | |
274 * @exception SWTException <ul> | |
275 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
276 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
277 * </ul> | |
278 */ | |
279 public int getMaximum () { | |
280 checkWidget(); | |
281 SCROLLINFO info; | |
282 info.cbSize = SCROLLINFO.sizeof; | |
283 info.fMask = OS.SIF_RANGE; | |
284 auto hwnd = hwndScrollBar (); | |
285 auto type = scrollBarType (); | |
286 OS.GetScrollInfo (hwnd, type, &info); | |
287 return info.nMax; | |
288 } | |
289 | |
290 /** | |
291 * Returns the minimum value which the receiver will allow. | |
292 * | |
293 * @return the minimum | |
294 * | |
295 * @exception SWTException <ul> | |
296 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
297 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
298 * </ul> | |
299 */ | |
300 public int getMinimum () { | |
301 checkWidget(); | |
302 SCROLLINFO info; | |
303 info.cbSize = SCROLLINFO.sizeof; | |
304 info.fMask = OS.SIF_RANGE; | |
305 auto hwnd = hwndScrollBar (); | |
306 auto type = scrollBarType (); | |
307 OS.GetScrollInfo (hwnd, type, &info); | |
308 return info.nMin; | |
309 } | |
310 | |
311 /** | |
312 * Returns the amount that the receiver's value will be | |
313 * modified by when the page increment/decrement areas | |
314 * are selected. | |
315 * | |
316 * @return the page increment | |
317 * | |
318 * @exception SWTException <ul> | |
319 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
320 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
321 * </ul> | |
322 */ | |
323 public int getPageIncrement () { | |
324 checkWidget(); | |
325 return pageIncrement; | |
326 } | |
327 | |
328 /** | |
329 * Returns the receiver's parent, which must be a Scrollable. | |
330 * | |
331 * @return the receiver's parent | |
332 * | |
333 * @exception SWTException <ul> | |
334 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
335 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
336 * </ul> | |
337 */ | |
338 public Scrollable getParent () { | |
339 checkWidget(); | |
340 return parent; | |
341 } | |
342 | |
343 /** | |
344 * Returns the single 'selection' that is the receiver's value. | |
345 * | |
346 * @return the selection | |
347 * | |
348 * @exception SWTException <ul> | |
349 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
350 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
351 * </ul> | |
352 */ | |
353 public int getSelection () { | |
354 checkWidget(); | |
355 SCROLLINFO info; | |
356 info.cbSize = SCROLLINFO.sizeof; | |
357 info.fMask = OS.SIF_POS; | |
358 auto hwnd = hwndScrollBar (); | |
359 auto type = scrollBarType (); | |
360 OS.GetScrollInfo (hwnd, type, &info); | |
361 return info.nPos; | |
362 } | |
363 | |
364 /** | |
365 * Returns a point describing the receiver's size. The | |
366 * x coordinate of the result is the width of the receiver. | |
367 * The y coordinate of the result is the height of the | |
368 * receiver. | |
369 * | |
370 * @return the receiver's size | |
371 * | |
372 * @exception SWTException <ul> | |
373 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
374 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
375 * </ul> | |
376 */ | |
377 public Point getSize () { | |
378 checkWidget(); | |
379 parent.forceResize (); | |
380 RECT rect; | |
381 OS.GetClientRect (parent.scrolledHandle (), &rect); | |
382 int width, height; | |
383 if ((style & SWT.HORIZONTAL) !is 0) { | |
384 width = rect.right - rect.left; | |
385 height = OS.GetSystemMetrics (OS.SM_CYHSCROLL); | |
386 } else { | |
387 width = OS.GetSystemMetrics (OS.SM_CXVSCROLL); | |
388 height = rect.bottom - rect.top; | |
389 } | |
390 return new Point (width, height); | |
391 } | |
392 | |
393 /** | |
394 * Returns the size of the receiver's thumb relative to the | |
395 * difference between its maximum and minimum values. | |
396 * | |
397 * @return the thumb value | |
398 * | |
399 * @exception SWTException <ul> | |
400 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
401 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
402 * </ul> | |
403 * | |
404 * @see ScrollBar | |
405 */ | |
406 public int getThumb () { | |
407 checkWidget(); | |
408 SCROLLINFO info; | |
409 info.cbSize = SCROLLINFO.sizeof; | |
410 info.fMask = OS.SIF_PAGE; | |
411 auto hwnd = hwndScrollBar (); | |
412 auto type = scrollBarType (); | |
413 OS.GetScrollInfo (hwnd, type, &info); | |
414 if (info.nPage !is 0) --info.nPage; | |
415 return info.nPage; | |
416 } | |
417 | |
418 /** | |
419 * Returns <code>true</code> if the receiver is visible, and | |
420 * <code>false</code> otherwise. | |
421 * <p> | |
422 * If one of the receiver's ancestors is not visible or some | |
423 * other condition makes the receiver not visible, this method | |
424 * may still indicate that it is considered visible even though | |
425 * it may not actually be showing. | |
426 * </p> | |
427 * | |
428 * @return the receiver's visibility state | |
429 * | |
430 * @exception SWTException <ul> | |
431 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
432 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
433 * </ul> | |
434 */ | |
435 public bool getVisible () { | |
436 checkWidget(); | |
437 if (!OS.IsWinCE && OS.WIN32_VERSION >= OS.VERSION(4, 10)) { | |
438 SCROLLBARINFO psbi; | |
439 psbi.cbSize = SCROLLBARINFO.sizeof; | |
440 int idObject = (style & SWT.VERTICAL) !is 0 ? OS.OBJID_VSCROLL : OS.OBJID_HSCROLL; | |
441 OS.GetScrollBarInfo (hwndScrollBar (), idObject, &psbi); | |
442 return (psbi.rgstate [0] & OS.STATE_SYSTEM_INVISIBLE) is 0; | |
443 } | |
444 return (state & HIDDEN) is 0; | |
445 } | |
446 | |
447 HWND hwndScrollBar () { | |
448 return parent.scrolledHandle (); | |
449 } | |
450 | |
451 /** | |
452 * Returns <code>true</code> if the receiver is enabled and all | |
453 * of the receiver's ancestors are enabled, and <code>false</code> | |
454 * otherwise. A disabled control is typically not selectable from the | |
455 * user interface and draws with an inactive or "grayed" look. | |
456 * | |
457 * @return the receiver's enabled state | |
458 * | |
459 * @exception SWTException <ul> | |
460 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
461 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
462 * </ul> | |
463 * | |
464 * @see #getEnabled | |
465 */ | |
466 public bool isEnabled () { | |
467 checkWidget(); | |
468 return getEnabled () && parent.isEnabled (); | |
469 } | |
470 | |
471 /** | |
472 * Returns <code>true</code> if the receiver is visible and all | |
473 * of the receiver's ancestors are visible and <code>false</code> | |
474 * otherwise. | |
475 * | |
476 * @return the receiver's visibility state | |
477 * | |
478 * @exception SWTException <ul> | |
479 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
480 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
481 * </ul> | |
482 * | |
483 * @see #getVisible | |
484 */ | |
485 public bool isVisible () { | |
486 checkWidget(); | |
487 return getVisible () && parent.isVisible (); | |
488 } | |
489 | |
490 override void releaseHandle () { | |
491 super.releaseHandle (); | |
492 parent = null; | |
493 } | |
494 | |
495 override void releaseParent () { | |
496 super.releaseParent (); | |
497 if (parent.horizontalBar is this) parent.horizontalBar = null; | |
498 if (parent.verticalBar is this) parent.verticalBar = null; | |
499 } | |
500 | |
501 /** | |
502 * Removes the listener from the collection of listeners who will | |
503 * be notified when the user changes the receiver's value. | |
504 * | |
505 * @param listener the listener which should no longer be notified | |
506 * | |
507 * @exception IllegalArgumentException <ul> | |
508 * <li>ERROR_NULL_ARGUMENT - if the listener is null</li> | |
509 * </ul> | |
510 * @exception SWTException <ul> | |
511 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
512 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
513 * </ul> | |
514 * | |
515 * @see SelectionListener | |
516 * @see #addSelectionListener | |
517 */ | |
518 public void removeSelectionListener (SelectionListener listener) { | |
519 checkWidget(); | |
520 if (listener is null) error (SWT.ERROR_NULL_ARGUMENT); | |
521 if (eventTable is null) return; | |
522 eventTable.unhook (SWT.Selection, listener); | |
523 eventTable.unhook (SWT.DefaultSelection,listener); | |
524 } | |
525 | |
526 int scrollBarType () { | |
527 return (style & SWT.VERTICAL) !is 0 ? OS.SB_VERT : OS.SB_HORZ; | |
528 } | |
529 | |
530 /** | |
531 * Enables the receiver if the argument is <code>true</code>, | |
532 * and disables it otherwise. A disabled control is typically | |
533 * not selectable from the user interface and draws with an | |
534 * inactive or "grayed" look. | |
535 * | |
536 * @param enabled the new enabled state | |
537 * | |
538 * @exception SWTException <ul> | |
539 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
540 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
541 * </ul> | |
542 */ | |
543 public void setEnabled (bool enabled) { | |
544 checkWidget(); | |
545 /* | |
546 * This line is intentionally commented. Currently | |
547 * always show scrollbar as being enabled and visible. | |
548 */ | |
549 // if (OS.IsWinCE) error (SWT.ERROR_NOT_IMPLEMENTED); | |
550 static if (!OS.IsWinCE) { | |
551 auto hwnd = hwndScrollBar (); | |
552 auto type = scrollBarType (); | |
553 int flags = enabled ? OS.ESB_ENABLE_BOTH : OS.ESB_DISABLE_BOTH; | |
554 OS.EnableScrollBar (hwnd, type, flags); | |
555 if (enabled) { | |
556 state &= ~DISABLED; | |
557 } else { | |
558 state |= DISABLED; | |
559 } | |
560 } | |
561 } | |
562 | |
563 /** | |
564 * Sets the amount that the receiver's value will be | |
565 * modified by when the up/down (or right/left) arrows | |
566 * are pressed to the argument, which must be at least | |
567 * one. | |
568 * | |
569 * @param value the new increment (must be greater than zero) | |
570 * | |
571 * @exception SWTException <ul> | |
572 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
573 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
574 * </ul> | |
575 */ | |
576 public void setIncrement (int value) { | |
577 checkWidget(); | |
578 if (value < 1) return; | |
579 increment = value; | |
580 } | |
581 | |
582 /** | |
583 * Sets the maximum. If this value is negative or less than or | |
584 * equal to the minimum, the value is ignored. If necessary, first | |
585 * the thumb and then the selection are adjusted to fit within the | |
586 * new range. | |
587 * | |
588 * @param value the new maximum | |
589 * | |
590 * @exception SWTException <ul> | |
591 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
592 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
593 * </ul> | |
594 */ | |
595 public void setMaximum (int value) { | |
596 checkWidget(); | |
597 if (value < 0) return; | |
598 SCROLLINFO info; | |
599 info.cbSize = SCROLLINFO.sizeof; | |
600 auto hwnd = hwndScrollBar (); | |
601 auto type = scrollBarType (); | |
602 info.fMask = OS.SIF_RANGE | OS.SIF_DISABLENOSCROLL; | |
603 OS.GetScrollInfo (hwnd, type, &info); | |
604 if (value - info.nMin - info.nPage < 1) return; | |
605 info.nMax = value; | |
606 SetScrollInfo (hwnd, type, &info, true); | |
607 } | |
608 | |
609 /** | |
610 * Sets the minimum value. If this value is negative or greater | |
611 * than or equal to the maximum, the value is ignored. If necessary, | |
612 * first the thumb and then the selection are adjusted to fit within | |
613 * the new range. | |
614 * | |
615 * @param value the new minimum | |
616 * | |
617 * @exception SWTException <ul> | |
618 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
619 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
620 * </ul> | |
621 */ | |
622 public void setMinimum (int value) { | |
623 checkWidget(); | |
624 if (value < 0) return; | |
625 SCROLLINFO info; | |
626 info.cbSize = SCROLLINFO.sizeof; | |
627 auto hwnd = hwndScrollBar (); | |
628 auto type = scrollBarType (); | |
629 info.fMask = OS.SIF_RANGE | OS.SIF_DISABLENOSCROLL; | |
630 OS.GetScrollInfo (hwnd, type, &info); | |
631 if (info.nMax - value - info.nPage < 1) return; | |
632 info.nMin = value; | |
633 SetScrollInfo (hwnd, type, &info, true); | |
634 } | |
635 | |
636 /** | |
637 * Sets the amount that the receiver's value will be | |
638 * modified by when the page increment/decrement areas | |
639 * are selected to the argument, which must be at least | |
640 * one. | |
641 * | |
642 * @param value the page increment (must be greater than zero) | |
643 * | |
644 * @exception SWTException <ul> | |
645 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
646 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
647 * </ul> | |
648 */ | |
649 public void setPageIncrement (int value) { | |
650 checkWidget(); | |
651 if (value < 1) return; | |
652 pageIncrement = value; | |
653 } | |
654 | |
655 bool SetScrollInfo (HWND hwnd, int flags, SCROLLINFO* info, bool fRedraw) { | |
656 /* | |
657 * Bug in Windows. For some reason, when SetScrollInfo() | |
658 * is used with SIF_POS and the scroll bar is hidden, | |
659 * the opposite scroll bar is incorrectly made visible | |
660 * so that the next time the parent is resized (or another | |
661 * scroll bar operation is performed), the opposite scroll | |
662 * bar draws. The fix is to hide both scroll bars. | |
663 */ | |
664 bool barVisible = false; | |
665 bool visible = getVisible (); | |
666 | |
667 /* | |
668 * This line is intentionally commented. Currently | |
669 * always show scrollbar as being enabled and visible. | |
670 */ | |
671 // if (OS.IsWinCE) error (SWT.ERROR_NOT_IMPLEMENTED); | |
672 ScrollBar bar = null; | |
673 if (!OS.IsWinCE) { | |
674 switch (flags) { | |
675 case OS.SB_HORZ: | |
676 bar = parent.getVerticalBar (); | |
677 break; | |
678 case OS.SB_VERT: | |
679 bar = parent.getHorizontalBar (); | |
680 break; | |
681 default: | |
682 } | |
683 barVisible = bar !is null && bar.getVisible (); | |
684 } | |
685 if (!visible || (state & DISABLED) !is 0) fRedraw = false; | |
686 bool result = cast(bool) OS.SetScrollInfo (hwnd, flags, info, fRedraw); | |
687 | |
688 /* | |
689 * Bug in Windows. For some reason, when the widget | |
690 * is a standard scroll bar, and SetScrollInfo() is | |
691 * called with SIF_RANGE or SIF_PAGE, the widget is | |
692 * incorrectly made visible so that the next time the | |
693 * parent is resized (or another scroll bar operation | |
694 * is performed), the scroll bar draws. The fix is | |
695 * to hide the scroll bar (again) when already hidden. | |
696 */ | |
697 if (!visible) { | |
698 /* | |
699 * This line is intentionally commented. Currently | |
700 * always show scrollbar as being enabled and visible. | |
701 */ | |
702 // if (OS.IsWinCE) error (SWT.ERROR_NOT_IMPLEMENTED); | |
703 if (!OS.IsWinCE) { | |
704 OS.ShowScrollBar (hwnd, !barVisible ? OS.SB_BOTH : flags, false); | |
705 } | |
706 } | |
707 | |
708 /* | |
709 * Bug in Windows. When only one scroll bar is visible, | |
710 * and the thumb changes using SIF_RANGE or SIF_PAGE | |
711 * from being visible to hidden, the opposite scroll | |
712 * bar is incorrectly made visible. The next time the | |
713 * parent is resized (or another scroll bar operation | |
714 * is performed), the opposite scroll bar draws. The | |
715 * fix is to hide the opposite scroll bar again. | |
716 * | |
717 * NOTE: This problem only happens on Vista | |
718 */ | |
719 if (!OS.IsWinCE && OS.WIN32_VERSION >= OS.VERSION (6, 0)) { | |
720 if (visible && bar !is null && !barVisible) { | |
721 OS.ShowScrollBar (hwnd, flags is OS.SB_HORZ ? OS.SB_VERT : OS.SB_HORZ, false); | |
722 } | |
723 } | |
724 | |
725 /* | |
726 * Feature in Windows. Using SIF_DISABLENOSCROLL, | |
727 * SetScrollInfo () can change enabled and disabled | |
728 * state of the scroll bar causing a scroll bar that | |
729 * was disabled by the application to become enabled. | |
730 * The fix is to disable the scroll bar (again) when | |
731 * the application has disabled the scroll bar. | |
732 */ | |
733 if ((state & DISABLED) !is 0) { | |
734 /* | |
735 * This line is intentionally commented. Currently | |
736 * always show scrollbar as being enabled and visible. | |
737 */ | |
738 // if (OS.IsWinCE) error (SWT.ERROR_NOT_IMPLEMENTED); | |
739 if (!OS.IsWinCE) { | |
740 OS.EnableScrollBar (hwnd, flags, OS.ESB_DISABLE_BOTH); | |
741 } | |
742 } | |
743 return result; | |
744 } | |
745 | |
746 /** | |
747 * Sets the single <em>selection</em> that is the receiver's | |
748 * value to the argument which must be greater than or equal | |
749 * to zero. | |
750 * | |
751 * @param selection the new selection (must be zero or greater) | |
752 * | |
753 * @exception SWTException <ul> | |
754 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
755 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
756 * </ul> | |
757 */ | |
758 public void setSelection (int selection) { | |
759 checkWidget(); | |
760 SCROLLINFO info; | |
761 info.cbSize = SCROLLINFO.sizeof; | |
762 auto hwnd = hwndScrollBar (); | |
763 auto type = scrollBarType (); | |
764 info.fMask = OS.SIF_POS; | |
765 info.nPos = selection; | |
766 SetScrollInfo (hwnd, type, &info, true); | |
767 } | |
768 | |
769 /** | |
770 * Sets the size of the receiver's thumb relative to the | |
771 * difference between its maximum and minimum values. This new | |
772 * value will be ignored if it is less than one, and will be | |
773 * clamped if it exceeds the receiver's current range. | |
774 * | |
775 * @param value the new thumb value, which must be at least one and not | |
776 * larger than the size of the current range | |
777 * | |
778 * @exception SWTException <ul> | |
779 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
780 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
781 * </ul> | |
782 */ | |
783 public void setThumb (int value) { | |
784 checkWidget(); | |
785 if (value < 1) return; | |
786 SCROLLINFO info; | |
787 info.cbSize = SCROLLINFO.sizeof; | |
788 auto hwnd = hwndScrollBar (); | |
789 auto type = scrollBarType (); | |
790 info.fMask = OS.SIF_PAGE | OS.SIF_RANGE | OS.SIF_DISABLENOSCROLL; | |
791 OS.GetScrollInfo (hwnd, type, &info); | |
792 info.nPage = value; | |
793 if (info.nPage !is 0) info.nPage++; | |
794 SetScrollInfo (hwnd, type, &info, true); | |
795 } | |
796 | |
797 /** | |
798 * Sets the receiver's selection, minimum value, maximum | |
799 * value, thumb, increment and page increment all at once. | |
800 * <p> | |
801 * Note: This is similar to setting the values individually | |
802 * using the appropriate methods, but may be implemented in a | |
803 * more efficient fashion on some platforms. | |
804 * </p> | |
805 * | |
806 * @param selection the new selection value | |
807 * @param minimum the new minimum value | |
808 * @param maximum the new maximum value | |
809 * @param thumb the new thumb value | |
810 * @param increment the new increment value | |
811 * @param pageIncrement the new pageIncrement value | |
812 * | |
813 * @exception SWTException <ul> | |
814 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
815 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
816 * </ul> | |
817 */ | |
818 public void setValues (int selection, int minimum, int maximum, int thumb, int increment, int pageIncrement) { | |
819 checkWidget(); | |
820 if (minimum < 0) return; | |
821 if (maximum < 0) return; | |
822 if (thumb < 1) return; | |
823 if (increment < 1) return; | |
824 if (pageIncrement < 1) return; | |
825 this.increment = increment; | |
826 this.pageIncrement = pageIncrement; | |
827 SCROLLINFO info; | |
828 info.cbSize = SCROLLINFO.sizeof; | |
829 info.fMask = OS.SIF_POS | OS.SIF_PAGE | OS.SIF_RANGE | OS.SIF_DISABLENOSCROLL; | |
830 info.nPos = selection; | |
831 info.nMin = minimum; | |
832 info.nMax = maximum; | |
833 info.nPage = thumb; | |
834 if (info.nPage !is 0) info.nPage++; | |
835 auto hwnd = hwndScrollBar (); | |
836 auto type = scrollBarType (); | |
837 SetScrollInfo (hwnd, type, &info, true); | |
838 } | |
839 | |
840 /** | |
841 * Marks the receiver as visible if the argument is <code>true</code>, | |
842 * and marks it invisible otherwise. | |
843 * <p> | |
844 * If one of the receiver's ancestors is not visible or some | |
845 * other condition makes the receiver not visible, marking | |
846 * it visible may not actually cause it to be displayed. | |
847 * </p> | |
848 * | |
849 * @param visible the new visibility state | |
850 * | |
851 * @exception SWTException <ul> | |
852 * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> | |
853 * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> | |
854 * </ul> | |
855 */ | |
856 public void setVisible (bool visible) { | |
857 checkWidget(); | |
858 if (visible is getVisible ()) return; | |
859 | |
860 /* | |
861 * On Windows CE, use SIF_DISABLENOSCROLL to show and | |
862 * hide the scroll bar when the page size is equal to | |
863 * the range. | |
864 */ | |
865 static if (OS.IsWinCE) { | |
866 SCROLLINFO info; | |
867 info.cbSize = SCROLLINFO.sizeof; | |
868 auto hwnd = hwndScrollBar (); | |
869 auto type = scrollBarType (); | |
870 info.fMask = OS.SIF_RANGE | OS.SIF_PAGE; | |
871 if (visible) info.fMask |= OS.SIF_DISABLENOSCROLL; | |
872 OS.GetScrollInfo (hwnd, type, &info); | |
873 if (info.nPage is info.nMax - info.nMin + 1) { | |
874 /* | |
875 * Bug in Windows. When the only changed flag to | |
876 * SetScrollInfo () is OS.SIF_DISABLENOSCROLL, | |
877 * Windows does not update the scroll bar state. | |
878 * The fix is to increase and then decrease the | |
879 * maximum, causing Windows to honour the flag. | |
880 */ | |
881 int max = info.nMax; | |
882 info.nMax++; | |
883 OS.SetScrollInfo (hwnd, type, &info, false); | |
884 info.nMax = max; | |
885 OS.SetScrollInfo (hwnd, type, &info, true); | |
886 } else { | |
887 /* | |
888 * This line is intentionally commented. Currently | |
889 * always show scrollbar as being enabled and visible. | |
890 */ | |
891 // if (OS.IsWinCE) error (SWT.ERROR_NOT_IMPLEMENTED); | |
892 } | |
893 return; | |
894 } | |
895 | |
896 /* | |
897 * Set the state bits before calling ShowScrollBar () | |
898 * because hiding and showing the scroll bar can cause | |
899 * WM_SIZE messages when the client area is resized. | |
900 * Setting the state before the call means that code | |
901 * that runs during WM_SIZE that queries the visibility | |
902 * of the scroll bar will get the correct value. | |
903 */ | |
904 state = visible ? state & ~HIDDEN : state | HIDDEN; | |
905 auto hwnd = hwndScrollBar (); | |
906 auto type = scrollBarType (); | |
907 if (OS.ShowScrollBar (hwnd, type, visible)) { | |
908 /* | |
909 * Bug in Windows. For some reason, when the widget | |
910 * is a standard scroll bar, and SetScrollInfo () is | |
911 * called with SIF_RANGE or SIF_PAGE while the widget | |
912 * is not visible, the widget is incorrectly disabled | |
913 * even though the values for SIF_RANGE and SIF_PAGE, | |
914 * when set for a visible scroll bar would not disable | |
915 * the scroll bar. The fix is to enable the scroll bar | |
916 * when not disabled by the application and the current | |
917 * scroll bar ranges would cause the scroll bar to be | |
918 * enabled had they been set when the scroll bar was | |
919 * visible. | |
920 */ | |
921 if ((state & DISABLED) is 0) { | |
922 SCROLLINFO info; | |
923 info.cbSize = SCROLLINFO.sizeof; | |
924 info.fMask = OS.SIF_RANGE | OS.SIF_PAGE; | |
925 OS.GetScrollInfo (hwnd, type, &info); | |
926 if (info.nMax - info.nMin - info.nPage >= 0) { | |
927 OS.EnableScrollBar (hwnd, type, OS.ESB_ENABLE_BOTH); | |
928 } | |
929 } | |
930 sendEvent (visible ? SWT.Show : SWT.Hide); | |
931 // widget could be disposed at this point | |
932 } | |
933 } | |
934 | |
935 LRESULT wmScrollChild (int /*long*/ wParam, int /*long*/ lParam) { | |
936 | |
937 /* Do nothing when scrolling is ending */ | |
938 int code = OS.LOWORD (wParam); | |
939 if (code is OS.SB_ENDSCROLL) return null; | |
940 | |
941 /* | |
942 * Send the event because WM_HSCROLL and | |
943 * WM_VSCROLL are sent from a modal message | |
944 * loop in Windows that is active when the | |
945 * user is scrolling. | |
946 */ | |
947 Event event = new Event (); | |
948 switch (code) { | |
949 case OS.SB_THUMBPOSITION: event.detail = SWT.NONE; break; | |
950 case OS.SB_THUMBTRACK: event.detail = SWT.DRAG; break; | |
951 case OS.SB_TOP: event.detail = SWT.HOME; break; | |
952 case OS.SB_BOTTOM: event.detail = SWT.END; break; | |
953 case OS.SB_LINEDOWN: event.detail = SWT.ARROW_DOWN; break; | |
954 case OS.SB_LINEUP: event.detail = SWT.ARROW_UP; break; | |
955 case OS.SB_PAGEDOWN: event.detail = SWT.PAGE_DOWN; break; | |
956 case OS.SB_PAGEUP: event.detail = SWT.PAGE_UP; break; | |
957 default: | |
958 } | |
959 sendEvent (SWT.Selection, event); | |
960 // the widget could be destroyed at this point | |
961 return null; | |
962 } | |
963 | |
964 } | |
965 |