X-Git-Url: http://pileus.org/git/?a=blobdiff_plain;f=gtk%2Fgtkstylecontext.c;h=f5d1e86ea5a888f1a11729c50a188ad0b805d756;hb=5bbbc47a4c306653e8347f7afb85a940a503f755;hp=a139d392430bb0cde098b92ddfe4828220e28a3b;hpb=16677bb85ad78ac57776a679abaa69e3d1fc22b9;p=~andy%2Fgtk diff --git a/gtk/gtkstylecontext.c b/gtk/gtkstylecontext.c index a139d3924..f5d1e86ea 100644 --- a/gtk/gtkstylecontext.c +++ b/gtk/gtkstylecontext.c @@ -24,11 +24,12 @@ #include "gtkstylecontextprivate.h" #include "gtkcontainerprivate.h" +#include "gtkcsscolorvalueprivate.h" +#include "gtkcsscornervalueprivate.h" #include "gtkcssenginevalueprivate.h" #include "gtkcssnumbervalueprivate.h" #include "gtkcssrgbavalueprivate.h" #include "gtkdebug.h" -#include "gtkgradientprivate.h" #include "gtkstylepropertiesprivate.h" #include "gtktypebuiltins.h" #include "gtkthemingengineprivate.h" @@ -36,7 +37,6 @@ #include "gtkwidget.h" #include "gtkwindow.h" #include "gtkprivate.h" -#include "gtksymboliccolorprivate.h" #include "gtkiconfactory.h" #include "gtkwidgetpath.h" #include "gtkwidgetprivate.h" @@ -45,6 +45,9 @@ #include "gtksettings.h" #include "gtksettingsprivate.h" +#include "deprecated/gtkgradientprivate.h" +#include "deprecated/gtksymboliccolorprivate.h" + /** * SECTION:gtkstylecontext * @Short_description: Rendering UI elements @@ -355,22 +358,21 @@ struct _GtkStyleContextPrivate GtkStyleCascade *cascade; - GtkStyleContext *animation_list_prev; - GtkStyleContext *animation_list_next; - GtkStyleContext *parent; GSList *children; - GtkWidget *widget; + GtkWidget *widget; GtkWidgetPath *widget_path; GHashTable *style_data; GtkStyleInfo *info; - GtkTextDirection direction; + GdkFrameClock *frame_clock; + guint frame_clock_update_id; GtkCssChange relevant_changes; GtkCssChange pending_changes; - guint invalidating_context : 1; + const GtkBitmask *invalidating_context; + guint animating : 1; guint invalid : 1; }; @@ -378,6 +380,7 @@ enum { PROP_0, PROP_SCREEN, PROP_DIRECTION, + PROP_FRAME_CLOCK, PROP_PARENT }; @@ -387,8 +390,6 @@ enum { }; static guint signals[LAST_SIGNAL] = { 0 }; -static GtkStyleContext *_running_animations = NULL; -guint _running_animations_timer_id = 0; static void gtk_style_context_finalize (GObject *object); @@ -403,6 +404,9 @@ static void gtk_style_context_impl_get_property (GObject *object, static StyleData *style_data_lookup (GtkStyleContext *context); +static void gtk_style_context_disconnect_update (GtkStyleContext *context); +static void gtk_style_context_connect_update (GtkStyleContext *context); + G_DEFINE_TYPE (GtkStyleContext, gtk_style_context, G_TYPE_OBJECT) static void @@ -441,6 +445,13 @@ gtk_style_context_class_init (GtkStyleContextClass *klass) P_("The associated GdkScreen"), GDK_TYPE_SCREEN, GTK_PARAM_READWRITE)); + g_object_class_install_property (object_class, + PROP_FRAME_CLOCK, + g_param_spec_object ("paint-clock", + P_("FrameClock"), + P_("The associated GdkFrameClock"), + GDK_TYPE_FRAME_CLOCK, + GTK_PARAM_READWRITE)); g_object_class_install_property (object_class, PROP_DIRECTION, g_param_spec_enum ("direction", @@ -712,40 +723,59 @@ gtk_style_context_init (GtkStyleContext *style_context) (GDestroyNotify) style_info_free, (GDestroyNotify) style_data_unref); - priv->direction = GTK_TEXT_DIR_LTR; - priv->screen = gdk_screen_get_default (); priv->relevant_changes = GTK_CSS_CHANGE_ANY; /* Create default info store */ priv->info = style_info_new (); + priv->info->state_flags = GTK_STATE_FLAG_DIR_LTR; gtk_style_context_set_cascade (style_context, _gtk_style_cascade_get_for_screen (priv->screen)); } +static void +gtk_style_context_update (GdkFrameClock *clock, + GtkStyleContext *context) +{ + _gtk_style_context_queue_invalidate (context, GTK_CSS_CHANGE_ANIMATE); +} + static gboolean -gtk_style_context_do_animations (gpointer unused) +gtk_style_context_is_animating (GtkStyleContext *context) { - GtkStyleContext *context; + GtkStyleContextPrivate *priv = context->priv; + + return priv->animating; +} - for (context = _running_animations; - context != NULL; - context = context->priv->animation_list_next) +static void +gtk_style_context_disconnect_update (GtkStyleContext *context) +{ + GtkStyleContextPrivate *priv = context->priv; + + if (priv->frame_clock && priv->frame_clock_update_id) { - _gtk_style_context_queue_invalidate (context, GTK_CSS_CHANGE_ANIMATE); + g_signal_handler_disconnect (priv->frame_clock, + priv->frame_clock_update_id); + priv->frame_clock_update_id = 0; + gdk_frame_clock_end_updating (priv->frame_clock); } - - return TRUE; } -static gboolean -gtk_style_context_is_animating (GtkStyleContext *context) +static void +gtk_style_context_connect_update (GtkStyleContext *context) { GtkStyleContextPrivate *priv = context->priv; - return priv->animation_list_prev != NULL - || _running_animations == context; + if (priv->frame_clock && priv->frame_clock_update_id == 0) + { + priv->frame_clock_update_id = g_signal_connect (priv->frame_clock, + "update", + G_CALLBACK (gtk_style_context_update), + context); + gdk_frame_clock_begin_updating (priv->frame_clock); + } } static void @@ -756,25 +786,9 @@ gtk_style_context_stop_animating (GtkStyleContext *context) if (!gtk_style_context_is_animating (context)) return; - if (priv->animation_list_prev == NULL) - { - _running_animations = priv->animation_list_next; + priv->animating = FALSE; - if (_running_animations == NULL) - { - /* we were the last animation */ - g_source_remove (_running_animations_timer_id); - _running_animations_timer_id = 0; - } - } - else - priv->animation_list_prev->priv->animation_list_next = priv->animation_list_next; - - if (priv->animation_list_next) - priv->animation_list_next->priv->animation_list_prev = priv->animation_list_prev; - - priv->animation_list_next = NULL; - priv->animation_list_prev = NULL; + gtk_style_context_disconnect_update (context); } static void @@ -785,19 +799,9 @@ gtk_style_context_start_animating (GtkStyleContext *context) if (gtk_style_context_is_animating (context)) return; - if (_running_animations == NULL) - { - _running_animations_timer_id = gdk_threads_add_timeout (25, - gtk_style_context_do_animations, - NULL); - _running_animations = context; - } - else - { - priv->animation_list_next = _running_animations; - _running_animations->priv->animation_list_prev = context; - _running_animations = context; - } + priv->animating = TRUE; + + gtk_style_context_connect_update (context); } static gboolean @@ -881,8 +885,14 @@ gtk_style_context_impl_set_property (GObject *object, g_value_get_object (value)); break; case PROP_DIRECTION: + G_GNUC_BEGIN_IGNORE_DEPRECATIONS; gtk_style_context_set_direction (style_context, g_value_get_enum (value)); + G_GNUC_END_IGNORE_DEPRECATIONS; + break; + case PROP_FRAME_CLOCK: + gtk_style_context_set_frame_clock (style_context, + g_value_get_object (value)); break; case PROP_PARENT: gtk_style_context_set_parent (style_context, @@ -912,7 +922,12 @@ gtk_style_context_impl_get_property (GObject *object, g_value_set_object (value, priv->screen); break; case PROP_DIRECTION: - g_value_set_enum (value, priv->direction); + G_GNUC_BEGIN_IGNORE_DEPRECATIONS; + g_value_set_enum (value, gtk_style_context_get_direction (style_context)); + G_GNUC_END_IGNORE_DEPRECATIONS; + break; + case PROP_FRAME_CLOCK: + g_value_set_object (value, priv->frame_clock); break; case PROP_PARENT: g_value_set_object (value, priv->parent); @@ -1478,9 +1493,18 @@ void gtk_style_context_set_state (GtkStyleContext *context, GtkStateFlags flags) { + GtkStateFlags old_flags; g_return_if_fail (GTK_IS_STYLE_CONTEXT (context)); + old_flags = context->priv->info->state_flags; + if (old_flags == flags) + return; + context->priv->info->state_flags = flags; + + if (((old_flags ^ flags) & (GTK_STATE_FLAG_DIR_LTR | GTK_STATE_FLAG_DIR_RTL)) && + !gtk_style_context_is_saved (context)) + g_object_notify (G_OBJECT (context), "direction"); gtk_style_context_queue_invalidate_internal (context, GTK_CSS_CHANGE_STATE); } @@ -2220,17 +2244,6 @@ _gtk_style_context_peek_property (GtkStyleContext *context, return _gtk_css_computed_values_get_value (data->store, property_id); } -double -_gtk_style_context_get_number (GtkStyleContext *context, - guint property_id, - double one_hundred_percent) -{ - GtkCssValue *value; - - value = _gtk_style_context_peek_property (context, property_id); - return _gtk_css_number_value_get (value, one_hundred_percent); -} - const GValue * _gtk_style_context_peek_style_property (GtkStyleContext *context, GType widget_type, @@ -2282,6 +2295,8 @@ _gtk_style_context_peek_style_property (GtkStyleContext *context, widget_path, state, pspec, &pcache->value)) { + G_GNUC_BEGIN_IGNORE_DEPRECATIONS; + /* Resolve symbolic colors to GdkColor/GdkRGBA */ if (G_VALUE_TYPE (&pcache->value) == GTK_TYPE_SYMBOLIC_COLOR) { @@ -2297,7 +2312,7 @@ _gtk_style_context_peek_style_property (GtkStyleContext *context, else g_value_init (&pcache->value, GDK_TYPE_COLOR); - if (_gtk_style_context_resolve_color (context, color, &rgba, NULL)) + if (_gtk_style_context_resolve_color (context, _gtk_symbolic_color_get_css_value (color), &rgba, NULL)) { if (G_PARAM_SPEC_VALUE_TYPE (pspec) == GDK_TYPE_RGBA) g_value_set_boxed (&pcache->value, &rgba); @@ -2318,6 +2333,8 @@ _gtk_style_context_peek_style_property (GtkStyleContext *context, gtk_symbolic_color_unref (color); } + G_GNUC_END_IGNORE_DEPRECATIONS; + if (priv->widget) gtk_widget_path_free (widget_path); @@ -2608,6 +2625,70 @@ gtk_style_context_get_screen (GtkStyleContext *context) return priv->screen; } +/** + * gtk_style_context_set_frame_clock: + * @context: a #GdkFrameClock + * @frame_clock: a #GdkFrameClock + * + * Attaches @context to the given frame clock. + * + * The frame clock is used for the timing of animations. + * + * If you are using a #GtkStyleContext returned from + * gtk_widget_get_style_context(), you do not need to + * call this yourself. + * + * Since: 3.8 + **/ +void +gtk_style_context_set_frame_clock (GtkStyleContext *context, + GdkFrameClock *frame_clock) +{ + GtkStyleContextPrivate *priv; + + g_return_if_fail (GTK_IS_STYLE_CONTEXT (context)); + g_return_if_fail (frame_clock == NULL || GDK_IS_FRAME_CLOCK (frame_clock)); + + priv = context->priv; + if (priv->frame_clock == frame_clock) + return; + + if (priv->animating) + gtk_style_context_disconnect_update (context); + + if (priv->frame_clock) + g_object_unref (priv->frame_clock); + priv->frame_clock = frame_clock; + if (priv->frame_clock) + g_object_ref (priv->frame_clock); + + if (priv->animating) + gtk_style_context_connect_update (context); + + g_object_notify (G_OBJECT (context), "paint-clock"); +} + +/** + * gtk_style_context_get_frame_clock: + * @context: a #GtkStyleContext + * + * Returns the #GdkFrameClock to which @context is attached. + * + * Returns: (transfer none): a #GdkFrameClock, or %NULL + * if @context does not have an attached frame clock. + * Since: 3.8 + **/ +GdkFrameClock * +gtk_style_context_get_frame_clock (GtkStyleContext *context) +{ + GtkStyleContextPrivate *priv; + + g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), NULL); + + priv = context->priv; + return priv->frame_clock; +} + /** * gtk_style_context_set_direction: * @context: a #GtkStyleContext @@ -2620,19 +2701,38 @@ gtk_style_context_get_screen (GtkStyleContext *context) * call this yourself. * * Since: 3.0 + * + * Deprecated: 3.8: Use gtk_style_context_set_state() with + * #GTK_STATE_FLAG_DIR_LTR and #GTK_STATE_FLAG_DIR_RTL + * instead. **/ void gtk_style_context_set_direction (GtkStyleContext *context, GtkTextDirection direction) { - GtkStyleContextPrivate *priv; + GtkStateFlags state; g_return_if_fail (GTK_IS_STYLE_CONTEXT (context)); - priv = context->priv; - priv->direction = direction; + state = gtk_style_context_get_state (context); + state &= ~(GTK_STATE_FLAG_DIR_LTR | GTK_STATE_FLAG_DIR_RTL); + + switch (direction) + { + case GTK_TEXT_DIR_LTR: + state |= GTK_STATE_FLAG_DIR_LTR; + break; + + case GTK_TEXT_DIR_RTL: + state |= GTK_STATE_FLAG_DIR_RTL; + break; - g_object_notify (G_OBJECT (context), "direction"); + case GTK_TEXT_DIR_NONE: + default: + break; + } + + gtk_style_context_set_state (context, state); } /** @@ -2644,16 +2744,26 @@ gtk_style_context_set_direction (GtkStyleContext *context, * Returns: the widget direction * * Since: 3.0 + * + * Deprecated: 3.8: Use gtk_style_context_get_state() and + * check for #GTK_STATE_FLAG_DIR_LTR and + * #GTK_STATE_FLAG_DIR_RTL instead. **/ GtkTextDirection gtk_style_context_get_direction (GtkStyleContext *context) { - GtkStyleContextPrivate *priv; + GtkStateFlags state; g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), GTK_TEXT_DIR_LTR); - priv = context->priv; - return priv->direction; + state = gtk_style_context_get_state (context); + + if (state & GTK_STATE_FLAG_DIR_LTR) + return GTK_TEXT_DIR_LTR; + else if (state & GTK_STATE_FLAG_DIR_RTL) + return GTK_TEXT_DIR_RTL; + else + return GTK_TEXT_DIR_NONE; } /** @@ -2701,28 +2811,9 @@ gtk_style_context_get_junction_sides (GtkStyleContext *context) return context->priv->info->junction_sides; } -GtkCssValue * -_gtk_style_context_resolve_color_value (GtkStyleContext *context, - GtkCssValue *current, - GtkCssDependencies current_deps, - GtkCssValue *color, - GtkCssDependencies *dependencies) -{ - g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), FALSE); - g_return_val_if_fail (current != NULL, FALSE); - g_return_val_if_fail (color != NULL, FALSE); - - return _gtk_symbolic_color_resolve_full ((GtkSymbolicColor *) color, - GTK_STYLE_PROVIDER_PRIVATE (context->priv->cascade), - current, - current_deps, - dependencies); -} - - gboolean _gtk_style_context_resolve_color (GtkStyleContext *context, - GtkSymbolicColor *color, + GtkCssValue *color, GdkRGBA *result, GtkCssDependencies *dependencies) { @@ -2732,11 +2823,11 @@ _gtk_style_context_resolve_color (GtkStyleContext *context, g_return_val_if_fail (color != NULL, FALSE); g_return_val_if_fail (result != NULL, FALSE); - val = _gtk_symbolic_color_resolve_full (color, - GTK_STYLE_PROVIDER_PRIVATE (context->priv->cascade), - _gtk_style_context_peek_property (context, GTK_CSS_PROPERTY_COLOR), - GTK_CSS_DEPENDS_ON_COLOR, - dependencies); + val = _gtk_css_color_value_resolve (color, + GTK_STYLE_PROVIDER_PRIVATE (context->priv->cascade), + _gtk_style_context_peek_property (context, GTK_CSS_PROPERTY_COLOR), + GTK_CSS_DEPENDS_ON_COLOR, + dependencies); if (val == NULL) return FALSE; @@ -2760,17 +2851,17 @@ gtk_style_context_lookup_color (GtkStyleContext *context, const gchar *color_name, GdkRGBA *color) { - GtkSymbolicColor *sym_color; + GtkCssValue *value; g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), FALSE); g_return_val_if_fail (color_name != NULL, FALSE); g_return_val_if_fail (color != NULL, FALSE); - sym_color = _gtk_style_provider_private_get_color (GTK_STYLE_PROVIDER_PRIVATE (context->priv->cascade), color_name); - if (sym_color == NULL) + value = _gtk_style_provider_private_get_color (GTK_STYLE_PROVIDER_PRIVATE (context->priv->cascade), color_name); + if (value == NULL) return FALSE; - return _gtk_style_context_resolve_color (context, sym_color, color, NULL); + return _gtk_style_context_resolve_color (context, value, color, NULL); } /** @@ -2962,6 +3053,9 @@ gtk_style_context_update_cache (GtkStyleContext *context, GHashTableIter iter; gpointer key, value; + if (_gtk_bitmask_is_empty (parent_changes)) + return; + priv = context->priv; g_hash_table_iter_init (&iter, priv->style_data); @@ -2971,19 +3065,18 @@ gtk_style_context_update_cache (GtkStyleContext *context, StyleData *data = value; GtkBitmask *changes; - changes = _gtk_bitmask_copy (parent_changes); - changes = _gtk_bitmask_intersect (changes, data->store->depends_on_parent); - if (_gtk_bitmask_get (changes, GTK_CSS_PROPERTY_COLOR)) - changes = _gtk_bitmask_union (changes, data->store->depends_on_color); - if (_gtk_bitmask_get (changes, GTK_CSS_PROPERTY_FONT_SIZE)) - changes = _gtk_bitmask_union (changes, data->store->depends_on_font_size); + changes = _gtk_css_computed_values_compute_dependencies (data->store, parent_changes); + + if (!_gtk_bitmask_is_empty (changes)) + build_properties (context, data->store, info, changes); - build_properties (context, data->store, info, changes); + _gtk_bitmask_free (changes); } } static void -gtk_style_context_do_invalidate (GtkStyleContext *context) +gtk_style_context_do_invalidate (GtkStyleContext *context, + const GtkBitmask *changes) { GtkStyleContextPrivate *priv; @@ -2995,11 +3088,11 @@ gtk_style_context_do_invalidate (GtkStyleContext *context) if (priv->invalidating_context) return; - priv->invalidating_context = TRUE; + priv->invalidating_context = changes; g_signal_emit (context, signals[CHANGED], 0); - priv->invalidating_context = FALSE; + priv->invalidating_context = NULL; } static GtkBitmask * @@ -3170,12 +3263,7 @@ _gtk_style_context_validate (GtkStyleContext *context, } else { - changes = _gtk_bitmask_copy (parent_changes); - changes = _gtk_bitmask_intersect (changes, current->store->depends_on_parent); - if (_gtk_bitmask_get (changes, GTK_CSS_PROPERTY_COLOR)) - changes = _gtk_bitmask_union (changes, current->store->depends_on_color); - if (_gtk_bitmask_get (changes, GTK_CSS_PROPERTY_FONT_SIZE)) - changes = _gtk_bitmask_union (changes, current->store->depends_on_font_size); + changes = _gtk_css_computed_values_compute_dependencies (current->store, parent_changes); gtk_style_context_update_cache (context, parent_changes); } @@ -3193,8 +3281,8 @@ _gtk_style_context_validate (GtkStyleContext *context, _gtk_bitmask_free (animation_changes); } - if (!_gtk_bitmask_is_empty (changes)) - gtk_style_context_do_invalidate (context); + if (!_gtk_bitmask_is_empty (changes) || (change & GTK_CSS_CHANGE_FORCE_INVALIDATE)) + gtk_style_context_do_invalidate (context, changes); change = _gtk_css_change_for_child (change); for (list = priv->children; list; list = list->next) @@ -3243,10 +3331,25 @@ _gtk_style_context_queue_invalidate (GtkStyleContext *context, void gtk_style_context_invalidate (GtkStyleContext *context) { + GtkBitmask *changes; + g_return_if_fail (GTK_IS_STYLE_CONTEXT (context)); gtk_style_context_clear_cache (context); - gtk_style_context_do_invalidate (context); + + changes = _gtk_bitmask_new (); + changes = _gtk_bitmask_invert_range (changes, + 0, + _gtk_css_style_property_get_n_properties ()); + gtk_style_context_do_invalidate (context, changes); + _gtk_bitmask_free (changes); +} + +static gboolean +corner_value_is_right_angle (GtkCssValue *value) +{ + return _gtk_css_corner_value_get_x (value, 100) <= 0.0 && + _gtk_css_corner_value_get_y (value, 100) <= 0.0; } /** @@ -3263,21 +3366,33 @@ void gtk_style_context_set_background (GtkStyleContext *context, GdkWindow *window) { - GtkStateFlags state; - GdkRGBA *color; + const GdkRGBA *color; g_return_if_fail (GTK_IS_STYLE_CONTEXT (context)); g_return_if_fail (GDK_IS_WINDOW (window)); - state = gtk_style_context_get_state (context); + /* This is a sophisitcated optimization. + * If we know the GDK window's background will be opaque, we mark + * it as opaque. This is so GDK can do all the optimizations it does + * for opaque windows and be fast. + * This is mainly used when scrolling. + * + * We could indeed just set black instead of the color we have. + */ + color = _gtk_css_rgba_value_get_rgba (_gtk_style_context_peek_property (context, GTK_CSS_PROPERTY_BACKGROUND_COLOR)); - gtk_style_context_get (context, state, - "background-color", &color, - NULL); - if (color) + if (color->alpha >= 1.0 && + corner_value_is_right_angle (_gtk_style_context_peek_property (context, GTK_CSS_PROPERTY_BORDER_TOP_LEFT_RADIUS)) && + corner_value_is_right_angle (_gtk_style_context_peek_property (context, GTK_CSS_PROPERTY_BORDER_TOP_RIGHT_RADIUS)) && + corner_value_is_right_angle (_gtk_style_context_peek_property (context, GTK_CSS_PROPERTY_BORDER_BOTTOM_RIGHT_RADIUS)) && + corner_value_is_right_angle (_gtk_style_context_peek_property (context, GTK_CSS_PROPERTY_BORDER_BOTTOM_LEFT_RADIUS))) { gdk_window_set_background_rgba (window, color); - gdk_rgba_free (color); + } + else + { + GdkRGBA transparent = { 0.0, 0.0, 0.0, 0.0 }; + gdk_window_set_background_rgba (window, &transparent); } } @@ -3487,6 +3602,9 @@ gtk_style_context_get_margin (GtkStyleContext *context, * freed. * * Since: 3.0 + * + * Deprecated: 3.8: Use gtk_style_context_get() for "font" or + * subproperties instead. **/ const PangoFontDescription * gtk_style_context_get_font (GtkStyleContext *context, @@ -3494,7 +3612,7 @@ gtk_style_context_get_font (GtkStyleContext *context, { GtkStyleContextPrivate *priv; StyleData *data; - PangoFontDescription *description; + PangoFontDescription *description, *previous; g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), NULL); @@ -3505,15 +3623,24 @@ gtk_style_context_get_font (GtkStyleContext *context, /* Yuck, fonts are created on-demand but we don't return a ref. * Do bad things to achieve this requirement */ - description = g_object_get_data (G_OBJECT (data->store), "font-cache-for-get_font"); - if (description == NULL) + gtk_style_context_get (context, state, "font", &description, NULL); + + previous = g_object_get_data (G_OBJECT (data->store), "font-cache-for-get_font"); + + if (previous) + { + pango_font_description_merge (previous, description, TRUE); + pango_font_description_free (description); + description = previous; + } + else { - gtk_style_context_get (context, state, "font", &description, NULL); g_object_set_data_full (G_OBJECT (data->store), "font-cache-for-get_font", description, (GDestroyNotify) pango_font_description_free); } + return description; } @@ -4520,6 +4647,26 @@ gtk_draw_insertion_cursor (GtkWidget *widget, draw_arrow); } +/** + * _gtk_style_context_get_changes: + * @context: the context to query + * + * Queries the context for the changes for the currently executing + * GtkStyleContext::invalidate signal. If no signal is currently + * emitted, this function returns %NULL. + * + * FIXME 4.0: Make this part of the signal. + * + * Returns: %NULL or the currently invalidating changes + **/ +const GtkBitmask * +_gtk_style_context_get_changes (GtkStyleContext *context) +{ + g_return_val_if_fail (GTK_IS_STYLE_CONTEXT (context), NULL); + + return context->priv->invalidating_context; +} + static AtkAttributeSet * add_attribute (AtkAttributeSet *attributes, AtkTextAttribute attr,