diff options
author | Steve Northover <steve> | 2008-02-05 00:33:12 +0000 |
---|---|---|
committer | Steve Northover <steve> | 2008-02-05 00:33:12 +0000 |
commit | 30b3672ceb3d2c5d7c5e65c4765952fcea275186 (patch) | |
tree | 8d9266e9b39c2a8691a9b283c66b9ccc36c64317 | |
parent | 5a4ec706c1fb816c9cff4c4e7493b85db9b7b5b8 (diff) | |
download | eclipse.platform.swt-30b3672ceb3d2c5d7c5e65c4765952fcea275186.tar.gz eclipse.platform.swt-30b3672ceb3d2c5d7c5e65c4765952fcea275186.tar.xz eclipse.platform.swt-30b3672ceb3d2c5d7c5e65c4765952fcea275186.zip |
168807 - SWT.MeasureItem not used for selection hittest
-rwxr-xr-x | bundles/org.eclipse.swt/Eclipse SWT/win32/org/eclipse/swt/widgets/Table.java | 137 | ||||
-rwxr-xr-x | bundles/org.eclipse.swt/Eclipse SWT/win32/org/eclipse/swt/widgets/Tree.java | 85 |
2 files changed, 196 insertions, 26 deletions
diff --git a/bundles/org.eclipse.swt/Eclipse SWT/win32/org/eclipse/swt/widgets/Table.java b/bundles/org.eclipse.swt/Eclipse SWT/win32/org/eclipse/swt/widgets/Table.java index 7179b139b9..6c04c13772 100755 --- a/bundles/org.eclipse.swt/Eclipse SWT/win32/org/eclipse/swt/widgets/Table.java +++ b/bundles/org.eclipse.swt/Eclipse SWT/win32/org/eclipse/swt/widgets/Table.java @@ -74,7 +74,7 @@ public class Table extends Composite { TableColumn sortColumn; boolean ignoreCustomDraw, ignoreDrawForeground, ignoreDrawBackground, ignoreDrawFocus, ignoreDrawSelection, ignoreDrawHot; boolean customDraw, dragStarted, explorerTheme, firstColumnImage, fixScrollWidth, tipRequested, wasSelected, wasResized; - boolean ignoreActivate, ignoreSelect, ignoreShrink, ignoreResize, ignoreColumnMove, ignoreColumnResize; + boolean ignoreActivate, ignoreSelect, ignoreShrink, ignoreResize, ignoreColumnMove, ignoreColumnResize, fullRowSelect; int /*long*/ headerToolTipHandle; int itemHeight, lastIndexOf, lastWidth, sortDirection, resizeCount, selectionForeground, hotIndex; static /*final*/ int /*long*/ HeaderProc; @@ -2206,8 +2206,33 @@ public TableItem getItem (int index) { public TableItem getItem (Point point) { checkWidget (); if (point == null) error (SWT.ERROR_NULL_ARGUMENT); + int count = (int)/*64*/OS.SendMessage (handle, OS.LVM_GETITEMCOUNT, 0, 0); + if (count == 0) return null; LVHITTESTINFO pinfo = new LVHITTESTINFO (); - pinfo.x = point.x; pinfo.y = point.y; + pinfo.x = point.x; + pinfo.y = point.y; + if ((style & SWT.FULL_SELECTION) == 0) { + if (hooks (SWT.MeasureItem)) { + OS.SendMessage (handle, OS.LVM_SUBITEMHITTEST, 0, pinfo); + if (pinfo.iItem == -1) { + RECT rect = new RECT (); + rect.left = OS.LVIR_ICON; + ignoreCustomDraw = true; + int /*long*/ code = OS.SendMessage (handle, OS.LVM_GETITEMRECT, 0, rect); + ignoreCustomDraw = false; + if (code != 0) { + pinfo.x = rect.left; + OS.SendMessage (handle, OS.LVM_SUBITEMHITTEST, 0, pinfo); + } + } + if (pinfo.iItem != -1 && pinfo.iSubItem == 0) { + if (hitTestSelection (pinfo.iItem, pinfo.x, pinfo.y)) { + return _getItem (pinfo.iItem); + } + } + return null; + } + } OS.SendMessage (handle, OS.LVM_HITTEST, 0, pinfo); if (pinfo.iItem != -1) { /* @@ -2506,6 +2531,28 @@ boolean hasChildren () { return false; } +boolean hitTestSelection (int index, int x, int y) { + int count = (int)/*64*/OS.SendMessage (handle, OS.LVM_GETITEMCOUNT, 0, 0); + if (count == 0) return false; + if (!hooks (SWT.MeasureItem)) return false; + boolean result = false; + if (0 <= index && index < count) { + TableItem item = _getItem (index); + int /*long*/ hDC = OS.GetDC (handle); + int /*long*/ oldFont = 0, newFont = OS.SendMessage (handle, OS.WM_GETFONT, 0, 0); + if (newFont != 0) oldFont = OS.SelectObject (hDC, newFont); + int /*long*/ hFont = item.fontHandle (0); + if (hFont != -1) hFont = OS.SelectObject (hDC, hFont); + Event event = sendMeasureItemEvent (item, index, 0, hDC); + if (event.getBounds ().contains (x, y)) result = true; + if (hFont != -1) hFont = OS.SelectObject (hDC, hFont); + if (newFont != 0) OS.SelectObject (hDC, oldFont); + OS.ReleaseDC (handle, hDC); +// if (isDisposed () || item.isDisposed ()) return false; + } + return result; +} + int imageIndex (Image image, int column) { if (image == null) return OS.I_IMAGENONE; if (column == 0) { @@ -3326,6 +3373,15 @@ Event sendMeasureItemEvent (TableItem item, int row, int column, int /*long*/ hD } LRESULT sendMouseDownEvent (int type, int button, int msg, int /*long*/ wParam, int /*long*/ lParam) { + Display display = this.display; + display.captureChanged = false; + if (!sendMouseEvent (type, button, handle, msg, wParam, lParam)) { + if (!display.captureChanged && !isDisposed ()) { + if (OS.GetCapture () != handle) OS.SetCapture (handle); + } + return LRESULT.ZERO; + } + /* * Feature in Windows. Inside WM_LBUTTONDOWN and WM_RBUTTONDOWN, * the widget starts a modal loop to determine if the user wants @@ -3342,15 +3398,28 @@ LRESULT sendMouseDownEvent (int type, int button, int msg, int /*long*/ wParam, pinfo.x = OS.GET_X_LPARAM (lParam); pinfo.y = OS.GET_Y_LPARAM (lParam); OS.SendMessage (handle, OS.LVM_HITTEST, 0, pinfo); - Display display = this.display; - display.captureChanged = false; - if (!sendMouseEvent (type, button, handle, msg, wParam, lParam)) { - if (!display.captureChanged && !isDisposed ()) { - if (OS.GetCapture () != handle) OS.SetCapture (handle); + if ((style & SWT.FULL_SELECTION) == 0) { + if (hooks (SWT.MeasureItem)) { + OS.SendMessage (handle, OS.LVM_SUBITEMHITTEST, 0, pinfo); + if (pinfo.iItem == -1) { + int count = (int)/*64*/OS.SendMessage (handle, OS.LVM_GETITEMCOUNT, 0, 0); + if (count != 0) { + RECT rect = new RECT (); + rect.left = OS.LVIR_ICON; + ignoreCustomDraw = true; + int /*long*/ code = OS.SendMessage (handle, OS.LVM_GETITEMRECT, 0, rect); + ignoreCustomDraw = false; + if (code != 0) { + pinfo.x = rect.left; + OS.SendMessage (handle, OS.LVM_SUBITEMHITTEST, 0, pinfo); + } + } + } else { + if (pinfo.iSubItem != 0) pinfo.iItem = -1; + } } - return LRESULT.ZERO; } - + /* * Force the table to have focus so that when the user * reselects the focus item, the LVIS_FOCUSED state bits @@ -3398,6 +3467,17 @@ LRESULT sendMouseDownEvent (int type, int button, int msg, int /*long*/ wParam, forceSelect = true; } } + + /* Determine whether the user has selected an item based on SWT.MeasureItem */ + fullRowSelect = false; + if (pinfo.iItem != -1) { + if ((style & SWT.FULL_SELECTION) == 0) { + if (hooks (SWT.MeasureItem)) { + fullRowSelect = hitTestSelection (pinfo.iItem, pinfo.x, pinfo.y); + } + } + } + /* * Feature in Windows. Inside WM_LBUTTONDOWN and WM_RBUTTONDOWN, * the widget starts a modal loop to determine if the user wants @@ -3410,10 +3490,28 @@ LRESULT sendMouseDownEvent (int type, int button, int msg, int /*long*/ wParam, if (!dragDetect) { int flags = OS.LVHT_ONITEMICON | OS.LVHT_ONITEMLABEL; dragDetect = pinfo.iItem == -1 || (pinfo.flags & flags) == 0; + if (fullRowSelect) dragDetect = true; + } + + /* + * Temporarily set LVS_EX_FULLROWSELECT to allow drag and drop + * and the mouse to manipulate items based on the results of + * the SWT.MeasureItem event. + */ + if (fullRowSelect) { + OS.UpdateWindow (handle); + OS.DefWindowProc (handle, OS.WM_SETREDRAW, 0, 0); + OS.SendMessage (handle, OS.LVM_SETEXTENDEDLISTVIEWSTYLE, OS.LVS_EX_FULLROWSELECT, OS.LVS_EX_FULLROWSELECT); } if (!dragDetect) display.runDragDrop = false; int /*long*/ code = callWindowProc (handle, msg, wParam, lParam, forceSelect); if (!dragDetect) display.runDragDrop = true; + if (fullRowSelect) { + fullRowSelect = false; + OS.DefWindowProc (handle, OS.WM_SETREDRAW, 1, 0); + OS.SendMessage (handle, OS.LVM_SETEXTENDEDLISTVIEWSTYLE, OS.LVS_EX_FULLROWSELECT, 0); + } + if (dragStarted || !dragDetect) { if (!display.captureChanged && !isDisposed ()) { if (OS.GetCapture () != handle) OS.SetCapture (handle); @@ -5079,6 +5177,22 @@ int /*long*/ windowProc () { } int /*long*/ windowProc (int /*long*/ hwnd, int msg, int /*long*/ wParam, int /*long*/ lParam) { + +// //#define WM_STYLECHANGING 0x007C #define WM_STYLECHANGED +// if (msg == 0x007C) { +// System.out.println("WM_STYLECHANGING"); +// } +// if (msg == 0x007D) { +// System.out.println("WM_STYLECHANGED"); +// } + +// if (F) { +// System.out.println("0x" + Integer.toHexString(msg)); +// if (msg == OS.LVM_GETITEMRECT) { +// System.out.println("LVM_GETITEMRECT"); +// } +// } + if (handle == 0) return 0; if (hwnd != handle) { switch (msg) { @@ -6107,6 +6221,11 @@ LRESULT wmNotifyChild (NMHDR hdr, int /*long*/ wParam, int /*long*/ lParam) { break; } case OS.LVN_ITEMCHANGED: { + if (fullRowSelect) { + fullRowSelect = false; + OS.DefWindowProc (handle, OS.WM_SETREDRAW, 1, 0); + OS.SendMessage (handle, OS.LVM_SETEXTENDEDLISTVIEWSTYLE, OS.LVS_EX_FULLROWSELECT, 0); + } if (!ignoreSelect) { NMLISTVIEW pnmlv = new NMLISTVIEW (); OS.MoveMemory (pnmlv, lParam, NMLISTVIEW.sizeof); diff --git a/bundles/org.eclipse.swt/Eclipse SWT/win32/org/eclipse/swt/widgets/Tree.java b/bundles/org.eclipse.swt/Eclipse SWT/win32/org/eclipse/swt/widgets/Tree.java index 396c16a72a..c94048df2c 100755 --- a/bundles/org.eclipse.swt/Eclipse SWT/win32/org/eclipse/swt/widgets/Tree.java +++ b/bundles/org.eclipse.swt/Eclipse SWT/win32/org/eclipse/swt/widgets/Tree.java @@ -3085,10 +3085,15 @@ public TreeItem getItem (Point point) { int flags = OS.TVHT_ONITEM; if ((style & SWT.FULL_SELECTION) != 0) { flags |= OS.TVHT_ONITEMRIGHT | OS.TVHT_ONITEMINDENT; + } else { + if (hooks (SWT.MeasureItem)) { + lpht.flags &= ~(OS.TVHT_ONITEMICON | OS.TVHT_ONITEMLABEL); + if (hitTestSelection (lpht.hItem, lpht.x, lpht.y)) { + lpht.flags |= OS.TVHT_ONITEMICON | OS.TVHT_ONITEMLABEL; + } + } } - if ((lpht.flags & flags) != 0) { - return _getItem (lpht.hItem); - } + if ((lpht.flags & flags) != 0) return _getItem (lpht.hItem); } return null; } @@ -3519,6 +3524,30 @@ public TreeItem getTopItem () { return hItem != 0 ? _getItem (hItem) : null; } +boolean hitTestSelection (int /*long*/ hItem, int x, int y) { + if (hItem == 0) return false; + TreeItem item = _getItem (hItem); + if (item == null) return false; + if (!hooks (SWT.MeasureItem)) return false; + boolean result = false; + + //BUG? - moved columns, only hittest first column + //BUG? - check drag detect + int [] order = new int [1], index = new int [1]; + + int /*long*/ hDC = OS.GetDC (handle); + int /*long*/ oldFont = 0, newFont = OS.SendMessage (handle, OS.WM_GETFONT, 0, 0); + if (newFont != 0) oldFont = OS.SelectObject (hDC, newFont); + int /*long*/ hFont = item.fontHandle (order [index [0]]); + if (hFont != -1) hFont = OS.SelectObject (hDC, hFont); + Event event = sendMeasureItemEvent (item, order [index [0]], hDC); + if (event.getBounds ().contains (x, y)) result = true; + if (newFont != 0) OS.SelectObject (hDC, oldFont); + OS.ReleaseDC (handle, hDC); +// if (isDisposed () || item.isDisposed ()) return false; + return result; +} + int imageIndex (Image image, int index) { if (image == null) return OS.I_IMAGENONE; if (imageList == null) { @@ -5992,6 +6021,13 @@ LRESULT WM_LBUTTONDBLCLK (int /*long*/ wParam, int /*long*/ lParam) { int flags = OS.TVHT_ONITEM; if ((style & SWT.FULL_SELECTION) != 0) { flags |= OS.TVHT_ONITEMRIGHT | OS.TVHT_ONITEMINDENT; + } else { + if (hooks (SWT.MeasureItem)) { + lpht.flags &= ~(OS.TVHT_ONITEMICON | OS.TVHT_ONITEMLABEL); + if (hitTestSelection (lpht.hItem, lpht.x, lpht.y)) { + lpht.flags |= OS.TVHT_ONITEMICON | OS.TVHT_ONITEMLABEL; + } + } } if ((lpht.flags & flags) != 0) { Event event = new Event (); @@ -6115,7 +6151,7 @@ LRESULT WM_LBUTTONDOWN (int /*long*/ wParam, int /*long*/ lParam) { /* Process the mouse when an item is not selected */ if ((style & SWT.FULL_SELECTION) == 0) { - if ((lpht.flags & OS.TVHT_ONITEM) == 0) { + if ((lpht.flags & OS.TVHT_ONITEM) == 0 && !hooks (SWT.MeasureItem)) { Display display = this.display; display.captureChanged = false; if (!sendMouseEvent (SWT.MouseDown, 1, handle, OS.WM_LBUTTONDOWN, wParam, lParam)) { @@ -6210,20 +6246,26 @@ LRESULT WM_LBUTTONDOWN (int /*long*/ wParam, int /*long*/ lParam) { * drawing on top of any custom drawing. The fix * is to emulate TVS_FULLROWSELECT. */ - if ((style & SWT.FULL_SELECTION) != 0) { - int bits = OS.GetWindowLong (handle, OS.GWL_STYLE); - if ((bits & OS.TVS_FULLROWSELECT) == 0) { - if (lpht.hItem != 0) { - if (hOldItem == 0 || (hNewItem == hOldItem && lpht.hItem != hOldItem)) { - OS.SendMessage (handle, OS.TVM_SELECTITEM, OS.TVGN_CARET, lpht.hItem); - hNewItem = OS.SendMessage (handle, OS.TVM_GETNEXTITEM, OS.TVGN_CARET, 0); - } - if (!dragStarted && (state & DRAG_DETECT) != 0 && hooks (SWT.DragDetect)) { - dragStarted = dragDetect (handle, lpht.x, lpht.y, false, null, null); - } + boolean fakeSelection = false; + if (lpht.hItem != 0) { + if ((style & SWT.FULL_SELECTION) != 0) { + int bits = OS.GetWindowLong (handle, OS.GWL_STYLE); + if ((bits & OS.TVS_FULLROWSELECT) == 0) fakeSelection = true; + } else { + if (hooks (SWT.MeasureItem)) { + if (hitTestSelection (lpht.hItem, lpht.x, lpht.y)) fakeSelection = true; } } } + if (fakeSelection) { + if (hOldItem == 0 || (hNewItem == hOldItem && lpht.hItem != hOldItem)) { + OS.SendMessage (handle, OS.TVM_SELECTITEM, OS.TVGN_CARET, lpht.hItem); + hNewItem = OS.SendMessage (handle, OS.TVM_GETNEXTITEM, OS.TVGN_CARET, 0); + } + if (!dragStarted && (state & DRAG_DETECT) != 0 && hooks (SWT.DragDetect)) { + dragStarted = dragDetect (handle, lpht.x, lpht.y, false, null, null); + } + } ignoreDeselect = ignoreSelect = false; hSelect = 0; if (dragStarted) { @@ -6459,8 +6501,16 @@ LRESULT WM_RBUTTONDOWN (int /*long*/ wParam, int /*long*/ lParam) { lpht.y = OS.GET_Y_LPARAM (lParam); OS.SendMessage (handle, OS.TVM_HITTEST, 0, lpht); if (lpht.hItem != 0) { - int flags = OS.TVHT_ONITEMICON | OS.TVHT_ONITEMLABEL; - if ((style & SWT.FULL_SELECTION) != 0 || (lpht.flags & flags) != 0) { + boolean fakeSelection = (style & SWT.FULL_SELECTION) != 0; + if (!fakeSelection) { + if (hooks (SWT.MeasureItem)) { + fakeSelection = hitTestSelection (lpht.hItem, lpht.x, lpht.y); + } else { + int flags = OS.TVHT_ONITEMICON | OS.TVHT_ONITEMLABEL; + fakeSelection = (lpht.flags & flags) != 0; + } + } + if (fakeSelection) { if ((wParam & (OS.MK_CONTROL | OS.MK_SHIFT)) == 0) { TVITEM tvItem = new TVITEM (); tvItem.mask = OS.TVIF_HANDLE | OS.TVIF_STATE; @@ -6922,6 +6972,7 @@ LRESULT wmNotifyChild (NMHDR hdr, int /*long*/ wParam, int /*long*/ lParam) { * avoid the operation by testing to see whether * the mouse was inside a tree item. */ + if (hooks (SWT.MeasureItem)) return LRESULT.ONE; if (hooks (SWT.DefaultSelection)) { POINT pt = new POINT (); int pos = OS.GetMessagePos (); |