mirror of
https://gitlab.gnome.org/GNOME/gtk.git
synced 2024-12-27 06:00:22 +00:00
GtkMagnifier: Add a resizing mode
In addition to the fixed-size mode that is used by the text view, add a mode in which the magnifier requests enough size to render the entire inspected widget at the current magnification. In this mode, the magnifier will update its size when the size of the inspected widget changes. Also, make the magnifier redraw on its own whenever the inspected widget draws.
This commit is contained in:
parent
42a6ae6c6c
commit
10d0ca0a3d
@ -22,6 +22,7 @@
|
||||
|
||||
enum {
|
||||
PROP_INSPECTED = 1,
|
||||
PROP_RESIZE,
|
||||
PROP_MAGNIFICATION
|
||||
};
|
||||
|
||||
@ -33,6 +34,9 @@ struct _GtkMagnifierPrivate
|
||||
gdouble magnification;
|
||||
gint x;
|
||||
gint y;
|
||||
gboolean resize;
|
||||
gulong draw_handler;
|
||||
gulong resize_handler;
|
||||
};
|
||||
|
||||
G_DEFINE_TYPE_WITH_PRIVATE (GtkMagnifier, _gtk_magnifier,
|
||||
@ -54,6 +58,10 @@ _gtk_magnifier_set_property (GObject *object,
|
||||
_gtk_magnifier_set_magnification (GTK_MAGNIFIER (object),
|
||||
g_value_get_double (value));
|
||||
break;
|
||||
case PROP_RESIZE:
|
||||
_gtk_magnifier_set_resize (GTK_MAGNIFIER (object),
|
||||
g_value_get_boolean (value));
|
||||
break;
|
||||
default:
|
||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, param_id, pspec);
|
||||
}
|
||||
@ -79,6 +87,9 @@ _gtk_magnifier_get_property (GObject *object,
|
||||
case PROP_MAGNIFICATION:
|
||||
g_value_set_double (value, priv->magnification);
|
||||
break;
|
||||
case PROP_RESIZE:
|
||||
g_value_set_boolean (value, priv->resize);
|
||||
break;
|
||||
default:
|
||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, param_id, pspec);
|
||||
}
|
||||
@ -96,12 +107,17 @@ _gtk_magnifier_draw (GtkWidget *widget,
|
||||
magnifier = GTK_MAGNIFIER (widget);
|
||||
priv = _gtk_magnifier_get_instance_private (magnifier);
|
||||
|
||||
if (priv->inspected == NULL)
|
||||
return FALSE;
|
||||
|
||||
if (!gtk_widget_is_visible (priv->inspected))
|
||||
return FALSE;
|
||||
|
||||
gtk_widget_get_allocation (widget, &allocation);
|
||||
gtk_widget_get_allocation (priv->inspected, &inspected_alloc);
|
||||
cairo_translate (cr, allocation.width / 2, allocation.height / 2);
|
||||
|
||||
if (!priv->resize)
|
||||
cairo_translate (cr, allocation.width / 2, allocation.height / 2);
|
||||
|
||||
x = CLAMP (priv->x, 0, inspected_alloc.width);
|
||||
y = CLAMP (priv->y, 0, inspected_alloc.height);
|
||||
@ -109,12 +125,133 @@ _gtk_magnifier_draw (GtkWidget *widget,
|
||||
cairo_save (cr);
|
||||
cairo_scale (cr, priv->magnification, priv->magnification);
|
||||
cairo_translate (cr, -x, -y);
|
||||
g_signal_handler_block (priv->inspected, priv->draw_handler);
|
||||
gtk_widget_draw (priv->inspected, cr);
|
||||
g_signal_handler_unblock (priv->inspected, priv->draw_handler);
|
||||
cairo_restore (cr);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_magnifier_get_preferred_width (GtkWidget *widget,
|
||||
gint *minimum_width,
|
||||
gint *natural_width)
|
||||
{
|
||||
GtkMagnifier *magnifier;
|
||||
GtkMagnifierPrivate *priv;
|
||||
gint width;
|
||||
|
||||
magnifier = GTK_MAGNIFIER (widget);
|
||||
priv = _gtk_magnifier_get_instance_private (magnifier);
|
||||
|
||||
if (priv->resize && priv->inspected)
|
||||
width = priv->magnification * gtk_widget_get_allocated_width (priv->inspected);
|
||||
else
|
||||
width = 0;
|
||||
|
||||
*minimum_width = width;
|
||||
*natural_width = width;
|
||||
}
|
||||
|
||||
static void
|
||||
gtk_magnifier_get_preferred_height (GtkWidget *widget,
|
||||
gint *minimum_height,
|
||||
gint *natural_height)
|
||||
{
|
||||
GtkMagnifier *magnifier;
|
||||
GtkMagnifierPrivate *priv;
|
||||
gint height;
|
||||
|
||||
magnifier = GTK_MAGNIFIER (widget);
|
||||
priv = _gtk_magnifier_get_instance_private (magnifier);
|
||||
|
||||
if (priv->resize && priv->inspected)
|
||||
height = priv->magnification * gtk_widget_get_allocated_height (priv->inspected);
|
||||
else
|
||||
height = 0;
|
||||
|
||||
*minimum_height = height;
|
||||
*natural_height = height;
|
||||
}
|
||||
|
||||
static void
|
||||
resize_handler (GtkWidget *widget,
|
||||
GtkAllocation *alloc,
|
||||
GtkWidget *magnifier)
|
||||
{
|
||||
gtk_widget_queue_resize (magnifier);
|
||||
}
|
||||
|
||||
static void
|
||||
connect_resize_handler (GtkMagnifier *magnifier)
|
||||
{
|
||||
GtkMagnifierPrivate *priv;
|
||||
|
||||
priv = _gtk_magnifier_get_instance_private (magnifier);
|
||||
|
||||
if (priv->inspected && priv->resize)
|
||||
priv->resize_handler = g_signal_connect (priv->inspected, "size-allocate",
|
||||
G_CALLBACK (resize_handler), magnifier);
|
||||
}
|
||||
|
||||
static void
|
||||
disconnect_resize_handler (GtkMagnifier *magnifier)
|
||||
{
|
||||
GtkMagnifierPrivate *priv;
|
||||
|
||||
priv = _gtk_magnifier_get_instance_private (magnifier);
|
||||
|
||||
if (priv->resize_handler)
|
||||
{
|
||||
g_signal_handler_disconnect (priv->inspected, priv->resize_handler);
|
||||
priv->resize_handler = 0;
|
||||
}
|
||||
}
|
||||
|
||||
static gboolean
|
||||
draw_handler (GtkWidget *widget,
|
||||
cairo_t *cr,
|
||||
GtkWidget *magnifier)
|
||||
{
|
||||
gtk_widget_queue_draw (magnifier);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static void
|
||||
connect_draw_handler (GtkMagnifier *magnifier)
|
||||
{
|
||||
GtkMagnifierPrivate *priv;
|
||||
|
||||
priv = _gtk_magnifier_get_instance_private (magnifier);
|
||||
|
||||
if (priv->inspected)
|
||||
priv->draw_handler = g_signal_connect (priv->inspected, "draw",
|
||||
G_CALLBACK (draw_handler), magnifier);
|
||||
}
|
||||
|
||||
static void
|
||||
disconnect_draw_handler (GtkMagnifier *magnifier)
|
||||
{
|
||||
GtkMagnifierPrivate *priv;
|
||||
|
||||
priv = _gtk_magnifier_get_instance_private (magnifier);
|
||||
|
||||
if (priv->draw_handler)
|
||||
{
|
||||
g_signal_handler_disconnect (priv->inspected, priv->draw_handler);
|
||||
priv->draw_handler = 0;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
_gtk_magnifier_destroy (GtkWidget *widget)
|
||||
{
|
||||
_gtk_magnifier_set_inspected (GTK_MAGNIFIER (widget), NULL);
|
||||
|
||||
GTK_WIDGET_CLASS (_gtk_magnifier_parent_class)->destroy (widget);
|
||||
}
|
||||
|
||||
static void
|
||||
_gtk_magnifier_class_init (GtkMagnifierClass *klass)
|
||||
{
|
||||
@ -124,7 +261,10 @@ _gtk_magnifier_class_init (GtkMagnifierClass *klass)
|
||||
object_class->set_property = _gtk_magnifier_set_property;
|
||||
object_class->get_property = _gtk_magnifier_get_property;
|
||||
|
||||
widget_class->destroy = _gtk_magnifier_destroy;
|
||||
widget_class->draw = _gtk_magnifier_draw;
|
||||
widget_class->get_preferred_width = gtk_magnifier_get_preferred_width;
|
||||
widget_class->get_preferred_height = gtk_magnifier_get_preferred_height;
|
||||
|
||||
g_object_class_install_property (object_class,
|
||||
PROP_INSPECTED,
|
||||
@ -140,6 +280,13 @@ _gtk_magnifier_class_init (GtkMagnifierClass *klass)
|
||||
P_("magnification"),
|
||||
1, G_MAXDOUBLE, 1,
|
||||
G_PARAM_READWRITE));
|
||||
g_object_class_install_property (object_class,
|
||||
PROP_RESIZE,
|
||||
g_param_spec_boolean ("resize",
|
||||
P_("resize"),
|
||||
P_("resize"),
|
||||
FALSE,
|
||||
G_PARAM_READWRITE));
|
||||
}
|
||||
|
||||
static void
|
||||
@ -156,6 +303,7 @@ _gtk_magnifier_init (GtkMagnifier *magnifier)
|
||||
|
||||
gtk_widget_set_has_window (widget, FALSE);
|
||||
priv->magnification = 1;
|
||||
priv->resize = FALSE;
|
||||
}
|
||||
|
||||
GtkWidget *
|
||||
@ -193,7 +341,14 @@ _gtk_magnifier_set_inspected (GtkMagnifier *magnifier,
|
||||
if (priv->inspected == inspected)
|
||||
return;
|
||||
|
||||
disconnect_draw_handler (magnifier);
|
||||
disconnect_resize_handler (magnifier);
|
||||
|
||||
priv->inspected = inspected;
|
||||
|
||||
connect_draw_handler (magnifier);
|
||||
connect_resize_handler (magnifier);
|
||||
|
||||
g_object_notify (G_OBJECT (magnifier), "inspected");
|
||||
}
|
||||
|
||||
@ -252,6 +407,9 @@ _gtk_magnifier_set_magnification (GtkMagnifier *magnifier,
|
||||
priv->magnification = magnification;
|
||||
g_object_notify (G_OBJECT (magnifier), "magnification");
|
||||
|
||||
if (priv->resize)
|
||||
gtk_widget_queue_resize (GTK_WIDGET (magnifier));
|
||||
|
||||
if (gtk_widget_is_visible (GTK_WIDGET (magnifier)))
|
||||
gtk_widget_queue_draw (GTK_WIDGET (magnifier));
|
||||
}
|
||||
@ -267,3 +425,37 @@ _gtk_magnifier_get_magnification (GtkMagnifier *magnifier)
|
||||
|
||||
return priv->magnification;
|
||||
}
|
||||
|
||||
void
|
||||
_gtk_magnifier_set_resize (GtkMagnifier *magnifier,
|
||||
gboolean resize)
|
||||
{
|
||||
GtkMagnifierPrivate *priv;
|
||||
|
||||
g_return_if_fail (GTK_IS_MAGNIFIER (magnifier));
|
||||
|
||||
priv = _gtk_magnifier_get_instance_private (magnifier);
|
||||
|
||||
if (priv->resize == resize)
|
||||
return;
|
||||
|
||||
priv->resize = resize;
|
||||
|
||||
gtk_widget_queue_resize (GTK_WIDGET (magnifier));
|
||||
if (resize)
|
||||
connect_resize_handler (magnifier);
|
||||
else
|
||||
disconnect_resize_handler (magnifier);
|
||||
}
|
||||
|
||||
gboolean
|
||||
_gtk_magnifier_get_resize (GtkMagnifier *magnifier)
|
||||
{
|
||||
GtkMagnifierPrivate *priv;
|
||||
|
||||
g_return_val_if_fail (GTK_IS_MAGNIFIER (magnifier), FALSE);
|
||||
|
||||
priv = _gtk_magnifier_get_instance_private (magnifier);
|
||||
|
||||
return priv->resize;
|
||||
}
|
||||
|
@ -59,6 +59,10 @@ void _gtk_magnifier_set_magnification (GtkMagnifier *magnifier,
|
||||
gdouble magnification);
|
||||
gdouble _gtk_magnifier_get_magnification (GtkMagnifier *magnifier);
|
||||
|
||||
void _gtk_magnifier_set_resize (GtkMagnifier *magnifier,
|
||||
gboolean resize);
|
||||
gboolean _gtk_magnifier_get_resize (GtkMagnifier *magnifier);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
#endif /* __GTK_MAGNIFIER_H__ */
|
||||
|
Loading…
Reference in New Issue
Block a user