[gnome-calendar/wip/gbsneto/month-cell-subwindow] month-view: fight the sizing machinery even harder
- From: Georges Basile Stavracas Neto <gbsneto src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gnome-calendar/wip/gbsneto/month-cell-subwindow] month-view: fight the sizing machinery even harder
- Date: Mon, 13 Nov 2017 17:24:51 +0000 (UTC)
commit 6ad701adb3f3148749810832dd5446582a3ec23a
Author: Georges Basile Stavracas Neto <georges stavracas gmail com>
Date: Mon Nov 13 15:21:20 2017 -0200
month-view: fight the sizing machinery even harder
Make sure something changed in child widgets AND events,
otherwise just top allocating at all.
src/views/gcal-month-view.c | 65 +++++++++++++++++++++++++++++++++++++-----
1 files changed, 57 insertions(+), 8 deletions(-)
---
diff --git a/src/views/gcal-month-view.c b/src/views/gcal-month-view.c
index 0a64e5f..d1950a1 100644
--- a/src/views/gcal-month-view.c
+++ b/src/views/gcal-month-view.c
@@ -121,12 +121,14 @@ struct _GcalMonthView
/* Storage for the accumulated scrolling */
gdouble scroll_value;
-
guint update_grid_id;
/* property */
icaltimetype *date;
GcalManager *manager;
+
+ gboolean pending_event_allocation;
+ gboolean pending_child_allocation;
};
#define MIRROR(val,start,end) (start + (val / end) * end + (end - val % end))
@@ -472,8 +474,10 @@ static gboolean
update_month_cells (GcalMonthView *self)
{
g_autoptr (GDateTime) dt;
+ gboolean changed;
guint row, col;
+ changed = FALSE;
dt = g_date_time_new_local (self->date->year, self->date->month, 1, 0, 0, 0);
for (row = 0; row < 6; row++)
@@ -496,18 +500,27 @@ update_month_cells (GcalMonthView *self)
/* Cell date */
cell_date = g_date_time_add_days (dt, row * 7 + col - self->days_delay);
+
+ changed |= datetime_compare_date (gcal_month_cell_get_date (cell), cell_date) != 0;
+
gcal_month_cell_set_date (cell, cell_date);
/* Different month */
different_month = day < self->days_delay ||
day - self->days_delay >= icaltime_days_in_month (self->date->month,
self->date->year);
+ changed |= different_month != gcal_month_cell_get_different_month (cell);
+
gcal_month_cell_set_different_month (cell, different_month);
if (different_month)
{
+ changed |= gcal_month_cell_get_selected (cell) != FALSE;
gcal_month_cell_set_selected (cell, FALSE);
+
+ changed |= gcal_month_cell_get_overflow (cell) != 0;
gcal_month_cell_set_overflow (cell, 0);
+
continue;
}
@@ -515,6 +528,8 @@ update_month_cells (GcalMonthView *self)
if (g_hash_table_contains (self->overflow_cells, GINT_TO_POINTER (day)))
l = g_hash_table_lookup (self->overflow_cells, GINT_TO_POINTER (day));
+ changed |= gcal_month_cell_get_overflow (cell) != g_list_length (l);
+
gcal_month_cell_set_overflow (cell, l ? g_list_length (l) : 0);
/* Selection */
@@ -538,11 +553,14 @@ update_month_cells (GcalMonthView *self)
datetime_compare_date (gcal_month_cell_get_date (cell), selection_end) <= 0;
}
+ changed |= gcal_month_cell_get_selected (cell) != selected;
+
gcal_month_cell_set_selected (cell, selected);
}
}
self->update_grid_id = 0;
+ self->pending_child_allocation = changed;
return G_SOURCE_REMOVE;
}
@@ -878,11 +896,13 @@ gcal_month_view_component_added (ECalDataModelSubscriber *subscriber,
ECalClient *client,
ECalComponent *comp)
{
+ GcalMonthView *self;
GtkWidget *event_widget;
GcalEvent *event;
GError *error;
error = NULL;
+ self = GCAL_MONTH_VIEW (subscriber);
event = gcal_event_new (e_client_get_source (E_CLIENT (client)), comp, &error);
if (error)
@@ -898,6 +918,8 @@ gcal_month_view_component_added (ECalDataModelSubscriber *subscriber,
gtk_widget_show (event_widget);
gtk_container_add (GTK_CONTAINER (subscriber), event_widget);
+ self->pending_event_allocation = TRUE;
+
g_clear_object (&event);
}
@@ -942,6 +964,8 @@ gcal_month_view_component_modified (ECalDataModelSubscriber *subscriber,
gtk_widget_destroy (new_widget);
}
+ self->pending_event_allocation = TRUE;
+
g_clear_object (&event);
}
@@ -976,6 +1000,8 @@ gcal_month_view_component_removed (ECalDataModelSubscriber *subscriber,
}
gtk_widget_destroy (l->data);
+
+ self->pending_event_allocation = TRUE;
}
static void
@@ -1439,6 +1465,18 @@ gcal_month_view_size_allocate (GtkWidget *widget,
self = gcal_month_view_get_instance_private (GCAL_MONTH_VIEW (widget));
+ /*
+ * If nothing changed, and the month cells didn't request an allocation,
+ * and the size is the same, return early here.
+ */
+ if (!self->pending_event_allocation &&
+ !self->pending_child_allocation &&
+ allocation->width == gtk_widget_get_allocated_width (widget) &&
+ allocation->height == gtk_widget_get_allocated_height (widget))
+ {
+ return;
+ }
+
/* Remove every widget' parts, but the master widget */
widgets = g_hash_table_get_values (self->children);
@@ -1513,7 +1551,6 @@ gcal_month_view_size_allocate (GtkWidget *widget,
all_day = gcal_event_get_all_day (event);
child_context = gtk_widget_get_style_context (l->data);
- gtk_widget_show (child_widget);
gtk_widget_get_preferred_height (child_widget, &minimum_height, NULL);
/*
@@ -1622,9 +1659,9 @@ gcal_month_view_size_allocate (GtkWidget *widget,
if (cell != 0)
{
child_widget = gcal_event_widget_clone (GCAL_EVENT_WIDGET (child_widget));
+ gtk_widget_show (child_widget);
setup_child_widget (self, child_widget);
- gtk_widget_show (child_widget);
child_context = gtk_widget_get_style_context (child_widget);
@@ -1637,7 +1674,7 @@ gcal_month_view_size_allocate (GtkWidget *widget,
{
gint idx;
- gtk_widget_hide (child_widget);
+ gtk_widget_set_child_visible (child_widget, FALSE);
for (idx = cell_idx; idx < cell_idx + length; idx++)
{
@@ -1661,7 +1698,7 @@ gcal_month_view_size_allocate (GtkWidget *widget,
gtk_widget_get_allocation (month_cell, &cell_alloc);
- gtk_widget_get_preferred_height (child_widget, &minimum_height, NULL);
+ gtk_widget_set_child_visible (child_widget, TRUE);
/*
* Setup the widget's start date as the first day of the row,
@@ -1692,6 +1729,12 @@ gcal_month_view_size_allocate (GtkWidget *widget,
remove_cell_border_and_padding (month_cell, &pos_x, &pos_y, &width);
+ /*
+ * We can only get the minimum height after making all these calculations,
+ * otherwise GTK complains about allocating without calling get_preferred_height.
+ */
+ gtk_widget_get_preferred_height (child_widget, &minimum_height, NULL);
+
child_allocation.x = pos_x;
child_allocation.y = pos_y + vertical_cell_space[cell_idx] - size_left[cell_idx];
child_allocation.width = width - (margin.left + margin.right);
@@ -1740,7 +1783,7 @@ gcal_month_view_size_allocate (GtkWidget *widget,
event = gcal_event_widget_get_event (aux->data);
uuid = gcal_event_get_uid (event);
- if (!gtk_widget_is_visible (child_widget))
+ if (!gtk_widget_get_child_visible (child_widget))
continue;
gtk_widget_show (child_widget);
@@ -1749,7 +1792,7 @@ gcal_month_view_size_allocate (GtkWidget *widget,
/* No space left, add to the overflow and continue */
if (size_left[cell] < minimum_height)
{
- gtk_widget_hide (child_widget);
+ gtk_widget_set_child_visible (child_widget, FALSE);
l = g_hash_table_lookup (self->overflow_cells, GINT_TO_POINTER (cell));
l = g_list_append (l, child_widget);
@@ -1776,7 +1819,8 @@ gcal_month_view_size_allocate (GtkWidget *widget,
child_allocation.y = pos_y + vertical_cell_space[cell] - size_left[cell];
child_allocation.width = width - (margin.left + margin.right);
child_allocation.height = minimum_height;
- gtk_widget_show (child_widget);
+
+ gtk_widget_set_child_visible (child_widget, TRUE);
gtk_widget_size_allocate (child_widget, &child_allocation);
size_left[cell] -= minimum_height + margin.top + margin.bottom;
@@ -1784,6 +1828,9 @@ gcal_month_view_size_allocate (GtkWidget *widget,
}
queue_update_month_cells (self);
+
+ self->pending_event_allocation = FALSE;
+ self->pending_child_allocation = FALSE;
}
static gboolean
@@ -2007,6 +2054,8 @@ gcal_month_view_init (GcalMonthView *self)
self->children = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, (GDestroyNotify) g_list_free);
self->single_cell_children = g_hash_table_new_full (g_direct_hash, g_direct_equal, NULL, (GDestroyNotify)
g_list_free);
self->overflow_cells = g_hash_table_new_full (g_direct_hash, g_direct_equal, NULL, (GDestroyNotify)
g_list_free);
+ self->pending_event_allocation = FALSE;
+ self->pending_child_allocation = FALSE;
self->k = gtk_widget_get_direction (GTK_WIDGET (self)) == GTK_TEXT_DIR_RTL;
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]