[libadwaita/wip/cdavis/fold-threshold-policy: 1/2] leaflet: Add fold-threshold-policy property




commit 201ea6df9df512f80984180d13dc93b1eec21aac
Author: Christopher Davis <christopherdavis gnome org>
Date:   Wed Jun 23 16:29:30 2021 -0700

    leaflet: Add fold-threshold-policy property
    
    A followup to the previous commit; We use AdwFoldThresholdPolicy
    to determine the size at which a leaflet should fold, which
    may help with case like Fractal where the leaflet folds too
    early.

 src/adw-leaflet.c | 91 +++++++++++++++++++++++++++++++++++++++++++++++++++----
 src/adw-leaflet.h |  6 ++++
 2 files changed, 91 insertions(+), 6 deletions(-)
---
diff --git a/src/adw-leaflet.c b/src/adw-leaflet.c
index e925e5ba..20318985 100644
--- a/src/adw-leaflet.c
+++ b/src/adw-leaflet.c
@@ -10,6 +10,7 @@
 #include "gtkprogresstrackerprivate.h"
 #include "adw-animation-private.h"
 #include "adw-enums-private.h"
+#include "adw-fold-threshold-policy.h"
 #include "adw-leaflet.h"
 #include "adw-shadow-helper-private.h"
 #include "adw-swipeable.h"
