diff options
5 files changed, 104 insertions, 46 deletions
diff --git a/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Control.java b/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Control.java index 67e539c01f..f1d1d8c23b 100644 --- a/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Control.java +++ b/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Control.java @@ -2660,10 +2660,14 @@ boolean dragDetect (int x, int y, boolean filter, boolean dragOnTimeout, boolean if (eventPtr == 0) return dragOnTimeout; switch (GDK.GDK_EVENT_TYPE (eventPtr)) { case GDK.GDK_MOTION_NOTIFY: { - GdkEventMotion gdkMotionEvent = new GdkEventMotion (); - OS.memmove (gdkMotionEvent, eventPtr, GdkEventMotion.sizeof); - if ((gdkMotionEvent.state & GDK.GDK_BUTTON1_MASK) != 0) { - if (GTK.gtk_drag_check_threshold (handle, x, y, (int) gdkMotionEvent.x, (int) gdkMotionEvent.y)) { + int [] state = new int[1]; + GDK.gdk_event_get_state(eventPtr, state); + long /*int*/ gdkResource = gdk_event_get_surface_or_window(eventPtr); + double [] eventX = new double[1]; + double [] eventY = new double[1]; + GDK.gdk_event_get_coords(eventPtr, eventX, eventY); + if ((state[0] & GDK.GDK_BUTTON1_MASK) != 0) { + if (GTK.gtk_drag_check_threshold (handle, x, y, (int) eventX[0], (int) eventY[0])) { dragging = true; quit = true; } @@ -2671,7 +2675,11 @@ boolean dragDetect (int x, int y, boolean filter, boolean dragOnTimeout, boolean quit = true; } int [] newX = new int [1], newY = new int [1]; - display.gdk_window_get_device_position (gdkMotionEvent.window, newX, newY, null); + if (GTK.GTK4) { + display.gdk_surface_get_device_position (gdkResource, newX, newY, null); + } else { + display.gdk_window_get_device_position (gdkResource, newX, newY, null); + } break; } case GDK.GDK_KEY_PRESS: @@ -3782,10 +3790,14 @@ long /*int*/ gtk_motion_notify_event (long /*int*/ widget, long /*int*/ event) { dragBegun = true; } int result; - GdkEventMotion gdkEvent = new GdkEventMotion (); - OS.memmove (gdkEvent, event, GdkEventMotion.sizeof); - lastInput.x = (int) gdkEvent.x; - lastInput.y = (int) gdkEvent.y; + double [] eventX = new double[1]; + double [] eventY = new double[1]; + GDK.gdk_event_get_coords(event, eventX, eventY); + double [] eventRX = new double[1]; + double [] eventRY = new double[1]; + GDK.gdk_event_get_root_coords(event, eventRX, eventRY); + lastInput.x = (int) eventX[0]; + lastInput.y = (int) eventY[0]; if (containedInRegion(lastInput.x, lastInput.y)) return 0; /* * Feature in GTK: DND detection for X.11 & Wayland support is done through motion notify event @@ -3795,7 +3807,7 @@ long /*int*/ gtk_motion_notify_event (long /*int*/ widget, long /*int*/ event) { boolean dragging = false; if ((state & DRAG_DETECT) != 0 && hooks (SWT.DragDetect)) { boolean [] consume = new boolean [1]; - if (dragDetect ((int) gdkEvent.x, (int) gdkEvent.y, true, true, consume)) { + if (dragDetect ((int) eventX[0], (int) eventY[0], true, true, consume)) { dragging = true; if (consume [0]) result = 1; if (isDisposed ()) return 1; @@ -3806,9 +3818,6 @@ long /*int*/ gtk_motion_notify_event (long /*int*/ widget, long /*int*/ event) { GTK.gtk_event_controller_handle_event(dragGesture,event); int eventType = GDK.gdk_event_get_event_type(event); if (eventType == GDK.GDK_3BUTTON_PRESS) return 0; - double [] eventX = new double [1]; - double [] eventY = new double [1]; - GDK.gdk_event_get_coords(event, eventX, eventY); Point scaledEvent = DPIUtil.autoScaleDown(new Point((int)eventX[0], (int) eventY[0])); int [] eventButton = new int [1]; GDK.gdk_event_get_button(event, eventButton); @@ -3816,34 +3825,42 @@ long /*int*/ gtk_motion_notify_event (long /*int*/ widget, long /*int*/ event) { GDK.gdk_event_get_state(event, eventState); if (sendDragEvent (eventButton[0], eventState[0], scaledEvent.x, scaledEvent.y, false)){ return 1; + } } } -} if (this == display.currentControl && (hooks (SWT.MouseHover) || filters (SWT.MouseHover))) { display.addMouseHoverTimeout (handle); } - double x = gdkEvent.x_root, y = gdkEvent.y_root; - int state = gdkEvent.state; - if (gdkEvent.is_hint != 0) { - int [] pointer_x = new int [1], pointer_y = new int [1], mask = new int [1]; - long /*int*/ window = eventWindow (); - display.gdk_window_get_device_position (window, pointer_x, pointer_y, mask); - x = pointer_x [0]; - y = pointer_y [0]; - state = mask [0]; + double x = eventRX[0], y = eventRY[0]; + int [] state = new int [1]; + GdkEventMotion gdkEvent = new GdkEventMotion(); + if (!GTK.GTK4) { + OS.memmove(gdkEvent, event, GdkEventMotion.sizeof); + state[0] = gdkEvent.state; + if (gdkEvent.is_hint != 0) { + int [] pointer_x = new int [1], pointer_y = new int [1], mask = new int [1]; + long /*int*/ window = eventWindow (); + display.gdk_window_get_device_position (window, pointer_x, pointer_y, mask); + x = pointer_x [0]; + y = pointer_y [0]; + state[0] = mask [0]; + } + } else { + GDK.gdk_event_get_state(event, state); } + int time = GDK.gdk_event_get_time(event); if (this != display.currentControl) { if (display.currentControl != null && !display.currentControl.isDisposed ()) { display.removeMouseHoverTimeout (display.currentControl.handle); Point pt = display.mapInPixels (this, display.currentControl, (int) x, (int) y); - display.currentControl.sendMouseEvent (SWT.MouseExit, 0, gdkEvent.time, pt.x, pt.y, gdkEvent.is_hint != 0, state); + display.currentControl.sendMouseEvent (SWT.MouseExit, 0, time, pt.x, pt.y, GTK.GTK4 ? false : gdkEvent.is_hint != 0, state[0]); } if (!isDisposed ()) { display.currentControl = this; - sendMouseEvent (SWT.MouseEnter, 0, gdkEvent.time, x, y, gdkEvent.is_hint != 0, state); + sendMouseEvent (SWT.MouseEnter, 0, time, x, y, GTK.GTK4 ? false : gdkEvent.is_hint != 0, state[0]); } } - result = sendMouseEvent (SWT.MouseMove, 0, gdkEvent.time, x, y, gdkEvent.is_hint != 0, state) ? 0 : 1; + result = sendMouseEvent (SWT.MouseMove, 0, time, x, y, GTK.GTK4 ? false : gdkEvent.is_hint != 0, state[0]) ? 0 : 1; return result; } diff --git a/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Link.java b/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Link.java index b47ca9652a..41a8950842 100644 --- a/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Link.java +++ b/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Link.java @@ -461,12 +461,15 @@ long /*int*/ gtk_key_press_event (long /*int*/ widget, long /*int*/ eventPtr) { long /*int*/ gtk_motion_notify_event (long /*int*/ widget, long /*int*/ event) { long /*int*/ result = super.gtk_motion_notify_event (widget, event); if (result != 0) return result; - GdkEventMotion gdkEvent = new GdkEventMotion (); - OS.memmove (gdkEvent, event, GdkEventMotion.sizeof); - int x = (int) gdkEvent.x; - int y = (int) gdkEvent.y; + double [] eventX = new double [1]; + double [] eventY = new double [1]; + GDK.gdk_event_get_coords(event, eventX, eventY); + int x = (int) eventX[0]; + int y = (int) eventY[0]; + int [] state = new int [1]; + GDK.gdk_event_get_state(event, state); if ((style & SWT.MIRRORED) != 0) x = getClientWidth () - x; - if ((gdkEvent.state & GDK.GDK_BUTTON1_MASK) != 0) { + if ((state[0] & GDK.GDK_BUTTON1_MASK) != 0) { int oldSelection = selection.y; selection.y = DPIUtil.autoScaleUp(layout.getOffset (x, y, null)); if (selection.y != oldSelection) { diff --git a/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Sash.java b/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Sash.java index 9775092de2..0c80cdfb38 100644 --- a/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Sash.java +++ b/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Sash.java @@ -354,21 +354,37 @@ long /*int*/ gtk_motion_notify_event (long /*int*/ widget, long /*int*/ eventPtr long /*int*/ result = super.gtk_motion_notify_event (widget, eventPtr); if (result != 0) return result; if (!dragging) return 0; - GdkEventMotion gdkEvent = new GdkEventMotion (); - OS.memmove (gdkEvent, eventPtr, GdkEventButton.sizeof); int eventX, eventY, eventState; - if (gdkEvent.is_hint != 0) { + double [] fetchedX = new double [1]; + double [] fetchedY = new double [1]; + GDK.gdk_event_get_root_coords(eventPtr, fetchedX, fetchedY); + int [] state = new int [1]; + GDK.gdk_event_get_state(eventPtr, state); + long /*int*/ gdkResource = gdk_event_get_surface_or_window(eventPtr); + boolean isHint; + if (GTK.GTK4) { + isHint = false; + } else { + GdkEventMotion gdkEvent = new GdkEventMotion (); + OS.memmove(gdkEvent, eventPtr, GdkEventMotion.sizeof); + isHint = gdkEvent.is_hint != 0; + } + if (isHint) { int [] pointer_x = new int [1], pointer_y = new int [1], mask = new int [1]; - display.gdk_window_get_device_position (gdkEvent.window, pointer_x, pointer_y, mask); + display.gdk_window_get_device_position (gdkResource, pointer_x, pointer_y, mask); eventX = pointer_x [0]; eventY = pointer_y [0]; eventState = mask [0]; } else { int [] origin_x = new int [1], origin_y = new int [1]; - GDK.gdk_window_get_origin (gdkEvent.window, origin_x, origin_y); - eventX = (int) (gdkEvent.x_root - origin_x [0]); - eventY = (int) (gdkEvent.y_root - origin_y [0]); - eventState = gdkEvent.state; + if (GTK.GTK4) { + GDK.gdk_surface_get_origin(gdkResource, origin_x, origin_y); + } else { + GDK.gdk_window_get_origin (gdkResource, origin_x, origin_y); + } + eventX = (int) (fetchedX[0] - origin_x [0]); + eventY = (int) (fetchedY[0] - origin_y [0]); + eventState = state[0]; } if ((eventState & GDK.GDK_BUTTON1_MASK) == 0) return 0; GtkAllocation allocation = new GtkAllocation (); @@ -391,7 +407,7 @@ long /*int*/ gtk_motion_notify_event (long /*int*/ widget, long /*int*/ eventPtr drawBand (lastX, lastY, width, height); Event event = new Event (); - event.time = gdkEvent.time; + event.time = GDK.gdk_event_get_time(eventPtr); Rectangle eventRect = new Rectangle (newX, newY, width, height); event.setBounds (DPIUtil.autoScaleDown (eventRect)); if ((style & SWT.SMOOTH) == 0) { diff --git a/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Shell.java b/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Shell.java index 48af5fb592..9d72b13237 100644 --- a/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Shell.java +++ b/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Shell.java @@ -1556,12 +1556,15 @@ long /*int*/ gtk_move_focus (long /*int*/ widget, long /*int*/ directionType) { long /*int*/ gtk_motion_notify_event (long /*int*/ widget, long /*int*/ event) { if (widget == shellHandle) { if (isCustomResize ()) { - GdkEventMotion gdkEvent = new GdkEventMotion (); - OS.memmove (gdkEvent, event, GdkEventMotion.sizeof); - if ((gdkEvent.state & GDK.GDK_BUTTON1_MASK) != 0) { + int [] state = new int [1]; + GDK.gdk_event_get_state(event, state); + double [] eventRX = new double [1]; + double [] eventRY = new double [1]; + GDK.gdk_event_get_root_coords(event, eventRX, eventRY); + if ((state[0] & GDK.GDK_BUTTON1_MASK) != 0) { int border = gtk_container_get_border_width_or_margin (shellHandle); - int dx = (int)(gdkEvent.x_root - display.resizeLocationX); - int dy = (int)(gdkEvent.y_root - display.resizeLocationY); + int dx = (int)(eventRX[0] - display.resizeLocationX); + int dy = (int)(eventRY[0] - display.resizeLocationY); int x = display.resizeBoundsX; int y = display.resizeBoundsY; int width = display.resizeBoundsWidth; @@ -1610,7 +1613,10 @@ long /*int*/ gtk_motion_notify_event (long /*int*/ widget, long /*int*/ event) { GTK.gtk_window_resize (shellHandle, width, height); } } else { - int mode = getResizeMode (gdkEvent.x, gdkEvent.y); + double [] eventX = new double [1]; + double [] eventY = new double [1]; + GDK.gdk_event_get_coords(event, eventX, eventY); + int mode = getResizeMode (eventX[0], eventY[0]); if (mode != display.resizeMode) { long /*int*/ window = gtk_widget_get_window (shellHandle); long /*int*/ cursor = GDK.gdk_cursor_new_for_display (GDK.gdk_display_get_default(), mode); diff --git a/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Widget.java b/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Widget.java index c31a6cdb5f..d609988da0 100644 --- a/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Widget.java +++ b/bundles/org.eclipse.swt/Eclipse SWT/gtk/org/eclipse/swt/widgets/Widget.java @@ -1919,6 +1919,22 @@ void gdk_event_free (long /*int*/ event) { } /** + * Wrapper function for gdk_event_get_surface() on GTK4, + * and gdk_event_get_window() on GTK3. + * + * @param event the event whose window or surface to fetch + * @return the GdkWindow or GdkSurface associated with the event + */ +long /*int*/ gdk_event_get_surface_or_window(long /*int*/ event) { + if (event == 0) return 0; + if (GTK.GTK4) { + return GDK.gdk_event_get_surface(event); + } else { + return GDK.gdk_event_get_window(event); + } +} + +/** * Wrapper function for gdk_event_get_state() * @param event pointer to the GdkEvent. * @return the keymask to be used with constants like |