Mercurial > projects > dwt-win
diff dwt/widgets/Sash.d @ 31:92c102dd64a3
Added all widgets modules as dummy. Most modules of accessible are equal to the linux version, except Accessible.
author | Frank Benoit <benoit@tionex.de> |
---|---|
date | Mon, 28 Jan 2008 04:47:28 +0100 |
parents | |
children | 0f25be5cbe6f |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/dwt/widgets/Sash.d Mon Jan 28 04:47:28 2008 +0100 @@ -0,0 +1,427 @@ +/******************************************************************************* + * Copyright (c) 2000, 2007 IBM Corporation and others. + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Eclipse Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/epl-v10.html + * + * Contributors: + * IBM Corporation - initial API and implementation + *******************************************************************************/ +module dwt.widgets.Sash; + +import dwt.widgets.Control; +class Sash : Control { +} +/++ +import dwt.DWT; +import dwt.DWTException; +import dwt.events.SelectionEvent; +import dwt.events.SelectionListener; +import dwt.graphics.Point; +import dwt.internal.win32.LRESULT; +import dwt.internal.win32.OS; +import dwt.internal.win32.POINT; +import dwt.internal.win32.RECT; +import dwt.internal.win32.TCHAR; + +/** + * Instances of the receiver represent a selectable user interface object + * that allows the user to drag a rubber banded outline of the sash within + * the parent control. + * <dl> + * <dt><b>Styles:</b></dt> + * <dd>HORIZONTAL, VERTICAL, SMOOTH</dd> + * <dt><b>Events:</b></dt> + * <dd>Selection</dd> + * </dl> + * <p> + * Note: Only one of the styles HORIZONTAL and VERTICAL may be specified. + * </p><p> + * IMPORTANT: This class is intended to be subclassed <em>only</em> + * within the DWT implementation. + * </p> + */ +public class Sash extends Control { + bool dragging; + int startX, startY, lastX, lastY; + final static int INCREMENT = 1; + final static int PAGE_INCREMENT = 9; + +/** + * Constructs a new instance of this class given its parent + * and a style value describing its behavior and appearance. + * <p> + * The style value is either one of the style constants defined in + * class <code>DWT</code> which is applicable to instances of this + * class, or must be built by <em>bitwise OR</em>'ing together + * (that is, using the <code>int</code> "|" operator) two or more + * of those <code>DWT</code> style constants. The class description + * lists the style constants that are applicable to the class. + * Style bits are also inherited from superclasses. + * </p> + * + * @param parent a composite control which will be the parent of the new instance (cannot be null) + * @param style the style of control to construct + * + * @exception IllegalArgumentException <ul> + * <li>ERROR_NULL_ARGUMENT - if the parent is null</li> + * </ul> + * @exception DWTException <ul> + * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the parent</li> + * <li>ERROR_INVALID_SUBCLASS - if this class is not an allowed subclass</li> + * </ul> + * + * @see DWT#HORIZONTAL + * @see DWT#VERTICAL + * @see Widget#checkSubclass + * @see Widget#getStyle + */ +public Sash (Composite parent, int style) { + super (parent, checkStyle (style)); +} + +/** + * Adds the listener to the collection of listeners who will + * be notified when the control is selected by the user, by sending + * it one of the messages defined in the <code>SelectionListener</code> + * interface. + * <p> + * When <code>widgetSelected</code> is called, the x, y, width, and height fields of the event object are valid. + * If the receiver is being dragged, the event object detail field contains the value <code>DWT.DRAG</code>. + * <code>widgetDefaultSelected</code> is not called. + * </p> + * + * @param listener the listener which should be notified when the control is selected by the user + * + * @exception IllegalArgumentException <ul> + * <li>ERROR_NULL_ARGUMENT - if the listener is null</li> + * </ul> + * @exception DWTException <ul> + * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> + * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> + * </ul> + * + * @see SelectionListener + * @see #removeSelectionListener + * @see SelectionEvent + */ +public void addSelectionListener (SelectionListener listener) { + checkWidget (); + if (listener is null) error (DWT.ERROR_NULL_ARGUMENT); + TypedListener typedListener = new TypedListener (listener); + addListener (DWT.Selection,typedListener); + addListener (DWT.DefaultSelection,typedListener); +} + +int callWindowProc (int hwnd, int msg, int wParam, int lParam) { + if (handle is 0) return 0; + return OS.DefWindowProc (hwnd, msg, wParam, lParam); +} + +void createHandle () { + super.createHandle (); + state |= THEME_BACKGROUND; +} + +static int checkStyle (int style) { + return checkBits (style, DWT.HORIZONTAL, DWT.VERTICAL, 0, 0, 0, 0); +} + +public Point computeSize (int wHint, int hHint, bool changed) { + checkWidget (); + int border = getBorderWidth (); + int width = border * 2, height = border * 2; + if ((style & DWT.HORIZONTAL) !is 0) { + width += DEFAULT_WIDTH; height += 3; + } else { + width += 3; height += DEFAULT_HEIGHT; + } + if (wHint !is DWT.DEFAULT) width = wHint + (border * 2); + if (hHint !is DWT.DEFAULT) height = hHint + (border * 2); + return new Point (width, height); +} + +void drawBand (int x, int y, int width, int height) { + if ((style & DWT.SMOOTH) !is 0) return; + int hwndTrack = parent.handle; + byte [] bits = {-86, 0, 85, 0, -86, 0, 85, 0, -86, 0, 85, 0, -86, 0, 85, 0}; + int stippleBitmap = OS.CreateBitmap (8, 8, 1, 1, bits); + int stippleBrush = OS.CreatePatternBrush (stippleBitmap); + int hDC = OS.GetDCEx (hwndTrack, 0, OS.DCX_CACHE); + int oldBrush = OS.SelectObject (hDC, stippleBrush); + OS.PatBlt (hDC, x, y, width, height, OS.PATINVERT); + OS.SelectObject (hDC, oldBrush); + OS.ReleaseDC (hwndTrack, hDC); + OS.DeleteObject (stippleBrush); + OS.DeleteObject (stippleBitmap); +} + +/** + * Removes the listener from the collection of listeners who will + * be notified when the control is selected by the user. + * + * @param listener the listener which should no longer be notified + * + * @exception IllegalArgumentException <ul> + * <li>ERROR_NULL_ARGUMENT - if the listener is null</li> + * </ul> + * @exception DWTException <ul> + * <li>ERROR_WIDGET_DISPOSED - if the receiver has been disposed</li> + * <li>ERROR_THREAD_INVALID_ACCESS - if not called from the thread that created the receiver</li> + * </ul> + * + * @see SelectionListener + * @see #addSelectionListener + */ +public void removeSelectionListener(SelectionListener listener) { + checkWidget (); + if (listener is null) error (DWT.ERROR_NULL_ARGUMENT); + if (eventTable is null) return; + eventTable.unhook (DWT.Selection, listener); + eventTable.unhook (DWT.DefaultSelection,listener); +} + +TCHAR windowClass () { + return display.windowClass; +} + +int windowProc () { + return display.windowProc; +} + +LRESULT WM_ERASEBKGND (int wParam, int lParam) { + super.WM_ERASEBKGND (wParam, lParam); + drawBackground (wParam); + return LRESULT.ONE; +} + +LRESULT WM_KEYDOWN (int wParam, int lParam) { + LRESULT result = super.WM_KEYDOWN (wParam, lParam); + if (result !is null) return result; + switch (wParam) { + case OS.VK_LEFT: + case OS.VK_RIGHT: + case OS.VK_UP: + case OS.VK_DOWN: + + /* Calculate the new x or y position */ + if (OS.GetKeyState (OS.VK_LBUTTON) < 0) return result; + int step = OS.GetKeyState (OS.VK_CONTROL) < 0 ? INCREMENT : PAGE_INCREMENT; + POINT pt = new POINT (); + if ((style & DWT.VERTICAL) !is 0) { + if (wParam is OS.VK_UP || wParam is OS.VK_DOWN) break; + pt.x = wParam is OS.VK_LEFT ? -step : step; + } else { + if (wParam is OS.VK_LEFT || wParam is OS.VK_RIGHT) break; + pt.y = wParam is OS.VK_UP ? -step : step; + } + int hwndTrack = parent.handle; + OS.MapWindowPoints (handle, hwndTrack, pt, 1); + RECT rect = new RECT (), clientRect = new RECT (); + OS.GetWindowRect (handle, rect); + int width = rect.right - rect.left; + int height = rect.bottom - rect.top; + OS.GetClientRect (hwndTrack, clientRect); + int clientWidth = clientRect.right - clientRect.left; + int clientHeight = clientRect.bottom - clientRect.top; + int newX = lastX, newY = lastY; + if ((style & DWT.VERTICAL) !is 0) { + newX = Math.min (Math.max (0, pt.x - startX), clientWidth - width); + } else { + newY = Math.min (Math.max (0, pt.y - startY), clientHeight - height); + } + if (newX is lastX && newY is lastY) return result; + + /* Update the pointer position */ + POINT cursorPt = new POINT (); + cursorPt.x = pt.x; cursorPt.y = pt.y; + OS.ClientToScreen (hwndTrack, cursorPt); + if ((style & DWT.VERTICAL) !is 0) { + cursorPt.y += height / 2; + } + else { + cursorPt.x += width / 2; + } + OS.SetCursorPos (cursorPt.x, cursorPt.y); + + Event event = new Event (); + event.x = newX; + event.y = newY; + event.width = width; + event.height = height; + sendEvent (DWT.Selection, event); + if (isDisposed ()) return LRESULT.ZERO; + if (event.doit) { + if ((style & DWT.SMOOTH) !is 0) { + setBounds (event.x, event.y, width, height); + } + } + return result; + } + return result; +} + +LRESULT WM_GETDLGCODE (int wParam, int lParam) { + return new LRESULT (OS.DLGC_STATIC); +} + +LRESULT WM_LBUTTONDOWN (int wParam, int lParam) { + LRESULT result = super.WM_LBUTTONDOWN (wParam, lParam); + if (result is LRESULT.ZERO) return result; + + /* Compute the banding rectangle */ + int hwndTrack = parent.handle; + POINT pt = new POINT (); + pt.x = (short) (lParam & 0xFFFF); + pt.y = (short) (lParam >> 16); + RECT rect = new RECT (); + OS.GetWindowRect (handle, rect); + OS.MapWindowPoints (handle, 0, pt, 1); + startX = pt.x - rect.left; + startY = pt.y - rect.top; + OS.MapWindowPoints (0, hwndTrack, rect, 2); + lastX = rect.left; + lastY = rect.top; + int width = rect.right - rect.left; + int height = rect.bottom - rect.top; + + /* The event must be sent because doit flag is used */ + Event event = new Event (); + event.x = lastX; + event.y = lastY; + event.width = width; + event.height = height; + if ((style & DWT.SMOOTH) is 0) { + event.detail = DWT.DRAG; + } + sendEvent (DWT.Selection, event); + if (isDisposed ()) return LRESULT.ZERO; + + /* Draw the banding rectangle */ + if (event.doit) { + dragging = true; + lastX = event.x; + lastY = event.y; + menuShell ().bringToTop (); + if (isDisposed ()) return LRESULT.ZERO; + if (OS.IsWinCE) { + OS.UpdateWindow (hwndTrack); + } else { + int flags = OS.RDW_UPDATENOW | OS.RDW_ALLCHILDREN; + OS.RedrawWindow (hwndTrack, null, 0, flags); + } + drawBand (event.x, event.y, width, height); + if ((style & DWT.SMOOTH) !is 0) { + setBounds (event.x, event.y, width, height); + // widget could be disposed at this point + } + } + return result; +} + +LRESULT WM_LBUTTONUP (int wParam, int lParam) { + LRESULT result = super.WM_LBUTTONUP (wParam, lParam); + if (result is LRESULT.ZERO) return result; + + /* Compute the banding rectangle */ + if (!dragging) return result; + dragging = false; + RECT rect = new RECT (); + OS.GetWindowRect (handle, rect); + int width = rect.right - rect.left; + int height = rect.bottom - rect.top; + + /* The event must be sent because doit flag is used */ + Event event = new Event (); + event.x = lastX; + event.y = lastY; + event.width = width; + event.height = height; + drawBand (event.x, event.y, width, height); + sendEvent (DWT.Selection, event); + if (isDisposed ()) return result; + if (event.doit) { + if ((style & DWT.SMOOTH) !is 0) { + setBounds (event.x, event.y, width, height); + // widget could be disposed at this point + } + } + return result; +} + +LRESULT WM_MOUSEMOVE (int wParam, int lParam) { + LRESULT result = super.WM_MOUSEMOVE (wParam, lParam); + if (result !is null) return result; + if (!dragging || (wParam & OS.MK_LBUTTON) is 0) return result; + + /* Compute the banding rectangle */ + POINT pt = new POINT (); + pt.x = (short) (lParam & 0xFFFF); + pt.y = (short) (lParam >> 16); + int hwndTrack = parent.handle; + OS.MapWindowPoints (handle, hwndTrack, pt, 1); + RECT rect = new RECT (), clientRect = new RECT (); + OS.GetWindowRect (handle, rect); + int width = rect.right - rect.left; + int height = rect.bottom - rect.top; + OS.GetClientRect (hwndTrack, clientRect); + int newX = lastX, newY = lastY; + if ((style & DWT.VERTICAL) !is 0) { + int clientWidth = clientRect.right - clientRect.left; + newX = Math.min (Math.max (0, pt.x - startX), clientWidth - width); + } else { + int clientHeight = clientRect.bottom - clientRect.top; + newY = Math.min (Math.max (0, pt.y - startY), clientHeight - height); + } + if (newX is lastX && newY is lastY) return result; + drawBand (lastX, lastY, width, height); + + /* The event must be sent because doit flag is used */ + Event event = new Event (); + event.x = newX; + event.y = newY; + event.width = width; + event.height = height; + if ((style & DWT.SMOOTH) is 0) { + event.detail = DWT.DRAG; + } + sendEvent (DWT.Selection, event); + if (isDisposed ()) return LRESULT.ZERO; + if (event.doit) { + lastX = event.x; + lastY = event.y; + } + if (OS.IsWinCE) { + OS.UpdateWindow (hwndTrack); + } else { + int flags = OS.RDW_UPDATENOW | OS.RDW_ALLCHILDREN; + OS.RedrawWindow (hwndTrack, null, 0, flags); + } + drawBand (lastX, lastY, width, height); + if ((style & DWT.SMOOTH) !is 0) { + setBounds (lastX, lastY, width, height); + // widget could be disposed at this point + } + return result; +} + +LRESULT WM_SETCURSOR (int wParam, int lParam) { + LRESULT result = super.WM_SETCURSOR (wParam, lParam); + if (result !is null) return result; + int hitTest = lParam & 0xFFFF; + if (hitTest is OS.HTCLIENT) { + int hCursor = 0; + if ((style & DWT.HORIZONTAL) !is 0) { + hCursor = OS.LoadCursor (0, OS.IDC_SIZENS); + } else { + hCursor = OS.LoadCursor (0, OS.IDC_SIZEWE); + } + OS.SetCursor (hCursor); + return LRESULT.ONE; + } + return result; +} + +} +++/