demo: Spice up the mask demo
authorBenjamin Otte <otte@redhat.com>
Tue, 14 Feb 2023 19:16:15 +0000 (20:16 +0100)
committerMatthias Clasen <mclasen@redhat.com>
Wed, 15 Feb 2023 00:07:01 +0000 (19:07 -0500)
Also use all the mask modes, weeeee!

demos/gtk-demo/demo4widget.c
demos/gtk-demo/mask.c

index 0152581c3da3304d11ac3788be8782b8a70618bc..8bee75d8b77a33b099ae7f33a134a36948d23d25 100644 (file)
@@ -2,12 +2,19 @@
 #include "demo4widget.h"
 #include "hsla.h"
 
+enum
+{
+  PROP_0,
+  PROP_PROGRESS,
+};
+
 struct _Demo4Widget
 {
   GtkWidget parent_instance;
   PangoLayout *layout;
   GskColorStop stops[8];
   gsize n_stops;
+  double progress;
 
   guint tick;
 };
@@ -49,6 +56,8 @@ demo4_widget_init (Demo4Widget *self)
 {
   PangoFontDescription *desc;
 
+  self->progress = 0.5;
+
   self->n_stops = 8;
   self->stops[0].offset = 0;
   self->stops[0].color = (GdkRGBA) { 1, 0, 0, 1 };
@@ -83,16 +92,24 @@ demo4_widget_dispose (GObject *object)
 }
 
 static void
