summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBenjamin Otte <otte@redhat.com>2012-12-13 02:46:09 +0100
committerBenjamin Otte <otte@redhat.com>2013-01-05 20:15:16 +0100
commit46570d6a76df43bf276170cb9c2827aba6134831 (patch)
tree6245ff405e8f87d7fcd5ed9e1a8acccdfc5036f4
parentf7ef7c11d337433844d8450b7277bc61159b27a5 (diff)
downloadgtk+-46570d6a76df43bf276170cb9c2827aba6134831.tar.gz
actors: Make GtkCssActor a style context source
... and add a style_updated signal.
-rw-r--r--gtk/actors/gtkcssactor.c158
-rw-r--r--gtk/actors/gtkcssactorprivate.h4
-rw-r--r--gtk/actors/gtkcssbox.c14
3 files changed, 175 insertions, 1 deletions
diff --git a/gtk/actors/gtkcssactor.c b/gtk/actors/gtkcssactor.c
index 50929090fb..9d43c333d2 100644
--- a/gtk/actors/gtkcssactor.c
+++ b/gtk/actors/gtkcssactor.c
@@ -21,12 +21,17 @@
#include "gtkcssactorprivate.h"
+#include "gtkcontainer.h"
+#include "gtkcontainerprivate.h"
#include "gtkcssboxprivate.h"
+#include "gtkcssmatcherprivate.h"
#include "gtkdebug.h"
#include "gtkintl.h"
#include "gtkprivate.h"
#include "gtkstylecontext.h"
+#include "gtkstylecontextprivate.h"
#include "gtktypebuiltins.h"
+#include "gtkwidgetprivate.h"
struct _GtkCssActorPrivate {
GtkStyleContext *context;
@@ -59,6 +64,8 @@ gtk_css_actor_finalize (GObject *object)
if (priv->context)
{
+ if (gtk_css_actor_owns_context (self))
+ _gtk_style_context_set_source (priv->context, NULL, NULL);
g_object_unref (priv->context);
priv->context = NULL;
}
@@ -145,6 +152,7 @@ gtk_css_actor_set_style_context (GtkCssActor *self,
g_object_notify (G_OBJECT (self), "style-context");
}
+
static void
gtk_css_actor_real_parent_set (GtkActor *actor,
GtkActor *old_parent)
@@ -171,6 +179,12 @@ gtk_css_actor_real_parent_set (GtkActor *actor,
}
static void
+gtk_css_actor_real_style_updated (GtkCssActor *actor,
+ const GtkBitmask *changed)
+{
+}
+
+static void
_gtk_css_actor_class_init (GtkCssActorClass *klass)
{
GObjectClass *object_class = G_OBJECT_CLASS (klass);
@@ -182,6 +196,8 @@ _gtk_css_actor_class_init (GtkCssActorClass *klass)
actor_class->parent_set = gtk_css_actor_real_parent_set;
+ klass->style_updated = gtk_css_actor_real_style_updated;
+
/**
* GtkCssActor:style-context:
*
@@ -217,6 +233,146 @@ _gtk_css_actor_get_style_context (GtkCssActor *actor)
return actor->priv->context;
}
+static gboolean
+actor_needs_to_use_widget_path (GtkActor *actor)
+{
+ GtkWidget *widget, *parent;
+
+ widget = _gtk_actor_get_widget (actor);
+ if (widget == NULL)
+ return FALSE;
+
+ parent = gtk_widget_get_parent (widget);
+ if (parent == NULL)
+ return FALSE;
+
+ if (GTK_CONTAINER_GET_CLASS (parent)->get_path_for_child ==
+ GTK_CONTAINER_CLASS(g_type_class_peek (GTK_TYPE_CONTAINER))->get_path_for_child)
+ return FALSE;
+
+ return TRUE;
+}
+
+static gboolean
+gtk_css_actor_source_init_css_matcher (GtkCssMatcher *matcher,
+ gpointer actor)
+{
+ if (actor_needs_to_use_widget_path (actor))
+ return FALSE;
+
+ _gtk_css_matcher_actor_init (matcher, actor);
+
+ return TRUE;
+}
+
+static GtkWidgetPath *
+gtk_css_actor_source_create_query_path (gpointer actor)
+{
+ GtkWidget *widget;
+
+ widget = _gtk_actor_get_widget (actor);
+ if (widget == NULL)
+ return NULL;
+
+ return _gtk_widget_create_path (widget);
+}
+
+static const GtkWidgetPath *
+gtk_css_actor_source_get_path (gpointer actor)
+{
+ GtkWidget *widget;
+
+ widget = _gtk_actor_get_widget (actor);
+ if (widget == NULL)
+ return NULL;
+
+ return gtk_widget_get_path (widget);
+}
+
+static void
+gtk_css_actor_source_invalidate (gpointer actor)
+{
+ GtkStyleContext *context;
+ GtkActor *iter;
+
+ context = GTK_CSS_ACTOR (actor)->priv->context;
+
+ GTK_CSS_ACTOR_GET_CLASS (actor)->style_updated (actor, _gtk_style_context_get_changes (context));
+
+ for (iter = _gtk_actor_get_first_child (actor);
+ iter != NULL;
+ iter = _gtk_actor_get_next_sibling (iter))
+ {
+ if (!GTK_IS_CSS_ACTOR (iter))
+ continue;
+
+ if (gtk_css_actor_owns_context (GTK_CSS_ACTOR (iter)))
+ continue;
+
+ gtk_css_actor_source_invalidate (iter);
+ }
+}
+
+static void
+gtk_css_actor_source_queue_invalidate (gpointer actor)
+{
+ GtkWidget *widget;
+
+ widget = _gtk_actor_get_widget (actor);
+
+ if (GTK_IS_RESIZE_CONTAINER (widget))
+ _gtk_container_queue_restyle (GTK_CONTAINER (widget));
+}
+
+static gboolean
+gtk_css_actor_source_should_animate (gpointer actor)
+{
+ if (!_gtk_actor_get_mapped (actor))
+ return FALSE;
+
+#if 0
+ gboolean animate;
+
+ g_object_get (gtk_widget_get_settings (widget),
+ "gtk-enable-animations", &animate,
+ NULL);
+
+ return animate;
+#endif
+
+ return TRUE;
+}
+
+static GType
+gtk_css_actor_source_get_widget_type (gpointer actor)
+{
+ GtkWidget *widget;
+
+ widget = _gtk_actor_get_widget (actor);
+ if (widget == NULL)
+ return G_TYPE_INVALID;
+
+ return G_OBJECT_TYPE (widget);
+}
+
+static void
+gtk_css_actor_source_destroy (gpointer actor)
+{
+}
+
+static const GtkStyleContextSource gtk_css_actor_source = {
+ TRUE,
+ FALSE,
+ gtk_css_actor_source_init_css_matcher,
+ gtk_css_actor_source_create_query_path,
+ gtk_css_actor_source_get_path,
+ gtk_css_actor_source_invalidate,
+ gtk_css_actor_source_queue_invalidate,
+ gtk_css_actor_source_should_animate,
+ gtk_css_actor_source_get_widget_type,
+ gtk_css_actor_source_destroy
+};
+
void
_gtk_css_actor_init_box (GtkCssActor *self)
{
@@ -225,6 +381,6 @@ _gtk_css_actor_init_box (GtkCssActor *self)
priv->context = gtk_style_context_new ();
gtk_style_context_set_screen (priv->context, _gtk_actor_get_screen (actor));
- //_gtk_style_context_set_actor (priv->context, actor);
+ _gtk_style_context_set_source (priv->context, &gtk_css_actor_source, actor);
}
diff --git a/gtk/actors/gtkcssactorprivate.h b/gtk/actors/gtkcssactorprivate.h
index cae42bc6c6..9514202e08 100644
--- a/gtk/actors/gtkcssactorprivate.h
+++ b/gtk/actors/gtkcssactorprivate.h
@@ -21,6 +21,7 @@
#define __GTK_CSS_ACTOR_PRIVATE_H__
#include <gtk/actors/gtkactorprivate.h>
+#include <gtk/gtkbitmaskprivate.h>
#include <gtk/gtkstylecontext.h>
G_BEGIN_DECLS
@@ -47,6 +48,9 @@ struct _GtkCssActor
struct _GtkCssActorClass
{
GtkActorClass parent_class;
+
+ void (* style_updated) (GtkCssActor *actor,
+ const GtkBitmask *changed);
};
GType _gtk_css_actor_get_type (void) G_GNUC_CONST;
diff --git a/gtk/actors/gtkcssbox.c b/gtk/actors/gtkcssbox.c
index 1f250e4a84..7da578a002 100644
--- a/gtk/actors/gtkcssbox.c
+++ b/gtk/actors/gtkcssbox.c
@@ -23,6 +23,7 @@
#include "gtkcssenumvalueprivate.h"
#include "gtkcssnumbervalueprivate.h"
+#include "gtkcssstylepropertyprivate.h"
#include "gtkcsstypesprivate.h"
#include "gtkdebug.h"
#include "gtkintl.h"
@@ -474,10 +475,21 @@ gtk_css_box_real_draw (GtkActor *actor,
}
static void
+gtk_css_box_real_style_updated (GtkCssActor *actor,
+ const GtkBitmask *changes)
+{
+ if (_gtk_css_style_property_changes_affect_size (changes))
+ _gtk_actor_queue_relayout (GTK_ACTOR (actor));
+ else
+ _gtk_actor_queue_redraw (GTK_ACTOR (actor));
+}
+
+static void
_gtk_css_box_class_init (GtkCssBoxClass *klass)
{
GObjectClass *object_class = G_OBJECT_CLASS (klass);
GtkActorClass *actor_class = GTK_ACTOR_CLASS (klass);
+ GtkCssActorClass *css_actor_class = GTK_CSS_ACTOR_CLASS (klass);
object_class->finalize = gtk_css_box_finalize;
object_class->set_property = gtk_css_box_set_property;
@@ -492,6 +504,8 @@ _gtk_css_box_class_init (GtkCssBoxClass *klass)
actor_class->get_preferred_size = gtk_css_box_real_get_preferred_size;
actor_class->allocate = gtk_css_box_real_allocate;
+ css_actor_class->style_updated = gtk_css_box_real_style_updated;
+
/**
* GtkCssBox:state:
*