st: Track stylesheet changes on the StThemeContext
Instead of every individual StThemeNode. There are essentially two kinds of theme nodes: Those we create for lookups, and those interned by the theme context and used by StWidgets. Listening to the signal on the former is pointless as they are short lived and not meant to be really used for drawing. So it is only essential to track stylesheet changes in those we intern for later use. This change does precisely that, it lets the StThemeContext track the stylesheet changes and let all known theme nodes reset their state for it. The internal array holding all connected handlers for this signal in glib was about the biggest single allocation made in gnome-shell, as interned theme nodes nodes are around the 4 to 5 digit numbers. This essentially makes it disappear. This however means that widgets that are explicitly set a theme through st_widget_set_theme() don't get their theme node implicitly updated. There's little reasons to use that API, so perhaps this is an acceptable tradeoff. https://gitlab.gnome.org/GNOME/gnome-shell/merge_requests/779
This commit is contained in:
parent
55867c40c4
commit
6a42d77261
@ -25,6 +25,7 @@
|
||||
#include "st-texture-cache.h"
|
||||
#include "st-theme.h"
|
||||
#include "st-theme-context.h"
|
||||
#include "st-theme-node-private.h"
|
||||
|
||||
struct _StThemeContext {
|
||||
GObject parent;
|
||||
@ -36,6 +37,8 @@ struct _StThemeContext {
|
||||
/* set of StThemeNode */
|
||||
GHashTable *nodes;
|
||||
|
||||
gulong stylesheets_changed_id;
|
||||
|
||||
int scale_factor;
|
||||
};
|
||||
|
||||
@ -83,6 +86,8 @@ st_theme_context_finalize (GObject *object)
|
||||
(gpointer) st_theme_context_changed,
|
||||
context);
|
||||
|
||||
g_clear_signal_handler (&context->stylesheets_changed_id, context->theme);
|
||||
|
||||
if (context->nodes)
|
||||
g_hash_table_unref (context->nodes);
|
||||
if (context->root_node)
|
||||
@ -254,6 +259,19 @@ on_icon_theme_changed (StTextureCache *cache,
|
||||
g_source_set_name_by_id (id, "[gnome-shell] changed_idle");
|
||||
}
|
||||
|
||||
static void
|
||||
on_custom_stylesheets_changed (StTheme *theme,
|
||||
StThemeContext *context)
|
||||
{
|
||||
GHashTableIter iter;
|
||||
StThemeNode *node;
|
||||
|
||||
g_hash_table_iter_init (&iter, context->nodes);
|
||||
|
||||
while (g_hash_table_iter_next (&iter, (gpointer *) &node, NULL))
|
||||
_st_theme_node_reset_for_stylesheet_change (node);
|
||||
}
|
||||
|
||||
/**
|
||||
* st_theme_context_get_for_stage:
|
||||
* @stage: a #ClutterStage
|
||||
@ -299,12 +317,17 @@ st_theme_context_set_theme (StThemeContext *context,
|
||||
if (context->theme != theme)
|
||||
{
|
||||
if (context->theme)
|
||||
g_object_unref (context->theme);
|
||||
g_clear_signal_handler (&context->stylesheets_changed_id, context->theme);
|
||||
|
||||
context->theme = theme;
|
||||
g_set_object (&context->theme, theme);
|
||||
|
||||
if (context->theme)
|
||||
g_object_ref (context->theme);
|
||||
{
|
||||
context->stylesheets_changed_id =
|
||||
g_signal_connect (context->theme, "custom-stylesheets-changed",
|
||||
G_CALLBACK (on_custom_stylesheets_changed),
|
||||
context);
|
||||
}
|
||||
|
||||
st_theme_context_changed (context);
|
||||
}
|
||||
|
@ -123,6 +123,7 @@ void _st_theme_node_ensure_background (StThemeNode *node);
|
||||
void _st_theme_node_ensure_geometry (StThemeNode *node);
|
||||
void _st_theme_node_apply_margins (StThemeNode *node,
|
||||
ClutterActor *actor);
|
||||
void _st_theme_node_reset_for_stylesheet_change (StThemeNode *node);
|
||||
|
||||
G_END_DECLS
|
||||
|
||||
|
@ -77,16 +77,13 @@ maybe_free_properties (StThemeNode *node)
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
on_custom_stylesheets_changed (StTheme *theme,
|
||||
gpointer data)
|
||||
void
|
||||
_st_theme_node_reset_for_stylesheet_change (StThemeNode *node)
|
||||
{
|
||||
StThemeNode *node = data;
|
||||
maybe_free_properties (node);
|
||||
node->properties_computed = FALSE;
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
st_theme_node_dispose (GObject *gobject)
|
||||
{
|
||||
@ -110,12 +107,6 @@ st_theme_node_dispose (GObject *gobject)
|
||||
node->icon_colors = NULL;
|
||||
}
|
||||
|
||||
if (node->theme && node->stylesheets_changed_id)
|
||||
{
|
||||
g_signal_handler_disconnect (node->theme, node->stylesheets_changed_id);
|
||||
node->stylesheets_changed_id = 0;
|
||||
}
|
||||
|
||||
st_theme_node_paint_state_free (&node->cached_state);
|
||||
|
||||
g_clear_object (&node->theme);
|
||||
@ -228,14 +219,7 @@ st_theme_node_new (StThemeContext *context,
|
||||
if (theme == NULL && parent_node != NULL)
|
||||
theme = parent_node->theme;
|
||||
|
||||
if (theme != NULL)
|
||||
{
|
||||
node->theme = g_object_ref (theme);
|
||||
node->stylesheets_changed_id =
|
||||
g_signal_connect (node->theme, "custom-stylesheets-changed",
|
||||
G_CALLBACK (on_custom_stylesheets_changed), node);
|
||||
}
|
||||
|
||||
g_set_object (&node->theme, theme);
|
||||
node->element_type = element_type;
|
||||
node->element_id = g_strdup (element_id);
|
||||
node->element_classes = split_on_whitespace (element_class);
|
||||
|
Loading…
Reference in New Issue
Block a user