-demo4_widget_snapshot (GtkWidget   *widget,
-                       GtkSnapshot *snapshot)
+demo4_widget_snapshot_content (GtkWidget   *widget,
+                               GtkSnapshot *snapshot,
+                               GskMaskMode  mode)
 {
   Demo4Widget *self = DEMO4_WIDGET (widget);
-  int width, height;
+  int width, height, layout_width, layout_height;
+  double scale;
 
   width = gtk_widget_get_width (widget);
   height = gtk_widget_get_height (widget);
 
-  gtk_snapshot_push_mask (snapshot, GSK_MASK_MODE_INVERTED_ALPHA);
+  gtk_snapshot_push_mask (snapshot, mode);
+  pango_layout_get_pixel_size (self->layout, &layout_width, &layout_height);
+  scale = MIN ((double) width / layout_width, (double) height / layout_height);
+  gtk_snapshot_translate (snapshot,
+                          &GRAPHENE_POINT_INIT ((width - scale * layout_width) / 2,
+                                                (height - scale * layout_height) / 2));
+  gtk_snapshot_scale (snapshot, scale, scale);
   gtk_snapshot_append_layout (snapshot, self->layout, &(GdkRGBA) { 0, 0, 0, 1 });
   gtk_snapshot_pop (snapshot);
 
@@ -105,6 +122,84 @@ demo4_widget_snapshot (GtkWidget   *widget,
   gtk_snapshot_pop (snapshot);
 }
 
+static void
+demo4_widget_snapshot (GtkWidget   *widget,
+                       GtkSnapshot *snapshot)
+{
+  Demo4Widget *self = DEMO4_WIDGET (widget);
+  int width, height;
+
+  width = gtk_widget_get_width (widget);
+  height = gtk_widget_get_height (widget);
+
+  gtk_snapshot_push_mask (snapshot, GSK_MASK_MODE_INVERTED_LUMINANCE);
+  gtk_snapshot_append_linear_gradient (snapshot,
+                                       &GRAPHENE_RECT_INIT (0, 0, width, height),
+                                       &GRAPHENE_POINT_INIT (0, 0),
+                                       &GRAPHENE_POINT_INIT (width, 0),
+                                       (GskColorStop[2]) {
+                                         { MAX (0.0, self->progress - 5.0 / width), { 1, 1, 1, 1 } },
+                                         { MIN (1.0, self->progress + 5.0 / width), { 0, 0, 0, 1 } }
+                                       }, 2);
+  gtk_snapshot_pop (snapshot);
+  demo4_widget_snapshot_content (widget, snapshot, GSK_MASK_MODE_INVERTED_ALPHA);
+  gtk_snapshot_pop (snapshot);
+
+  gtk_snapshot_push_mask (snapshot, GSK_MASK_MODE_LUMINANCE);
+  gtk_snapshot_append_linear_gradient (snapshot,
+                                       &GRAPHENE_RECT_INIT (0, 0, width, height),
+                                       &GRAPHENE_POINT_INIT (0, 0),
+                                       &GRAPHENE_POINT_INIT (width, 0),
+                                       (GskColorStop[2]) {
+                                         { MAX (0.0, self->progress - 5.0 / width), { 1, 1, 1, 1 } },
+                                         { MIN (1.0, self->progress + 5.0 / width), { 0, 0, 0, 1 } }
+                                       }, 2);
+  gtk_snapshot_pop (snapshot);
+  demo4_widget_snapshot_content (widget, snapshot, GSK_MASK_MODE_ALPHA);
+  gtk_snapshot_pop (snapshot);
+}
+
+static void
+demo4_widget_set_property (GObject      *object,
+                           guint         prop_id,
+                           const GValue *value,
+                           GParamSpec   *pspec)
+{
+  Demo4Widget *self = DEMO4_WIDGET (object);
+
+  switch (prop_id)
+    {
+    case PROP_PROGRESS:
+      self->progress = g_value_get_double (value);
+      gtk_widget_queue_draw (GTK_WIDGET (object));
+      break;
+
+    default:
+      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
+      break;
+    }
+}
+
+static void
+demo4_widget_get_property (GObject     *object,
+                           guint        prop_id,
+                           GValue      *value,
+                           GParamSpec  *pspec)
+{
+  Demo4Widget *self = DEMO4_WIDGET (object);
+
+  switch (prop_id)
+    {
+    case PROP_PROGRESS:
+      g_value_set_double (value, self->progress);
+      break;
+
+    default:
+      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
+      break;
+    }
+}
+
 static void
 demo4_widget_class_init (Demo4WidgetClass *class)
 {
@@ -112,8 +207,15 @@ demo4_widget_class_init (Demo4WidgetClass *class)
   GtkWidgetClass *widget_class = GTK_WIDGET_CLASS (class);
 
   object_class->dispose = demo4_widget_dispose;
+  object_class->get_property = demo4_widget_get_property;
+  object_class->set_property = demo4_widget_set_property;
 
   widget_class->snapshot = demo4_widget_snapshot;
+
+  g_object_class_install_property (object_class, PROP_PROGRESS,
+      g_param_spec_double ("progress", NULL, NULL,
+                           0.0, 1.0, 0.5,
+                           G_PARAM_READWRITE));
 }
 
 GtkWidget *
@@ -121,3 +223,4 @@ demo4_widget_new (void)
 {
   return g_object_new (DEMO4_TYPE_WIDGET, NULL);
 }
+
index 4266b44b52e9fed276fb5589f549d0f246396449..ad846ab2d4295bc6fe63278cb0b77f5b34210576 100644 (file)
@@ -18,7 +18,8 @@ do_mask (GtkWidget *do_widget)
   if (!window)
     {
       GtkWidget *box;
-      GtkWidget *widget;
+      GtkWidget *demo;
+      GtkWidget *scale;
 
       window = gtk_window_new ();
       gtk_window_set_title (GTK_WINDOW (window), "Mask Nodes");
@@ -30,11 +31,17 @@ do_mask (GtkWidget *do_widget)
       box = gtk_box_new (GTK_ORIENTATION_VERTICAL, 0);
       gtk_window_set_child (GTK_WINDOW (window), box);
 
-      widget = demo4_widget_new ();
-      gtk_widget_set_hexpand (widget, TRUE);
-      gtk_widget_set_vexpand (widget, TRUE);
+      demo = demo4_widget_new ();
+      gtk_widget_set_hexpand (demo, TRUE);
+      gtk_widget_set_vexpand (demo, TRUE);
 
-      gtk_box_append (GTK_BOX (box), widget);
+      gtk_box_append (GTK_BOX (box), demo);
+
+      scale = gtk_scale_new_with_range (GTK_ORIENTATION_HORIZONTAL, 0, 1, 0.1);
+      gtk_range_set_value (GTK_RANGE (scale), 0.5);
+      g_object_bind_property (gtk_range_get_adjustment (GTK_RANGE (scale)), "value", demo, "progress", 0);
+
+      gtk_box_append (GTK_BOX (box), scale);
     }
 
   if (!gtk_widget_get_visible (window))