diff --git a/gtk/gtksnapshot.c b/gtk/gtksnapshot.c index 26aef79382..110cdb5847 100644 --- a/gtk/gtksnapshot.c +++ b/gtk/gtksnapshot.c @@ -20,6 +20,8 @@ #include "gtksnapshot.h" #include "gtksnapshotprivate.h" +#include "gtkcssrgbavalueprivate.h" +#include "gtkcssshadowsvalueprivate.h" #include "gtkrenderbackgroundprivate.h" #include "gtkrenderborderprivate.h" #include "gtkstylecontextprivate.h" @@ -295,3 +297,45 @@ gtk_snapshot_render_frame (GtkSnapshot *state, gtk_style_context_get_junction_sides (context)); gtk_snapshot_translate_2d (state, -x, -y); } + +void +gtk_snapshot_render_layout (GtkSnapshot *state, + GtkStyleContext *context, + gdouble x, + gdouble y, + PangoLayout *layout) +{ + const GdkRGBA *fg_color; + graphene_rect_t bounds; + GtkBorder shadow_extents; + PangoRectangle ink_rect; + GtkCssValue *shadow; + cairo_t *cr; + + g_return_if_fail (state != NULL); + g_return_if_fail (GTK_IS_STYLE_CONTEXT (context)); + g_return_if_fail (PANGO_IS_LAYOUT (layout)); + + fg_color = _gtk_css_rgba_value_get_rgba (_gtk_style_context_peek_property (context, GTK_CSS_PROPERTY_COLOR)); + shadow = _gtk_style_context_peek_property (context, GTK_CSS_PROPERTY_TEXT_SHADOW); + pango_layout_get_pixel_extents (layout, &ink_rect, NULL); + _gtk_css_shadows_value_get_extents (shadow, &shadow_extents); + graphene_rect_init (&bounds, + ink_rect.x - shadow_extents.left, + ink_rect.y - shadow_extents.top, + ink_rect.width + shadow_extents.left + shadow_extents.right, + ink_rect.height + shadow_extents.top + shadow_extents.bottom); + + gtk_snapshot_translate_2d (state, x, y); + + cr = gtk_snapshot_append_cairo_node (state, &bounds, "Text<%dchars>", pango_layout_get_character_count (layout)); + + _gtk_css_shadows_value_paint_layout (shadow, cr, layout); + + gdk_cairo_set_source_rgba (cr, fg_color); + pango_cairo_show_layout (cr, layout); + + cairo_destroy (cr); + gtk_snapshot_translate_2d (state, -x, -y); +} + diff --git a/gtk/gtksnapshot.h b/gtk/gtksnapshot.h index 159c25362c..948e22c02e 100644 --- a/gtk/gtksnapshot.h +++ b/gtk/gtksnapshot.h @@ -96,6 +96,12 @@ void gtk_snapshot_render_frame (GtkSnapshot gdouble y, gdouble width, gdouble height); +GDK_AVAILABLE_IN_3_90 +void gtk_snapshot_render_layout (GtkSnapshot *state, + GtkStyleContext *context, + gdouble x, + gdouble y, + PangoLayout *layout); G_END_DECLS diff --git a/gtk/gtkswitch.c b/gtk/gtkswitch.c index 1ac6df57a7..62e32eaf39 100644 --- a/gtk/gtkswitch.c +++ b/gtk/gtkswitch.c @@ -532,25 +532,25 @@ gtk_switch_unmap (GtkWidget *widget) } static gboolean -gtk_switch_render_slider (GtkCssGadget *gadget, - cairo_t *cr, - int x, - int y, - int width, - int height, - gpointer data) +gtk_switch_snapshot_slider (GtkCssGadget *gadget, + GtkSnapshot *snapshot, + int x, + int y, + int width, + int height, + gpointer data) { return gtk_widget_has_visible_focus (gtk_css_gadget_get_owner (gadget)); } static gboolean -gtk_switch_render_trough (GtkCssGadget *gadget, - cairo_t *cr, - int x, - int y, - int width, - int height, - gpointer data) +gtk_switch_snapshot_trough (GtkCssGadget *gadget, + GtkSnapshot *snapshot, + int x, + int y, + int width, + int height, + gpointer data) { GtkWidget *widget = gtk_css_gadget_get_owner (gadget); GtkSwitchPrivate *priv = GTK_SWITCH (widget)->priv; @@ -563,18 +563,27 @@ gtk_switch_render_trough (GtkCssGadget *gadget, label_x = x + ((width / 2) - rect.width) / 2; label_y = y + (height - rect.height) / 2; - gtk_render_layout (context, cr, label_x, label_y, priv->on_layout); + gtk_snapshot_render_layout (snapshot, context, label_x, label_y, priv->on_layout); pango_layout_get_pixel_extents (priv->off_layout, NULL, &rect); label_x = x + (width / 2) + ((width / 2) - rect.width) / 2; label_y = y + (height - rect.height) / 2; - gtk_render_layout (context, cr, label_x, label_y, priv->off_layout); + gtk_snapshot_render_layout (snapshot, context, label_x, label_y, priv->off_layout); + + gtk_css_gadget_snapshot (priv->slider_gadget, snapshot); return FALSE; } +static void +gtk_switch_snapshot (GtkWidget *widget, + GtkSnapshot *snapshot) +{ + gtk_css_gadget_snapshot (GTK_SWITCH (widget)->priv->gadget, snapshot); +} + static void gtk_switch_set_action_name (GtkActionable *actionable, const gchar *action_name) @@ -723,27 +732,6 @@ state_set (GtkSwitch *sw, gboolean state) return TRUE; } -static GskRenderNode * -gtk_switch_get_render_node (GtkWidget *widget, GskRenderer *renderer) -{ - GtkSwitchPrivate *priv =gtk_switch_get_instance_private (GTK_SWITCH (widget)); - GskRenderNode *trough_node; - GskRenderNode *slider_node; - - trough_node = gtk_css_gadget_get_render_node (priv->gadget, renderer, FALSE); - - if (trough_node == NULL) - return NULL; - - slider_node = gtk_css_gadget_get_render_node (priv->slider_gadget, renderer, - gtk_widget_has_visible_focus (widget)); - - gsk_render_node_append_child (trough_node, slider_node); - gsk_render_node_unref (slider_node); - - return trough_node; -} - static void gtk_switch_class_init (GtkSwitchClass *klass) { @@ -790,11 +778,11 @@ gtk_switch_class_init (GtkSwitchClass *klass) widget_class->unrealize = gtk_switch_unrealize; widget_class->map = gtk_switch_map; widget_class->unmap = gtk_switch_unmap; + widget_class->snapshot = gtk_switch_snapshot; widget_class->enter_notify_event = gtk_switch_enter; widget_class->leave_notify_event = gtk_switch_leave; widget_class->screen_changed = gtk_switch_screen_changed; widget_class->style_updated = gtk_switch_style_updated; - widget_class->get_render_node = gtk_switch_get_render_node; klass->activate = gtk_switch_activate; klass->state_set = state_set; @@ -877,8 +865,8 @@ gtk_switch_init (GtkSwitch *self) GTK_WIDGET (self), gtk_switch_get_content_size, gtk_switch_allocate_contents, - gtk_switch_render_trough, NULL, + gtk_switch_snapshot_trough, NULL, NULL); @@ -888,8 +876,8 @@ gtk_switch_init (GtkSwitch *self) NULL, NULL, NULL, - gtk_switch_render_slider, NULL, + gtk_switch_snapshot_slider, NULL, NULL);