gesture: set widget x and y if coordinate translation between widgets fails

Bug Description: In a GTK+ application with a menu bar, clicking the
menu item displays a dialog. However, when the user opens this dialog
and drags the parent window's menu bar with the cursor, the dialog
gets moved.
Issue: When _gtk_gesture_update_point calls the _update_widget_coordinates
function, the local variables x and y are not explicitly initialized, leading
to arbitrary values. For instance, in my case, x was 32767 and y was
-145750164 . These values are used in the subsequent call to
gtk_widget_translate_coordinates. In gtk_widget_translate_coordinates,
if ancestor is NULL, the function returns FALSE, and dest_x and dest_y
are not updated. The incorrect values of x and y cause data->widget_x
and data->widget_y to be incorrect, ultimately leading to abnormal
x and y values in the gtk_gesture_drag_update function.

To avoid this, we should set x and y to values clearly outside the widget.

Signed-off-by: Li Kai <likai@kylinos.cn>
This commit is contained in:
likai 2024-08-07 22:01:15 +08:00
parent 02cec9b8c9
commit a1046a13da

View File

@ -125,6 +125,7 @@
#include "gtkmain.h"
#include "gtkintl.h"
#include "gtkmarshalers.h"
#include <math.h>
typedef struct _GtkGesturePrivate GtkGesturePrivate;
typedef struct _PointData PointData;
@ -472,7 +473,7 @@ _update_widget_coordinates (GtkGesture *gesture,
GtkWidget *event_widget, *widget;
GtkAllocation allocation;
gdouble event_x, event_y;
gint wx, wy, x, y;
gint x, y;
event_widget = gtk_get_event_widget (data->event);
@ -486,6 +487,7 @@ _update_widget_coordinates (GtkGesture *gesture,
while (window && window != event_widget_window)
{
gint wx, wy;
gdk_window_get_position (window, &wx, &wy);
event_x += wx;
event_y += wy;
@ -502,13 +504,20 @@ _update_widget_coordinates (GtkGesture *gesture,
event_y -= allocation.y;
}
gtk_widget_translate_coordinates (event_widget, widget,
event_x, event_y, &x, &y);
/* gtk_widget_translate() loses the fractional part so we need to
* add it back to not lose accuracy */
data->widget_x = x + (event_x - (int)event_x);
data->widget_y = y + (event_y - (int)event_y);
if (gtk_widget_translate_coordinates (event_widget, widget,
event_x, event_y, &x, &y))
{
/* gtk_widget_translate() loses the fractional part so we need to
* add it back to not lose accuracy */
data->widget_x = x + (event_x - (int)event_x);
data->widget_y = y + (event_y - (int)event_y);
}
else
{
/* Mark the coordinates well outside the widget, to
* signal that the translation has failed */
data->widget_x = data->widget_y = NAN;
}
}
static GtkEventSequenceState