@@ -66,6 +67,7 @@
 enum {
   PROP_0,
   PROP_FOLDED,
+  PROP_FOLD_THRESHOLD_POLICY,
   PROP_HHOMOGENEOUS_FOLDED,
   PROP_VHOMOGENEOUS_FOLDED,
   PROP_HHOMOGENEOUS_UNFOLDED,
@@ -133,6 +135,7 @@ struct _AdwLeaflet {
   AdwLeafletPage *last_visible_child;
 
   gboolean folded;
+  AdwFoldThresholdPolicy fold_threshold_policy;
 
   gboolean homogeneous[ADW_FOLD_MAX][GTK_ORIENTATION_MAX];
 
@@ -1948,7 +1951,7 @@ adw_leaflet_size_allocate (GtkWidget *widget,
 
   /* Check whether the children should be stacked or not. */
   if (self->can_unfold) {
-    int nat_box_size = 0, nat_max_size = 0, visible_children = 0;
+    int nat_box_size = 0, nat_max_size = 0, min_box_size = 0, min_max_size = 0, visible_children = 0;
 
     if (orientation == GTK_ORIENTATION_HORIZONTAL) {
 
@@ -1963,12 +1966,21 @@ adw_leaflet_size_allocate (GtkWidget *widget,
           continue;
 
         nat_box_size += page->nat.width;
+        min_box_size += page->min.width;
         nat_max_size = MAX (nat_max_size, page->nat.width);
+        min_max_size = MAX (min_max_size, page->min.width);
         visible_children++;
       }
-      if (self->homogeneous[ADW_FOLD_UNFOLDED][GTK_ORIENTATION_HORIZONTAL])
+
+      if (self->homogeneous[ADW_FOLD_UNFOLDED][GTK_ORIENTATION_HORIZONTAL]) {
         nat_box_size = nat_max_size * visible_children;
-      folded = visible_children > 1 && width < nat_box_size;
+        min_box_size = min_max_size * visible_children;
+      }
+
+      if (self->fold_threshold_policy == ADW_FOLD_THRESHOLD_POLICY_NATURAL)
+        folded = visible_children > 1 && width < nat_box_size;
+      else
+        folded = visible_children > 1 && width < min_box_size;
     }
     else {
       for (children = directed_children; children; children = children->next) {
@@ -1982,12 +1994,21 @@ adw_leaflet_size_allocate (GtkWidget *widget,
           continue;
 
         nat_box_size += page->nat.height;
+        min_box_size += page->min.height;
         nat_max_size = MAX (nat_max_size, page->nat.height);
+        min_max_size = MAX (min_max_size, page->min.height);
         visible_children++;
       }
-      if (self->homogeneous[ADW_FOLD_UNFOLDED][GTK_ORIENTATION_VERTICAL])
+
+      if (self->homogeneous[ADW_FOLD_UNFOLDED][GTK_ORIENTATION_VERTICAL]) {
         nat_box_size = nat_max_size * visible_children;
-      folded = visible_children > 1 && height < nat_box_size;
+        min_box_size = min_max_size * visible_children;
+      }
+
+      if (self->fold_threshold_policy == ADW_FOLD_THRESHOLD_POLICY_NATURAL)
+        folded = visible_children > 1 && height < nat_box_size;
+      else
+        folded = visible_children > 1 && height < min_box_size;
     }
   } else {
     folded = TRUE;
@@ -2111,6 +2132,9 @@ adw_leaflet_get_property (GObject    *object,
   case PROP_FOLDED:
     g_value_set_boolean (value, adw_leaflet_get_folded (self));
     break;
+  case PROP_FOLD_THRESHOLD_POLICY:
+    g_value_set_enum (value, adw_leaflet_get_fold_threshold_policy (self));
+    break;
   case PROP_HHOMOGENEOUS_FOLDED:
     g_value_set_boolean (value, adw_leaflet_get_homogeneous (self, TRUE, GTK_ORIENTATION_HORIZONTAL));
     break;
@@ -2173,6 +2197,9 @@ adw_leaflet_set_property (GObject      *object,
   AdwLeaflet *self = ADW_LEAFLET (object);
 
   switch (prop_id) {
+  case PROP_FOLD_THRESHOLD_POLICY:
+    adw_leaflet_set_fold_threshold_policy (self, g_value_get_enum (value));
+    break;
   case PROP_HHOMOGENEOUS_FOLDED:
     adw_leaflet_set_homogeneous (self, TRUE, GTK_ORIENTATION_HORIZONTAL, g_value_get_boolean (value));
     break;
@@ -2280,7 +2307,7 @@ adw_leaflet_class_init (AdwLeafletClass *klass)
    * Whether the leaflet is folded.
    *
    * The leaflet will be folded if the size allocated to it is smaller than the
-   * sum of the natural size of its children, it will be unfolded otherwise.
+   * sum of the fold threshold policy, it will be unfolded otherwise.
    *
    * Since: 1.0
    */
@@ -2291,6 +2318,20 @@ adw_leaflet_class_init (AdwLeafletClass *klass)
                           FALSE,
                           G_PARAM_READABLE | G_PARAM_EXPLICIT_NOTIFY);
 
+  /**
+   * AdwLeaflet:fold-threshold-policy: (attributes 
org.gtk.Property.get=adw_leaflet_get_fold_threshold_policy 
org.gtk.Property.set=adw_leaflet_set_fold_threshold_policy)
+   *
+   * Determines the threshold at which the leaflet will fold.
+   *
+   * Since: 1.0
+   */
+  props[PROP_FOLD_THRESHOLD_POLICY] =
+    g_param_spec_enum ("fold-threshold-policy",
+                       "Fold Threshold Policy",
+                       "Determines the threshold at which the leaflet will fold.",
+                       ADW_TYPE_FOLD_THRESHOLD_POLICY, ADW_FOLD_THRESHOLD_POLICY_NATURAL,
+                       G_PARAM_READWRITE | G_PARAM_EXPLICIT_NOTIFY);
+
   /**
    * AdwLeaflet:hhomogeneous-folded: (attributes org.gtk.Property.get=adw_leaflet_get_homogeneous 
org.gtk.Property.set=adw_leaflet_set_homogeneous)
    *
@@ -2541,6 +2582,7 @@ adw_leaflet_init (AdwLeaflet *self)
   self->children_reversed = NULL;
   self->visible_child = NULL;
   self->folded = FALSE;
+  self->fold_threshold_policy = ADW_FOLD_THRESHOLD_POLICY_NATURAL;
   self->homogeneous[ADW_FOLD_UNFOLDED][GTK_ORIENTATION_HORIZONTAL] = FALSE;
   self->homogeneous[ADW_FOLD_UNFOLDED][GTK_ORIENTATION_VERTICAL] = FALSE;
   self->homogeneous[ADW_FOLD_FOLDED][GTK_ORIENTATION_HORIZONTAL] = TRUE;
@@ -3753,3 +3795,40 @@ adw_leaflet_get_pages (AdwLeaflet *self)
 
   return self->pages;
 }
+
+/**
+ * adw_leaflet_get_fold_threshold_policy: (attributes org.gtk.Method.get_property=fold-threshold-policy)
+ * @self: a `AdwLeaflet`
+ *
+ * Gets the fold threshold policy for @self.
+ *
+ * Since: 1.0
+ */
+AdwFoldThresholdPolicy
+adw_leaflet_get_fold_threshold_policy (AdwLeaflet *self)
+{
+  g_return_val_if_fail (ADW_IS_LEAFLET (self), ADW_FOLD_THRESHOLD_POLICY_NATURAL);
+
+  return self->fold_threshold_policy;
+}
+
+
+/**
+ * adw_leaflet_set_fold_threshold_policy: (attributes org.gtk.Method.set_property=fold-threshold-policy)
+ * @self: a `AdwLeaflet`
+ * @policy: a `AdwFoldThresholdPolicy`
+ *
+ * Sets the fold threshold policy for @self.
+ *
+ * Since: 1.0
+ */
+void
+adw_leaflet_set_fold_threshold_policy (AdwLeaflet             *self,
+                                       AdwFoldThresholdPolicy  policy)
+{
+  g_return_if_fail (ADW_IS_LEAFLET (self));
+
+  self->fold_threshold_policy = policy;
+
+  g_object_notify_by_pspec (G_OBJECT (self), props[PROP_FOLD_THRESHOLD_POLICY]);
+}
diff --git a/src/adw-leaflet.h b/src/adw-leaflet.h
index c6fdad78..a820bd55 100644
--- a/src/adw-leaflet.h
+++ b/src/adw-leaflet.h
@@ -14,6 +14,7 @@
 
 #include <gtk/gtk.h>
 #include "adw-enums.h"
+#include "adw-fold-threshold-policy.h"
 #include "adw-navigation-direction.h"
 
 G_BEGIN_DECLS
@@ -160,4 +161,9 @@ void     adw_leaflet_set_can_unfold (AdwLeaflet *self,
 ADW_AVAILABLE_IN_ALL
 GtkSelectionModel *adw_leaflet_get_pages (AdwLeaflet *self) G_GNUC_WARN_UNUSED_RESULT;
 
+ADW_AVAILABLE_IN_ALL
+AdwFoldThresholdPolicy adw_leaflet_get_fold_threshold_policy (AdwLeaflet             *self);
+ADW_AVAILABLE_IN_ALL
+void                   adw_leaflet_set_fold_threshold_policy (AdwLeaflet             *self,
+                                                              AdwFoldThresholdPolicy  policy);
 G_END_DECLS


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]