Last active
April 17, 2025 14:17
-
-
Save luigifab/0fce786cdb93b5687069a82f490ea95e to your computer and use it in GitHub Desktop.
gtk3-classic (GTK 3.24.49) & gtk4-classic (GTK 4.18.4) & gtk5-classic (xptdr) - for Debian Testing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# GtkWindow3: restore focus on application start (GTK_FOCUS_VISIBLE=1) | |
# https://github.com/GNOME/gtk/blob/3.24.37/gtk/gtkwindow.c | |
Index: b/gtk/gtkwindow.c | |
=================================================================== | |
--- a/gtk/gtkwindow.c | |
+++ b/gtk/gtkwindow.c | |
@@ -6357,7 +6357,9 @@ gtk_window_map | |
/* inherit from transient parent, so that a dialog that is | |
* opened via keynav shows focus initially | |
*/ | |
- if (priv->transient_parent) | |
+ if (g_strcmp0 (g_getenv ("GTK_FOCUS_VISIBLE"), "1") == 0) | |
+ gtk_window_set_focus_visible (window, TRUE); | |
+ else if (priv->transient_parent) | |
gtk_window_set_focus_visible (window, gtk_window_get_focus_visible (priv->transient_parent)); | |
else | |
gtk_window_set_focus_visible (window, FALSE); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# GtkWindow4: restore focus on application start (GTK_FOCUS_VISIBLE=1) | |
# https://github.com/GNOME/gtk/blob/4.12.3/gtk/gtkwindow.c | |
# @todo: with awf-gtk4, compared to awf-gtk3, focus is not on the first toolbar button, why? | |
Index: b/gtk/gtkwindow.c | |
=================================================================== | |
--- a/gtk/gtkwindow.c | |
+++ b/gtk/gtkwindow.c | |
@@ -4013,7 +4013,9 @@ gtk_window_map | |
/* inherit from transient parent, so that a dialog that is | |
* opened via keynav shows focus initially | |
*/ | |
- if (priv->transient_parent) | |
+ if (g_strcmp0 (g_getenv ("GTK_FOCUS_VISIBLE"), "1") == 0) | |
+ gtk_window_set_focus_visible (window, TRUE); | |
+ else if (priv->transient_parent) | |
gtk_window_set_focus_visible (window, gtk_window_get_focus_visible (priv->transient_parent)); | |
else | |
gtk_window_set_focus_visible (window, FALSE); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# GtkNotebook3: add classes for stack widget | |
# default way: notebook header.top.bottom.left.right + notebook stack | |
# updated way: notebook header.top.bottom.left.right + notebook stack.top.bottom.left.right | |
# https://github.com/GNOME/gtk/blob/3.24.37/gtk/gtknotebook.c | |
Index: b/gtk/gtknotebook.c | |
=================================================================== | |
--- a/gtk/gtknotebook.c | |
+++ b/gtk/gtknotebook.c | |
@@ -1351,6 +1351,7 @@ gtk_notebook_init | |
gtk_notebook_draw_stack, | |
NULL, | |
NULL); | |
+ gtk_css_gadget_add_class (priv->stack_gadget, GTK_STYLE_CLASS_TOP); | |
gtk_css_gadget_set_state (priv->stack_gadget, gtk_css_node_get_state (widget_node)); | |
gtk_box_gadget_insert_gadget (GTK_BOX_GADGET (priv->gadget), -1, priv->stack_gadget, TRUE, GTK_ALIGN_FILL); | |
@@ -7074,9 +7075,15 @@ gtk_notebook_update_tab_pos | |
for (i = 0; i < G_N_ELEMENTS (tab_pos_names); i++) | |
{ | |
if (tab_pos == i) | |
+ { | |
+ gtk_css_gadget_add_class (priv->stack_gadget, tab_pos_names[i]); | |
gtk_css_gadget_add_class (priv->header_gadget, tab_pos_names[i]); | |
+ } | |
else | |
+ { | |
+ gtk_css_gadget_remove_class (priv->stack_gadget, tab_pos_names[i]); | |
gtk_css_gadget_remove_class (priv->header_gadget, tab_pos_names[i]); | |
+ } | |
} | |
gtk_box_gadget_remove_gadget (GTK_BOX_GADGET (priv->gadget), priv->header_gadget); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# GtkNotebook4: add classes for stack widget (warning! left/right not inverted in rtl with gtk4) | |
# default way: notebook header.top.bottom.left.right + notebook stack | |
# updated way: notebook header.top.bottom.left.right + notebook stack.top.bottom.left.right | |
# https://github.com/GNOME/gtk/blob/4.12.3/gtk/gtknotebook.c | |
Index: b/gtk/gtknotebook.c | |
=================================================================== | |
--- a/gtk/gtknotebook.c | |
+++ b/gtk/gtknotebook.c | |
@@ -1492,6 +1492,7 @@ gtk_notebook_init | |
gtk_widget_set_hexpand (notebook->stack_widget, TRUE); | |
gtk_widget_set_vexpand (notebook->stack_widget, TRUE); | |
gtk_widget_set_parent (notebook->stack_widget, GTK_WIDGET (notebook)); | |
+ gtk_widget_add_css_class (notebook->stack_widget, "top"); | |
dest = gtk_drop_target_new (GTK_TYPE_NOTEBOOK_PAGE, GDK_ACTION_MOVE); | |
gtk_drop_target_set_preload (dest, TRUE); | |
@@ -6214,9 +6214,15 @@ gtk_notebook_update_tab_pos | |
for (i = 0; i < G_N_ELEMENTS (tab_pos_names); i++) | |
{ | |
if (tab_pos == i) | |
+ { | |
+ gtk_widget_add_css_class (notebook->stack_widget, tab_pos_names[i]); | |
gtk_widget_add_css_class (notebook->header_widget, tab_pos_names[i]); | |
+ } | |
else | |
+ { | |
+ gtk_widget_remove_css_class (notebook->stack_widget, tab_pos_names[i]); | |
gtk_widget_remove_css_class (notebook->header_widget, tab_pos_names[i]); | |
+ } | |
} | |
layout = gtk_widget_get_layout_manager (GTK_WIDGET (notebook)); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# GtkProgressBar3: restore the double color of the progress text with automatic min-width/min-height from text | |
# default way | |
# progressbar trough[.empty][.full] | |
# progressbar text OR progressbar > text | |
# updated way | |
# progressbar[.empty][.full] trough[.empty][.full] | |
# progressbar[.empty][.full] text OR progressbar[.empty][.full] > text | |
# and when GTK_PROGRESS_TEXT_INSIDE=1 (text is the last child node of progressbar) | |
# (start_clip) progressbar.classic text.progress | |
# (end_clip) progressbar.classic text.trough | |
# https://github.com/lah7/gtk3-classic/issues/58 | |
# https://github.com/GNOME/gtk/blob/3.24.49/gtk/gtkprogressbar.c | |
Index: b/gtk/gtkprogressbar.c | |
=================================================================== | |
--- a/gtk/gtkprogressbar.c | |
+++ b/gtk/gtkprogressbar.c | |
@@ -449,15 +449,21 @@ update_fraction_classes | |
full = TRUE; | |
} | |
- if (empty) | |
- gtk_css_gadget_add_class (priv->trough_gadget, "empty"); | |
- else | |
- gtk_css_gadget_remove_class (priv->trough_gadget, "empty"); | |
- | |
- if (full) | |
- gtk_css_gadget_add_class (priv->trough_gadget, "full"); | |
- else | |
- gtk_css_gadget_remove_class (priv->trough_gadget, "full"); | |
+ if (empty) { | |
+ gtk_css_gadget_add_class (priv->trough_gadget, "empty"); | |
+ gtk_css_gadget_add_class (priv->gadget, "empty"); | |
+ } else { | |
+ gtk_css_gadget_remove_class (priv->trough_gadget, "empty"); | |
+ gtk_css_gadget_remove_class (priv->gadget, "empty"); | |
+ } | |
+ | |
+ if (full) { | |
+ gtk_css_gadget_add_class (priv->trough_gadget, "full"); | |
+ gtk_css_gadget_add_class (priv->gadget, "full"); | |
+ } else { | |
+ gtk_css_gadget_remove_class (priv->trough_gadget, "full"); | |
+ gtk_css_gadget_remove_class (priv->gadget, "full"); | |
+ } | |
} | |
static void | |
@@ -749,7 +755,7 @@ gtk_progress_bar_measure | |
pbar = GTK_PROGRESS_BAR (widget); | |
priv = pbar->priv; | |
- if (priv->show_text) | |
+ if (priv->show_text && (g_strcmp0 (g_getenv ("GTK_PROGRESS_TEXT_INSIDE"), "1") != 0)) | |
gtk_css_gadget_get_preferred_size (priv->text_gadget, | |
orientation, | |
-1, | |
@@ -932,6 +938,18 @@ gtk_progress_bar_measure_trough | |
gtk_widget_style_get (widget, "min-vertical-bar-height", minimum, NULL); | |
} | |
+ if (priv->show_text && (g_strcmp0 (g_getenv ("GTK_PROGRESS_TEXT_INSIDE"), "1") == 0)) | |
+ { | |
+ if ( ((orientation == GTK_ORIENTATION_HORIZONTAL) && (priv->orientation == GTK_ORIENTATION_VERTICAL)) || | |
+ ((orientation == GTK_ORIENTATION_VERTICAL) && (priv->orientation == GTK_ORIENTATION_HORIZONTAL)) ) | |
+ { | |
+ gint text_minimum; | |
+ gtk_css_gadget_get_preferred_size (priv->text_gadget, orientation, -1, &text_minimum, NULL, NULL, NULL); | |
+ if (*minimum < text_minimum) | |
+ *minimum = text_minimum; | |
+ } | |
+ } | |
+ | |
*natural = *minimum; | |
if (minimum_baseline) | |
@@ -987,6 +1005,18 @@ gtk_progress_bar_measure_progress | |
gtk_widget_style_get (widget, "min-horizontal-bar-height", minimum, NULL); | |
} | |
+ if (priv->show_text && (g_strcmp0 (g_getenv ("GTK_PROGRESS_TEXT_INSIDE"), "1") == 0)) | |
+ { | |
+ if ( ((orientation == GTK_ORIENTATION_HORIZONTAL) && (priv->orientation == GTK_ORIENTATION_VERTICAL)) || | |
+ ((orientation == GTK_ORIENTATION_VERTICAL) && (priv->orientation == GTK_ORIENTATION_HORIZONTAL)) ) | |
+ { | |
+ gint text_minimum; | |
+ gtk_css_gadget_get_preferred_size (priv->text_gadget, orientation, -1, &text_minimum, NULL, NULL, NULL); | |
+ if (*minimum < text_minimum) | |
+ *minimum = text_minimum; | |
+ } | |
+ } | |
+ | |
*natural = *minimum; | |
if (minimum_baseline) | |
@@ -1328,11 +1358,105 @@ gtk_progress_bar_render_text | |
if (priv->ellipsize) | |
pango_layout_set_width (layout, width * PANGO_SCALE); | |
- gtk_render_layout (context, cr, x, y, layout); | |
- | |
- g_object_unref (layout); | |
- | |
- gtk_style_context_restore (context); | |
+ if ((g_strcmp0 (g_getenv ("GTK_PROGRESS_TEXT_INSIDE"), "1") == 0) && (g_strcmp0 (g_getenv ("STOP3"), "1") != 0)) | |
+ { | |
+ gint width, height; | |
+ GdkRectangle start_clip, end_clip; | |
+ gboolean ltr = gtk_widget_get_direction (widget) == GTK_TEXT_DIR_LTR, rtl = !ltr; | |
+ | |
+ GtkAllocation allocation_total, allocation_progress; | |
+ gtk_css_gadget_get_preferred_size (priv->gadget, GTK_ORIENTATION_HORIZONTAL, -1, &width, NULL, NULL, NULL); | |
+ gtk_css_gadget_get_preferred_size (priv->gadget, GTK_ORIENTATION_VERTICAL, -1, &height, NULL, NULL, NULL); | |
+ allocation_total.width = width; | |
+ allocation_total.height = height; | |
+ gtk_css_gadget_get_preferred_size (priv->progress_gadget, GTK_ORIENTATION_HORIZONTAL, -1, &width, NULL, NULL, NULL); | |
+ gtk_css_gadget_get_preferred_size (priv->progress_gadget, GTK_ORIENTATION_VERTICAL, -1, &height, NULL, NULL, NULL); | |
+ allocation_progress.width = width; | |
+ allocation_progress.height = height; | |
+ | |
+ if (priv->orientation == GTK_ORIENTATION_HORIZONTAL) | |
+ { | |
+ if (ltr && !priv->inverted || rtl && priv->inverted) | |
+ { | |
+ start_clip.x = 0; | |
+ start_clip.y = 0; | |
+ start_clip.width = allocation_progress.width; | |
+ start_clip.height = allocation_progress.height; | |
+ end_clip.x = allocation_progress.width; | |
+ end_clip.y = 0; | |
+ end_clip.width = allocation_total.width - allocation_progress.width; | |
+ end_clip.height = allocation_total.height; | |
+ } | |
+ else | |
+ { | |
+ start_clip.x = allocation_total.width - allocation_progress.width; // here | |
+ start_clip.y = 0; | |
+ start_clip.width = allocation_progress.width; | |
+ start_clip.height = allocation_progress.height; | |
+ end_clip.x = 0; // here | |
+ end_clip.y = 0; | |
+ end_clip.width = allocation_total.width - allocation_progress.width; | |
+ end_clip.height = allocation_total.height; | |
+ } | |
+ } | |
+ else | |
+ { | |
+ if (!priv->ellipsize) | |
+ pango_layout_set_width (layout, allocation_total.width * PANGO_SCALE); | |
+ pango_layout_set_alignment (layout, PANGO_ALIGN_CENTER); | |
+ | |
+ if (ltr && !priv->inverted || rtl && !priv->inverted) | |
+ { | |
+ start_clip.x = 0; | |
+ start_clip.y = 0; | |
+ start_clip.width = allocation_progress.width; | |
+ start_clip.height = allocation_progress.height; | |
+ end_clip.x = 0; | |
+ end_clip.y = allocation_progress.height; | |
+ end_clip.width = allocation_total.width; | |
+ end_clip.height = allocation_total.height - allocation_progress.height; | |
+ } | |
+ else | |
+ { | |
+ start_clip.x = 0; | |
+ start_clip.y = allocation_total.height - allocation_progress.height; // here | |
+ start_clip.width = allocation_progress.width; | |
+ start_clip.height = allocation_progress.height; | |
+ end_clip.x = 0; | |
+ end_clip.y = 0; // here | |
+ end_clip.width = allocation_total.width; | |
+ end_clip.height = allocation_total.height - allocation_progress.height; | |
+ } | |
+ } | |
+ | |
+ if (start_clip.width > 0 && start_clip.height > 0) | |
+ { | |
+ cairo_save (cr); | |
+ gdk_cairo_rectangle (cr, &start_clip); | |
+ cairo_clip (cr); | |
+ gtk_style_context_add_class (context, "progress"); | |
+ gtk_render_layout (context, cr, x, y, layout); | |
+ gtk_style_context_remove_class (context, "progress"); | |
+ cairo_restore (cr); | |
+ } | |
+ if (end_clip.width > 0 && end_clip.height > 0) | |
+ { | |
+ cairo_save (cr); | |
+ gdk_cairo_rectangle (cr, &end_clip); | |
+ cairo_clip (cr); | |
+ gtk_style_context_add_class (context, "trough"); | |
+ gtk_render_layout (context, cr, x, y, layout); | |
+ gtk_style_context_remove_class (context, "trough"); | |
+ cairo_restore (cr); | |
+ } | |
+ } | |
+ else | |
+ { | |
+ gtk_render_layout (context, cr, x, y, layout); | |
+ } | |
+ | |
+ g_object_unref (layout); | |
+ gtk_style_context_restore (context); g_print("gtk_progress_bar_render_text\n"); | |
return FALSE; | |
} | |
@@ -1565,22 +1689,40 @@ gtk_progress_bar_set_show_text | |
if (show_text) | |
{ | |
- priv->text_gadget = gtk_css_custom_gadget_new ("text", | |
- GTK_WIDGET (pbar), | |
- priv->gadget, | |
- priv->trough_gadget, | |
- gtk_progress_bar_measure_text, | |
- NULL, | |
- gtk_progress_bar_render_text, | |
- NULL, | |
- NULL); | |
+ if (g_strcmp0 (g_getenv ("GTK_PROGRESS_TEXT_INSIDE"), "1") == 0) | |
+ { | |
+ gtk_css_gadget_add_class (priv->gadget, "classic"); | |
+ priv->text_gadget = gtk_css_custom_gadget_new ("text", | |
+ GTK_WIDGET (pbar), | |
+ priv->gadget, | |
+ NULL, | |
+ gtk_progress_bar_measure_text, | |
+ NULL, | |
+ gtk_progress_bar_render_text, | |
+ NULL, | |
+ NULL); | |
+ } | |
+ else | |
+ { | |
+ priv->text_gadget = gtk_css_custom_gadget_new ("text", | |
+ GTK_WIDGET (pbar), | |
+ priv->gadget, | |
+ priv->trough_gadget, | |
+ gtk_progress_bar_measure_text, | |
+ NULL, | |
+ gtk_progress_bar_render_text, | |
+ NULL, | |
+ NULL); | |
+ } | |
g_signal_connect (gtk_css_gadget_get_node (priv->text_gadget), "style-changed", | |
G_CALLBACK (gtk_progress_bar_text_style_changed), pbar); | |
update_node_state (pbar); | |
} | |
else | |
{ | |
+ if (g_strcmp0 (g_getenv ("GTK_PROGRESS_TEXT_INSIDE"), "1") == 0) | |
+ gtk_css_gadget_remove_class (priv->gadget, "classic"); | |
if (priv->text_gadget) | |
gtk_css_node_set_parent (gtk_css_gadget_get_node (priv->text_gadget), NULL); | |
g_clear_object (&priv->text_gadget); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# GtkProgressBar4: experimental, restore the double color of the progress text WITHOUT automatic min-width/min-height from text | |
# default way | |
# progressbar trough[.empty][.full] | |
# progressbar text OR progressbar > text | |
# updated way | |
# progressbar[.empty][.full] trough[.empty][.full] | |
# progressbar[.empty][.full] text OR progressbar[.empty][.full] > text | |
# and when GTK_PROGRESS_TEXT_INSIDE=1 (text and .text are the last child nodes of progressbar) | |
# (original) progressbar.classic text | |
# (start_clip) progressbar.classic .text.progress | |
# (end_clip) progressbar.classic .text.trough | |
# a lot of deprecated things - but it works | |
# https://github.com/lah7/gtk3-classic/issues/58 | |
# https://github.com/GNOME/gtk/blob/4.18.3/gtk/gtkprogressbar.c | |
Index: b/gtk/gtkprogressbar.c | |
=================================================================== | |
--- a/gtk/gtkprogressbar.c | |
+++ b/gtk/gtkprogressbar.c | |
@@ -37,6 +37,11 @@ | |
#include "gtkprivate.h" | |
#include "gtksnapshot.h" | |
#include "gtkwidgetprivate.h" | |
+#include "deprecated/gtkstylecontext.h" | |
+#include "deprecated/gtkrender.h" | |
+#include "gtkdrawingarea.h" | |
+#include "gtkcssprovider.h" | |
+#include <graphene.h> | |
#include <string.h> | |
@@ -161,6 +166,8 @@ | |
GtkOrientation orientation); | |
static void gtk_progress_bar_direction_changed (GtkWidget *widget, | |
GtkTextDirection previous_dir); | |
+static void on_label_update (GObject *object, GParamSpec *pspec, gpointer user_data); | |
+static void draw_text (GtkProgressBar *pbar, GtkWidget *widget, cairo_t* cr, int width, int height); | |
G_DEFINE_TYPE_WITH_CODE (GtkProgressBar, gtk_progress_bar, GTK_TYPE_WIDGET, | |
G_IMPLEMENT_INTERFACE (GTK_TYPE_ORIENTABLE, NULL) | |
@@ -288,15 +295,21 @@ update_fraction_classes | |
full = TRUE; | |
} | |
- if (empty) | |
- gtk_widget_add_css_class (pbar->trough_widget, "empty"); | |
- else | |
- gtk_widget_remove_css_class (pbar->trough_widget, "empty"); | |
- | |
- if (full) | |
- gtk_widget_add_css_class (pbar->trough_widget, "full"); | |
- else | |
- gtk_widget_remove_css_class (pbar->trough_widget, "full"); | |
+ if (empty) { | |
+ gtk_widget_add_css_class (pbar->trough_widget, "empty"); | |
+ gtk_widget_add_css_class (GTK_WIDGET (pbar), "empty"); | |
+ } else { | |
+ gtk_widget_remove_css_class (pbar->trough_widget, "empty"); | |
+ gtk_widget_remove_css_class (GTK_WIDGET (pbar), "empty"); | |
+ } | |
+ | |
+ if (full) { | |
+ gtk_widget_add_css_class (pbar->trough_widget, "full"); | |
+ gtk_widget_add_css_class (GTK_WIDGET (pbar), "full"); | |
+ } else { | |
+ gtk_widget_remove_css_class (pbar->trough_widget, "full"); | |
+ gtk_widget_remove_css_class (GTK_WIDGET (pbar), "full"); | |
+ } | |
} | |
static void | |
@@ -397,6 +410,24 @@ allocate_trough | |
&progress_width, NULL, | |
NULL, NULL); | |
+ g_print("allocate_trough\n"); if (pbar->show_text && (g_strcmp0 (g_getenv ("GTK_PROGRESS_TEXT_INSIDE"), "1") == 0)) | |
+ { g_print("label = %s\n", gtk_label_get_labe (GTK_LABEL (pbar->label))); | |
+ if (pbar->orientation == GTK_ORIENTATION_HORIZONTAL) | |
+ { | |
+ int text_height; | |
+ gtk_widget_measure (pbar->label, GTK_ORIENTATION_VERTICAL, -1, &text_height, NULL, NULL, NULL); | |
+ if (progress_height < text_height) | |
+ progress_height = text_height; | |
+ } | |
+ else if (pbar->orientation == GTK_ORIENTATION_VERTICAL) | |
+ { | |
+ int text_width; | |
+ gtk_widget_measure (pbar->label, GTK_ORIENTATION_HORIZONTAL, -1, &text_width, NULL, NULL, NULL); | |
+ if (progress_width < text_width) | |
+ progress_width = text_width; | |
+ } | |
+ } | |
+ | |
if (pbar->activity_mode) | |
{ | |
if (pbar->orientation == GTK_ORIENTATION_HORIZONTAL) | |
@@ -458,6 +489,16 @@ snapshot_trough | |
gtk_css_boxes_init (&boxes, GTK_WIDGET (gizmo)); | |
gtk_snapshot_push_rounded_clip (snapshot, gtk_css_boxes_get_border_box (&boxes)); | |
gtk_widget_snapshot_child (GTK_WIDGET (gizmo), pbar->progress_widget, snapshot); | |
+ | |
+ GtkAllocation alloc; | |
+ gtk_widget_get_allocation (GTK_WIDGET (gizmo), &alloc); | |
+ graphene_rect_t bounds; | |
+ bounds = graphene_rect_init (0, 0, alloc.width, alloc.height); | |
+ | |
+ cairo_t *cr = gtk_snapshot_append_cairo (snapshot, &bounds); | |
+ draw_text (pbar, GTK_WIDGET (gizmo), cr, alloc.width, alloc.height); | |
+ cairo_destroy (cr); | |
+ | |
gtk_snapshot_pop (snapshot); | |
} | |
} | |
@@ -916,13 +957,26 @@ gtk_progress_bar_set_show_text | |
"label", text, | |
"ellipsize", pbar->ellipsize, | |
NULL); | |
- gtk_widget_insert_after (pbar->label, GTK_WIDGET (pbar), NULL); | |
+ | |
+ if (g_strcmp0 (g_getenv ("GTK_PROGRESS_TEXT_INSIDE"), "1") == 0) | |
+ { | |
+ gtk_widget_add_css_class (GTK_WIDGET (pbar), "classic"); | |
+ gtk_widget_insert_before (pbar->label, GTK_WIDGET (pbar), NULL); | |
+ //gtk_widget_set_visible (pbar->label, FALSE); | |
+ //g_signal_connect (pbar->label, "notify::label", G_CALLBACK (on_label_update), pbar); | |
+ } | |
+ else | |
+ { | |
+ gtk_widget_insert_after (pbar->label, GTK_WIDGET (pbar), NULL); | |
+ } | |
g_free (text); | |
} | |
else | |
{ | |
g_clear_pointer (&pbar->label, gtk_widget_unparent); | |
+ if (g_strcmp0 (g_getenv ("GTK_PROGRESS_TEXT_INSIDE"), "1") == 0) | |
+ gtk_widget_remove_css_class (GTK_WIDGET (pbar), "classic"); | |
} | |
g_object_notify_by_pspec (G_OBJECT (pbar), progress_props[PROP_SHOW_TEXT]); | |
@@ -1156,3 +1210,112 @@ | |
return pbar->ellipsize; | |
} | |
+ | |
+static void on_label_update (GObject *object, GParamSpec *pspec, gpointer user_data) { | |
+ gtk_widget_queue_draw (GTK_WIDGET (user_data)); | |
+} | |
+ | |
+static void draw_text (GtkProgressBar *pbar, GtkWidget *widget, cairo_t* cr, int width, int height) { | |
+ | |
+ int x, y, text_width, text_height; | |
+ | |
+ // same idea as gtk3 | |
+ GtkStyleContext *context = gtk_widget_get_style_context (widget); | |
+ gtk_style_context_save (context); | |
+ PangoLayout *layout = gtk_widget_create_pango_layout (widget, get_current_text (pbar)); | |
+ | |
+ // to center the text horizontal & vertical | |
+ pango_layout_get_pixel_size (layout, &text_width, &text_height); | |
+ x = (width - text_width) / 2; | |
+ y = (height - text_height) / 2; | |
+ | |
+ // copied from gtk3 patch (except for gtk_widget_get_allocation) | |
+ // it's deprecated, but osef! | |
+ | |
+ pango_layout_set_ellipsize (layout, pbar->ellipsize); | |
+ if (pbar->ellipsize) | |
+ pango_layout_set_width (layout, width * PANGO_SCALE); | |
+ | |
+ | |
+ GdkRectangle start_clip, end_clip; | |
+ gboolean ltr = gtk_widget_get_direction (widget) == GTK_TEXT_DIR_LTR, rtl = !ltr; | |
+ | |
+ GtkAllocation allocation_total, allocation_progress; | |
+ gtk_widget_get_allocation (GTK_WIDGET (pbar), &allocation_total); | |
+ gtk_widget_get_allocation (pbar->progress_widget, &allocation_progress); | |
+ | |
+ if (pbar->orientation == GTK_ORIENTATION_HORIZONTAL) | |
+ { | |
+ if (ltr && !pbar->inverted || rtl && pbar->inverted) | |
+ { | |
+ start_clip.x = 0; | |
+ start_clip.y = 0; | |
+ start_clip.width = allocation_progress.width; | |
+ start_clip.height = allocation_progress.height; | |
+ end_clip.x = allocation_progress.width; | |
+ end_clip.y = 0; | |
+ end_clip.width = allocation_total.width - allocation_progress.width; | |
+ end_clip.height = allocation_total.height; | |
+ } | |
+ else | |
+ { | |
+ start_clip.x = allocation_total.width - allocation_progress.width; // here | |
+ start_clip.y = 0; | |
+ start_clip.width = allocation_progress.width; | |
+ start_clip.height = allocation_progress.height; | |
+ end_clip.x = 0; // here | |
+ end_clip.y = 0; | |
+ end_clip.width = allocation_total.width - allocation_progress.width; | |
+ end_clip.height = allocation_total.height; | |
+ } | |
+ } | |
+ else | |
+ { | |
+ if (ltr && !pbar->inverted || rtl && !pbar->inverted) | |
+ { | |
+ start_clip.x = 0; | |
+ start_clip.y = 0; | |
+ start_clip.width = allocation_progress.width; | |
+ start_clip.height = allocation_progress.height; | |
+ end_clip.x = 0; | |
+ end_clip.y = allocation_progress.height; | |
+ end_clip.width = allocation_total.width; | |
+ end_clip.height = allocation_total.height - allocation_progress.height; | |
+ } | |
+ else | |
+ { | |
+ start_clip.x = 0; | |
+ start_clip.y = allocation_total.height - allocation_progress.height; // here | |
+ start_clip.width = allocation_progress.width; | |
+ start_clip.height = allocation_progress.height; | |
+ end_clip.x = 0; | |
+ end_clip.y = 0; // here | |
+ end_clip.width = allocation_total.width; | |
+ end_clip.height = allocation_total.height - allocation_progress.height; | |
+ } | |
+ } | |
+ | |
+ if (start_clip.width > 0 && start_clip.height > 0) | |
+ { | |
+ cairo_save (cr); | |
+ gdk_cairo_rectangle (cr, &start_clip); | |
+ cairo_clip (cr); | |
+ gtk_style_context_add_class (context, "progress"); | |
+ gtk_render_layout (context, cr, x, y, layout); | |
+ gtk_style_context_remove_class (context, "progress"); | |
+ cairo_restore (cr); | |
+ } | |
+ if (end_clip.width > 0 && end_clip.height > 0) | |
+ { | |
+ cairo_save (cr); | |
+ gdk_cairo_rectangle (cr, &end_clip); | |
+ cairo_clip (cr); | |
+ gtk_style_context_add_class (context, "trough"); | |
+ gtk_render_layout (context, cr, x, y, layout); | |
+ gtk_style_context_remove_class (context, "trough"); | |
+ cairo_restore (cr); | |
+ } | |
+ | |
+ g_object_unref (layout); | |
+ gtk_style_context_restore (context); | |
+} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# GtkWindow3: toggle .csd/.solid-csd when compositor is enabled/disabled and do not add solid-csd for non CSD windows/dialogs | |
# default way | |
# compositor enabled + csd window/dialog: window.csd dialog.csd | |
# compositor disabled + csd window/dialog: window.solid-csd dialog.solid-csd | |
# standard window/dialog: window dialog.solid-csd | |
# updated way | |
# compositor enabled + csd window/dialog: window.csd dialog.csd | |
# compositor disabled + csd window/dialog: window.solid-csd.compositor-off dialog.solid-csd.compositor-off | |
# standard window/dialog: window dialog | |
# and when compositor is enabled -> disabled: .csd -> .solid-csd | |
# and when compositor is disabled -> enabled: .solid-csd -> .csd ONLY when .compositor-off is not defined | |
# https://github.com/GNOME/gtk/blob/3.24.49/gtk/gtkwindow.c | |
# https://github.com/lah7/gtk3-classic/issues/125 | |
Index: b/gtk/gtkwindow.c | |
=================================================================== | |
--- a/gtk/gtkwindow.c | |
+++ b/gtk/gtkwindow.c | |
@@ -7407,6 +7407,16 @@ gtk_window_realize | |
create_decoration (widget); | |
_gtk_widget_get_allocation (widget, &allocation); | |
+ if (!priv->client_decorated) | |
+ { | |
+ GtkStyleContext *context = gtk_widget_get_style_context (widget); | |
+ gtk_style_context_remove_class (context, "solid-csd"); | |
+ } | |
+ else if (!gdk_screen_is_composited (priv->screen)) | |
+ { | |
+ GtkStyleContext *context = gtk_widget_get_style_context (widget); | |
+ gtk_style_context_add_class (context, "compositor-off"); | |
+ } | |
if (gtk_widget_get_parent_window (widget)) | |
{ | |
@@ -11302,6 +11312,24 @@ gtk_window_on_composited_changed | |
{ | |
GtkWidget *widget = GTK_WIDGET (window); | |
+ GtkStyleContext *context = gtk_widget_get_style_context (widget); | |
+ if ( | |
+ !gtk_style_context_has_class (context, "compositor-off") && | |
+ (gtk_style_context_has_class (context, "solid-csd") || gtk_style_context_has_class (context, "csd")) | |
+ ) | |
+ { | |
+ if (gdk_screen_is_composited (screen)) | |
+ { | |
+ gtk_style_context_remove_class (context, "solid-csd"); | |
+ gtk_style_context_add_class (context, "csd"); | |
+ } | |
+ else | |
+ { | |
+ gtk_style_context_remove_class (context, "csd"); | |
+ gtk_style_context_add_class (context, "solid-csd"); | |
+ } | |
+ } | |
+ | |
gtk_widget_queue_draw (widget); | |
_gtk_widget_propagate_composited_changed (widget); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# GtkWindow4: toggle .csd/.solid-csd when compositor is enabled/disabled and do not add solid-csd for non CSD windows/dialogs | |
# default way | |
# compositor enabled + csd window/dialog: window.csd dialog.csd | |
# compositor disabled + csd window/dialog: window.solid-csd dialog.solid-csd | |
# standard window/dialog: window dialog | |
# updated way | |
# compositor enabled + csd window/dialog: window.csd dialog.csd | |
# compositor disabled + csd window/dialog: window.solid-csd.compositor-off dialog.solid-csd.compositor-off | |
# standard window/dialog: window dialog | |
# and when compositor is enabled -> disabled: .csd -> .solid-csd | |
# and when compositor is disabled -> enabled: .solid-csd -> .csd ONLY when .compositor-off is not defined | |
# https://github.com/GNOME/gtk/blob/4.18.3/gtk/gtkwindow.c | |
# https://github.com/lah7/gtk3-classic/issues/125 | |
Index: b/gtk/gtkwindow.c | |
=================================================================== | |
--- a/gtk/gtkwindow.c | |
+++ b/gtk/gtkwindow.c | |
@@ -543,6 +543,26 @@ | |
static GtkAccessibleInterface *parent_accessible_iface; | |
+static void gtk_window_on_composited_changed (GdkDisplay *display, GParamSpec *pspec, GtkWidget *widget) | |
+{ | |
+ if ( | |
+ !gtk_widget_has_css_class (widget, "compositor-off") && | |
+ (gtk_widget_has_css_class (widget, "solid-csd") || gtk_widget_has_css_class (widget, "csd")) | |
+ ) | |
+ { | |
+ if (gdk_display_is_composited (display)) | |
+ { | |
+ gtk_widget_remove_css_class (widget, "solid-csd"); | |
+ gtk_widget_add_css_class (widget, "csd"); | |
+ } | |
+ else | |
+ { | |
+ gtk_widget_remove_css_class (widget, "csd"); | |
+ gtk_widget_add_css_class (widget, "solid-csd"); | |
+ } | |
+ } g_print("gtk_window_on_composited_changed\n"); | |
+} | |
+ | |
static gboolean | |
gtk_window_accessible_get_platform_state (GtkAccessible *self, | |
GtkAccessiblePlatformState state) | |
@@ -4398,7 +4418,10 @@ gtk_window_realize | |
update_window_actions (window); | |
} | |
else | |
- priv->use_client_shadow = FALSE; | |
+ { | |
+ priv->use_client_shadow = FALSE; | |
+ gtk_widget_add_css_class (widget, "compositor-off"); | |
+ } | |
} | |
surface = gdk_surface_new_toplevel (gtk_widget_get_display (widget)); | |
@@ -4413,6 +4436,7 @@ gtk_window_realize | |
g_signal_connect (surface, "render", G_CALLBACK (surface_render), widget); | |
g_signal_connect (surface, "event", G_CALLBACK (surface_event), widget); | |
g_signal_connect (surface, "compute-size", G_CALLBACK (toplevel_compute_size), widget); | |
+ g_signal_connect (gtk_widget_get_display (widget), "notify::composited", G_CALLBACK (on_composited_changed), widget); | |
frame_clock = gdk_surface_get_frame_clock (surface); | |
g_signal_connect (frame_clock, "after-paint", G_CALLBACK (after_paint), widget); | |
@@ -4519,6 +4543,7 @@ gtk_window_unrealize | |
g_signal_handlers_disconnect_by_func (surface, surface_render, widget); | |
g_signal_handlers_disconnect_by_func (surface, surface_event, widget); | |
g_signal_handlers_disconnect_by_func (surface, toplevel_compute_size, widget); | |
+ g_signal_handlers_disconnect_by_func (gtk_widget_get_display (widget), on_composited_changed, widget); | |
frame_clock = gdk_surface_get_frame_clock (surface); | |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# GtkFileChooserWidget3: allow to use IEC units in GTK (GTK_USE_IEC_UNITS=1) | |
# https://github.com/GNOME/gtk/blob/3.24.41/gtk/gtkfilechooserwidget.c | |
Index: b/gtk/gtkfilechooserwidget.c | |
=================================================================== | |
--- a/gtk/gtkfilechooserwidget.c | |
+++ b/gtk/gtkfilechooserwidget.c | |
@@ -5223,6 +5223,8 @@ file_system_model_set | |
case MODEL_COL_SIZE_TEXT: | |
if (info == NULL || _gtk_file_info_consider_as_directory (info)) | |
g_value_set_string (value, NULL); | |
+ else if (g_strcmp0 (g_getenv ("GTK_USE_IEC_UNITS"), "1") == 0) | |
+ g_value_take_string (value, g_format_size_full (g_file_info_get_size (info), G_FORMAT_SIZE_IEC_UNITS)); | |
else | |
g_value_take_string (value, g_format_size (g_file_info_get_size (info))); | |
break; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# GtkFileChooserWidget4: allow to use IEC units in GTK (GTK_USE_IEC_UNITS=1) | |
# https://github.com/GNOME/gtk/blob/4.12.5/gtk/gtkfilechooserwidget.c | |
Index: b/gtk/gtkfilechooserwidget.c | |
=================================================================== | |
--- a/gtk/gtkfilechooserwidget.c | |
+++ b/gtk/gtkfilechooserwidget.c | |
@@ -2087,7 +2087,12 @@ column_view_get_size | |
column_view_get_size (GFileInfo *info) | |
{ | |
if (info && !_gtk_file_info_consider_as_directory (info)) | |
+ { | |
+ if (g_strcmp0 (g_getenv ("GTK_USE_IEC_UNITS"), "1") == 0) | |
+ return g_format_size_full (g_file_info_get_size (info), G_FORMAT_SIZE_IEC_UNITS); | |
+ | |
return g_format_size (g_file_info_get_size (info)); | |
+ } | |
else | |
return NULL; | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
# updated 15/04/2025 for Debian Testing (Trixie) | |
# gtk3-classic DEB packages: https://build.opensuse.org/package/show/home:luigifab/gtk3-classic | |
# classic desktop theme: https://github.com/luigifab/human-theme/releases | |
cd "$(dirname "$0")" | |
if [ ! -d gtk3-classic ]; then | |
git clone https://github.com/lah7/gtk3-classic.git | |
fi | |
if [ ! -d builder ]; then | |
mkdir builder | |
fi | |
cd builder/ | |
numb=171 | |
for serie in trixie; do | |
rm -rf ${serie}/*/ ${serie}/*.dsc ${serie}/*.buildinfo ${serie}/*.changes ${serie}/*-1* | |
if [ ! -d ${serie} ]; then | |
mkdir $serie | |
fi | |
cd ${serie}/ | |
# https://packages.ubuntu.com/search?searchon=sourcenames&keywords=gtk%2B3.0 | |
# https://packages.debian.org/search?searchon=sourcenames&keywords=gtk%2B3.0 | |
# https://packages.debian.org/source/trixie/gtk+3.0 | |
echo "" | |
echo "==== ${serie}/gtk3 ==========================================" | |
echo "" | |
version=3.24.49 | |
classic=${version} | |
wget -nc http://deb.debian.org/debian/pool/main/g/gtk+3.0/gtk+3.0_${version}.orig.tar.xz | |
wget -nc http://deb.debian.org/debian/pool/main/g/gtk+3.0/gtk+3.0_${version}-3.debian.tar.xz | |
# prepare gtk3-classic | |
cp -r ../../gtk3-classic/ . | |
cd gtk3-classic/ | |
#git checkout -q $classic | |
git checkout -q master | |
git pull -q | |
cd .. | |
# extract and update data | |
tar xf gtk+3.0_${version}.orig.tar.xz | |
cd gtk-${version} | |
tar xf ../gtk*.debian.tar.xz | |
rm debian/changelog | |
echo "gtk+3.0 (2:${version}-${numb}+${serie}) ${serie}; urgency=medium" > debian/changelog | |
echo "" >> debian/changelog | |
echo " * Rebuild gtk3 ${version} with gtk3-classic patches" >> debian/changelog | |
echo "" >> debian/changelog | |
echo " -- Fabrice Creuzot <[email protected]> $(LC_TIME=C date -u +"%a, %d %b %Y %H:%M:%S") +0000" >> debian/changelog | |
echo "" >> debian/changelog | |
cp ../gtk3-classic/*.patch debian/patches/ | |
cp ../gtk3-classic/*.css debian/patches/ | |
sed -i 's/env -u LD_PRELOAD xvfb-run -a dh_auto_test/#env -u LD_PRELOAD xvfb-run -a dh_auto_test/' debian/rules | |
sed -i 's/APIVER := 3/APIVER := 3\nexport DEB_BUILD_OPTIONS := nocheck/' debian/rules | |
rm debian/*symbols | |
# add patches | |
rm -f debian/patches/appearance__focus-visible.gtk3.patch | |
wget https://gist.githubusercontent.com/luigifab/0fce786cdb93b5687069a82f490ea95e/raw/appearance__focus-visible.gtk3.patch -q --output-document=debian/patches/appearance__focus-visible.gtk3.patch | |
rm -f debian/patches/appearance__notebook_stack_class.gtk3.patch | |
wget https://gist.githubusercontent.com/luigifab/0fce786cdb93b5687069a82f490ea95e/raw/appearance__notebook_stack_class.gtk3.patch -q --output-document=debian/patches/appearance__notebook_stack_class.gtk3.patch | |
rm -f debian/patches/appearance__progress_text.gtk3.patch | |
wget https://gist.githubusercontent.com/luigifab/0fce786cdb93b5687069a82f490ea95e/raw/appearance__progress_text.gtk3.patch -q --output-document=debian/patches/appearance__progress_text.gtk3.patch | |
rm -f debian/patches/consistent_file_size_units.gtk3.patch | |
wget https://gist.githubusercontent.com/luigifab/0fce786cdb93b5687069a82f490ea95e/raw/consistent_file_size_units.gtk3.patch -q --output-document=debian/patches/consistent_file_size_units.gtk3.patch | |
rm -f debian/patches/appearance__toggle_csd.gtk3.patch | |
wget https://gist.githubusercontent.com/luigifab/0fce786cdb93b5687069a82f490ea95e/raw/appearance__toggle_csd.gtk3.patch -q --output-document=debian/patches/appearance__toggle_csd.gtk3.patch | |
# update patch list | |
rm debian/patches/series | |
for file in debian/patches/*.patch; do | |
echo $(basename $file) >> debian/patches/series | |
done | |
# @todo? | |
sed -i 's/evince /atril /' debian/patches/printing-Default-to-papers-previewer-and-fallback-to-evin.patch | |
# build packages | |
# dpkg-buildpackage -rfakeroot -b -uc -us | |
dpkg-buildpackage -us -uc -ui -d -S | |
cd .. | |
# sign packages | |
debsign *.changes | |
cd .. | |
done | |
cd .. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
# updated 17/04/2025 for Debian Testing (Trixie) | |
# gtk4-classic DEB packages: https://build.opensuse.org/package/show/home:luigifab/gtk4-classic | |
# classic desktop theme: https://github.com/luigifab/human-theme/releases | |
cd "$(dirname "$0")" | |
if [ ! -d builder ]; then | |
mkdir builder | |
fi | |
cd builder/ | |
numb=171 | |
for serie in trixie; do | |
rm -rf ${serie}/*/ ${serie}/*.dsc ${serie}/*.buildinfo ${serie}/*.changes ${serie}/*-1* | |
if [ ! -d ${serie} ]; then | |
mkdir $serie | |
fi | |
cd ${serie}/ | |
# https://packages.ubuntu.com/search?searchon=sourcenames&keywords=gtk4 | |
# https://packages.debian.org/search?searchon=sourcenames&keywords=gtk4 | |
# https://packages.debian.org/source/trixie/gtk4 | |
echo "" | |
echo "==== ${serie}/gtk4 ==========================================" | |
echo "" | |
version=4.18.4 | |
classic=${version} | |
wget -nc http://deb.debian.org/debian/pool/main/g/gtk4/gtk4_${version}+ds.orig.tar.xz | |
wget -nc http://deb.debian.org/debian/pool/main/g/gtk4/gtk4_${version}+ds-1.debian.tar.xz | |
cp gtk4_${version}+ds.orig.tar.xz gtk4_${version}.orig.tar.xz | |
# extract and update data | |
tar xf gtk4_${version}.orig.tar.xz | |
cd gtk-${version} | |
tar xf ../gtk*.debian.tar.xz | |
rm debian/changelog | |
echo "gtk4 (2:${version}-${numb}+${serie}) ${serie}; urgency=medium" > debian/changelog | |
echo "" >> debian/changelog | |
echo " * Rebuild gtk4 ${version} with gtk4-classic patches" >> debian/changelog | |
echo "" >> debian/changelog | |
echo " -- Fabrice Creuzot <[email protected]> $(LC_TIME=C date -u +"%a, %d %b %Y %H:%M:%S") +0000" >> debian/changelog | |
echo "" >> debian/changelog | |
sed -i 's/export SONAME := 1/export SONAME := 1\nexport DEB_BUILD_OPTIONS := nocheck/' debian/rules | |
# add patches | |
rm -f debian/patches/treeview__alternating_row_colours.gtk4.patch | |
wget https://gist.githubusercontent.com/luigifab/0fce786cdb93b5687069a82f490ea95e/raw/treeview__alternating_row_colours.gtk4.patch -q --output-document=debian/patches/treeview__alternating_row_colours.gtk4.patch | |
rm -f debian/patches/appearance__notebook_stack_class.gtk4.patch | |
wget https://gist.githubusercontent.com/luigifab/0fce786cdb93b5687069a82f490ea95e/raw/appearance__notebook_stack_class.gtk4.patch -q --output-document=debian/patches/appearance__notebook_stack_class.gtk4.patch | |
rm -f debian/patches/appearance__focus-visible.gtk4.patch | |
wget https://gist.githubusercontent.com/luigifab/0fce786cdb93b5687069a82f490ea95e/raw/appearance__focus-visible.gtk4.patch -q --output-document=debian/patches/appearance__focus-visible.gtk4.patch | |
rm -f debian/patches/appearance__progress_text.gtk4.patch | |
wget https://gist.githubusercontent.com/luigifab/0fce786cdb93b5687069a82f490ea95e/raw/appearance__progress_text.gtk4.patch -q --output-document=debian/patches/appearance__progress_text.gtk4.patch | |
rm -f debian/patches/consistent_file_size_units.gtk4.patch | |
wget https://gist.githubusercontent.com/luigifab/0fce786cdb93b5687069a82f490ea95e/raw/consistent_file_size_units.gtk4.patch -q --output-document=debian/patches/consistent_file_size_units.gtk4.patch | |
rm -f debian/patches/appearance__toggle_csd.gtk4.patch | |
wget https://gist.githubusercontent.com/luigifab/0fce786cdb93b5687069a82f490ea95e/raw/appearance__toggle_csd.gtk4.patch -q --output-document=debian/patches/appearance__toggle_csd.gtk4.patch | |
# update patch list | |
echo treeview__alternating_row_colours.gtk4.patch >> debian/patches/series | |
echo appearance__notebook_stack_class.gtk4.patch >> debian/patches/series | |
echo appearance__focus-visible.gtk4.patch >> debian/patches/series | |
echo appearance__progress_text.gtk4.patch >> debian/patches/series | |
echo consistent_file_size_units.gtk4.patch >> debian/patches/series | |
echo appearance__toggle_csd.gtk4.patch >> debian/patches/series | |
# build packages | |
# dpkg-buildpackage -rfakeroot -b -uc -us | |
dpkg-buildpackage -us -uc -ui -d -S | |
cd .. | |
# sign packages | |
debsign *.changes | |
cd .. | |
done | |
cd .. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
# updated 17/04/2025 for Debian Testing (Trixie) | |
# https://docs.gtk.org/gtk4/migrating-4to5.html | |
# @todo color_expressions.gtk5.patch (because color expressions are going away... lol) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
# updated 17/04/2025 for Debian Testing (Trixie) | |
# mate-notification-daemon DEB packages: https://build.opensuse.org/package/show/home:luigifab/mate-notification | |
# classic desktop theme: https://github.com/luigifab/human-theme/releases | |
cd "$(dirname "$0")" | |
if [ ! -d builder ]; then | |
mkdir builder | |
fi | |
cd builder/ | |
numb=171 | |
for serie in trixie; do | |
rm -rf ${serie}/*/ ${serie}/*.dsc ${serie}/*.buildinfo ${serie}/*.changes ${serie}/*-1* | |
if [ ! -d ${serie} ]; then | |
mkdir $serie | |
fi | |
cd ${serie}/ | |
# https://packages.debian.org/source/trixie/mate-notification-daemon | |
echo "" | |
echo "==== ${serie}/mate-notification-daemon ======================" | |
echo "" | |
version=1.26.1 | |
wget -nc http://deb.debian.org/debian/pool/main/m/mate-notification-daemon/mate-notification-daemon_${version}.orig.tar.xz | |
wget -nc http://deb.debian.org/debian/pool/main/m/mate-notification-daemon/mate-notification-daemon_${version}-1.debian.tar.xz | |
# extract and update data | |
tar xf mate-notification-daemon_${version}.orig.tar.xz | |
cd mate-notification-daemon-${version} | |
tar xf ../mate-notification-daemon*.debian.tar.xz | |
rm debian/changelog | |
echo "mate-notification-daemon (${version}-${numb}+${serie}) ${serie}; urgency=medium" > debian/changelog | |
echo "" >> debian/changelog | |
echo " * Rebuild with PR 232+233+234" >> debian/changelog | |
echo "" >> debian/changelog | |
echo " -- Fabrice Creuzot <[email protected]> $(LC_TIME=C date -u +"%a, %d %b %Y %H:%M:%S") +0000" >> debian/changelog | |
echo "" >> debian/changelog | |
rm -f debian/patches/notifs.patch | |
wget https://gist.githubusercontent.com/luigifab/0fce786cdb93b5687069a82f490ea95e/raw/notifs.patch -q --output-document=debian/patches/notifs.patch | |
echo notifs.patch >> debian/patches/series | |
# build packages | |
#dpkg-buildpackage -rfakeroot -b -uc -us | |
dpkg-buildpackage -us -uc -ui -d -S | |
cd .. | |
cd .. | |
done | |
cd .. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
diff --git a/src/capplet/mate-notification-properties.c b/src/capplet/mate-notification-properties.c | |
index 10f99d5..d8a5eab 100644 | |
--- a/src/capplet/mate-notification-properties.c | |
+++ b/src/capplet/mate-notification-properties.c | |
@@ -46,7 +46,8 @@ typedef struct { | |
GtkWidget* dnd_checkbox; | |
GtkWidget* monitor_label; | |
- NotifyNotification* preview; | |
+ NotifyNotification* preview1; | |
+ NotifyNotification* preview2; | |
} NotificationAppletDialog; | |
enum { | |
@@ -387,14 +388,19 @@ static void show_message(NotificationAppletDialog* dialog, const gchar* message) | |
static void notification_properties_dialog_preview_closed(NotifyNotification* preview, NotificationAppletDialog* dialog) | |
{ | |
- if (preview == dialog->preview) | |
- { | |
- dialog->preview = NULL; | |
- } | |
+ if (preview == dialog->preview1) | |
+ dialog->preview1 = NULL; | |
+ else if (preview == dialog->preview2) | |
+ dialog->preview2 = NULL; | |
g_object_unref(preview); | |
} | |
+static gboolean notification_properties_dialog_preview_action(void *data) { | |
+ // @todo call notification_properties_dialog_preview_closed | |
+ return FALSE; | |
+} | |
+ | |
static void notification_properties_dialog_preview(NotificationAppletDialog* dialog) | |
{ | |
if (!notify_is_initted() && !notify_init("n-d")) | |
@@ -405,16 +411,23 @@ static void notification_properties_dialog_preview(NotificationAppletDialog* dia | |
GError* error = NULL; | |
- if (dialog->preview) | |
+ if (dialog->preview1) | |
{ | |
- notify_notification_close(dialog->preview, NULL); | |
- g_object_unref(dialog->preview); | |
- dialog->preview = NULL; | |
+ notify_notification_close(dialog->preview1, NULL); | |
+ g_object_unref(dialog->preview1); | |
+ dialog->preview1 = NULL; | |
+ } | |
+ if (dialog->preview2) | |
+ { | |
+ notify_notification_close(dialog->preview2, NULL); | |
+ g_object_unref(dialog->preview2); | |
+ dialog->preview2 = NULL; | |
} | |
- dialog->preview = notify_notification_new(_("Notification Test"), _("Just a test"), "dialog-information"); | |
+ dialog->preview1 = notify_notification_new(_("Notification Test"), _("Just a test"), "dialog-information"); | |
+ notify_notification_set_timeout (dialog->preview1, 50000); | |
- if (!notify_notification_show(dialog->preview, &error)) | |
+ if (!notify_notification_show(dialog->preview1, &error)) | |
{ | |
char* message = g_strdup_printf(_("Error while displaying notification: %s"), error->message); | |
show_message(dialog, message); | |
@@ -422,7 +435,20 @@ static void notification_properties_dialog_preview(NotificationAppletDialog* dia | |
g_free(message); | |
} | |
- g_signal_connect(dialog->preview, "closed", G_CALLBACK(notification_properties_dialog_preview_closed), dialog); | |
+ dialog->preview2 = notify_notification_new(_("Notification Test"), _("Just a test"), "dialog-information"); | |
+ notify_notification_add_action (dialog->preview2, "nothing", _("Close"), NOTIFY_ACTION_CALLBACK (notification_properties_dialog_preview_action), NULL, NULL); | |
+ notify_notification_set_timeout (dialog->preview2, 50000); | |
+ | |
+ if (!notify_notification_show(dialog->preview2, &error)) | |
+ { | |
+ char* message = g_strdup_printf(_("Error while displaying notification: %s"), error->message); | |
+ show_message(dialog, message); | |
+ g_error_free(error); | |
+ g_free(message); | |
+ } | |
+ | |
+ g_signal_connect(dialog->preview1, "closed", G_CALLBACK(notification_properties_dialog_preview_closed), dialog); | |
+ g_signal_connect(dialog->preview2, "closed", G_CALLBACK(notification_properties_dialog_preview_closed), dialog); | |
} | |
static void notification_properties_dialog_response(GtkWidget* widget, int response, NotificationAppletDialog* dialog) | |
@@ -491,7 +517,8 @@ static gboolean notification_properties_dialog_init(NotificationAppletDialog* di | |
gtk_widget_show_all(dialog->dialog); | |
- dialog->preview = NULL; | |
+ dialog->preview1 = NULL; | |
+ dialog->preview2 = NULL; | |
return TRUE; | |
} | |
@@ -504,16 +531,23 @@ static void notification_properties_dialog_finalize(NotificationAppletDialog* di | |
dialog->dialog = NULL; | |
} | |
- if (dialog->preview) | |
+ if (dialog->preview1) | |
+ { | |
+ notify_notification_close(dialog->preview1, NULL); | |
+ dialog->preview1 = NULL; | |
+ } | |
+ if (dialog->preview2) | |
{ | |
- notify_notification_close(dialog->preview, NULL); | |
- dialog->preview = NULL; | |
+ notify_notification_close(dialog->preview2, NULL); | |
+ dialog->preview2 = NULL; | |
} | |
+ | |
+ g_free (dialog); | |
} | |
int main(int argc, char** argv) | |
{ | |
- NotificationAppletDialog dialog = {NULL, }; /* <- ? */ | |
+ NotificationAppletDialog *dialog; | |
#ifdef ENABLE_NLS | |
bindtextdomain(GETTEXT_PACKAGE, NOTIFICATION_LOCALEDIR); | |
@@ -525,15 +559,16 @@ int main(int argc, char** argv) | |
notify_init("mate-notification-properties"); | |
- if (!notification_properties_dialog_init(&dialog)) | |
+ dialog = g_new0 (NotificationAppletDialog, 1); | |
+ if (!notification_properties_dialog_init (dialog)) | |
{ | |
- notification_properties_dialog_finalize(&dialog); | |
+ notification_properties_dialog_finalize (dialog); | |
return 1; | |
} | |
gtk_main(); | |
- notification_properties_dialog_finalize(&dialog); | |
+ notification_properties_dialog_finalize (dialog); | |
return 0; | |
} | |
diff --git a/src/themes/coco/coco-theme.c b/src/themes/coco/coco-theme.c | |
index 741861f..89e8d11 100644 | |
--- a/src/themes/coco/coco-theme.c | |
+++ b/src/themes/coco/coco-theme.c | |
@@ -1,11 +1,8 @@ | |
/* | |
- * coco-theme.c | |
- * This file is part of notification-daemon-engine-coco | |
- * | |
* Copyright (C) 2012 - Stefano Karapetsas <[email protected]> | |
* Copyright (C) 2010 - Eduardo Grajeda | |
* Copyright (C) 2008 - Martin Sourada | |
- * Copyright (C) 2012-2021 MATE Developers | |
+ * Copyright (C) 2012-2025 MATE Developers | |
* | |
* notification-daemon-engine-coco is free software; you can redistribute it | |
* and/or modify it under the terms of the GNU General Public License as | |
@@ -27,7 +24,8 @@ | |
#include <glib/gi18n.h> | |
#include <gtk/gtk.h> | |
- | |
+#include <libxml/parser.h> | |
+#include <libxml/xmlmemory.h> | |
#include <libxml/xpath.h> | |
/* Define basic coco types */ | |
@@ -62,11 +60,8 @@ typedef struct | |
glong remaining; | |
UrlClickedCb url_clicked; | |
- | |
- GtkTextDirection rtl; | |
} WindowData; | |
- | |
enum | |
{ | |
URGENCY_LOW, | |
@@ -74,22 +69,22 @@ enum | |
URGENCY_CRITICAL | |
}; | |
-gboolean theme_check_init(unsigned int major_ver, unsigned int minor_ver, | |
+gboolean theme_check_init (unsigned int major_ver, unsigned int minor_ver, | |
unsigned int micro_ver); | |
-void get_theme_info(char **theme_name, char **theme_ver, char **author, | |
+void get_theme_info (char **theme_name, char **theme_ver, char **author, | |
char **homepage); | |
-GtkWindow* create_notification(UrlClickedCb url_clicked); | |
-void set_notification_text(GtkWindow *nw, const char *summary, | |
+GtkWindow* create_notification (UrlClickedCb url_clicked); | |
+void set_notification_text (GtkWindow *nw, const char *summary, | |
const char *body); | |
-void set_notification_icon(GtkWindow *nw, GdkPixbuf *pixbuf); | |
-void set_notification_arrow(GtkWidget *nw, gboolean visible, int x, int y); | |
-void add_notification_action(GtkWindow *nw, const char *text, const char *key, | |
+void set_notification_icon (GtkWindow *nw, GdkPixbuf *pixbuf); | |
+void set_notification_arrow (GtkWidget *nw, gboolean visible, int x, int y); | |
+void add_notification_action (GtkWindow *nw, const char *text, const char *key, | |
ActionInvokedCb cb); | |
-void clear_notification_actions(GtkWindow *nw); | |
-void move_notification(GtkWidget *nw, int x, int y); | |
-void set_notification_timeout(GtkWindow *nw, glong timeout); | |
-void set_notification_hints(GtkWindow *nw, GVariant *hints); | |
-void notification_tick(GtkWindow *nw, glong remaining); | |
+void clear_notification_actions (GtkWindow *nw); | |
+void move_notification (GtkWidget *nw, int x, int y); | |
+void set_notification_timeout (GtkWindow *nw, glong timeout); | |
+void set_notification_hints (GtkWindow *nw, GVariant *hints); | |
+void notification_tick (GtkWindow *nw, glong remaining); | |
#define STRIPE_WIDTH 32 | |
#define WIDTH 300 | |
@@ -107,28 +102,33 @@ void notification_tick(GtkWindow *nw, glong remaining); | |
#define BACKGROUND_OPACITY 0.9 | |
#define GRADIENT_CENTER 0.7 | |
-/* Support Nodoka Functions */ | |
+static void get_background_color (GtkStyleContext *context, GtkStateFlags state, GdkRGBA *color) | |
+{ | |
+ GdkRGBA *c; | |
+ | |
+ g_return_if_fail (color != NULL); | |
+ g_return_if_fail (GTK_IS_STYLE_CONTEXT (context)); | |
+ | |
+ gtk_style_context_get (context, state, | |
+ "background-color", &c, | |
+ NULL); | |
+ | |
+ *color = *c; | |
+ gdk_rgba_free (c); | |
+} | |
-/* Handle clicking on link */ | |
-static gboolean | |
-activate_link (GtkLabel *label, const char *url, WindowData *windata) | |
+static gboolean activate_link (GtkLabel *label, const char *url, WindowData *windata) | |
{ | |
windata->url_clicked (GTK_WINDOW (windata->win), url); | |
return TRUE; | |
} | |
-static void | |
-destroy_windata(WindowData *windata) | |
+static void destroy_windata (WindowData *windata) | |
{ | |
g_free(windata); | |
} | |
-/* Draw fuctions */ | |
-/* Standard rounded rectangle */ | |
-static void | |
-nodoka_rounded_rectangle (cairo_t * cr, | |
- double x, double y, double w, double h, | |
- int radius) | |
+static void nodoka_rounded_rectangle (cairo_t * cr, double x, double y, double w, double h, int radius) | |
{ | |
cairo_move_to (cr, x + radius, y); | |
cairo_arc (cr, x + w - radius, y + radius, radius, G_PI * 1.5, G_PI * 2); | |
@@ -137,9 +137,7 @@ nodoka_rounded_rectangle (cairo_t * cr, | |
cairo_arc (cr, x + radius, y + radius, radius, G_PI, G_PI * 1.5); | |
} | |
-/* Fill background */ | |
-static void | |
-fill_background(GtkWidget *widget, WindowData *windata, cairo_t *cr) | |
+static void fill_background (GtkWidget *widget, WindowData *windata, cairo_t *cr) | |
{ | |
double alpha; | |
if (windata->composited) | |
@@ -164,14 +162,34 @@ fill_background(GtkWidget *widget, WindowData *windata, cairo_t *cr) | |
cairo_fill (cr); | |
} | |
-static void | |
-draw_pie(GtkWidget *pie, WindowData *windata, cairo_t *cr) | |
+static void draw_pie (GtkWidget *pie, WindowData *windata, cairo_t *cr) | |
{ | |
if (windata->timeout == 0) | |
return; | |
gdouble arc_angle = 1.0 - (gdouble)windata->remaining / (gdouble)windata->timeout; | |
- cairo_set_source_rgba (cr, 1.0, 0.4, 0.0, 0.3); | |
+ GtkStyleContext *context; | |
+ GdkRGBA orig, bg; | |
+ | |
+ // :selected { background-color:#aabbcc; } ignored -> 1.0, 1.0, 1.0, 0.3 | |
+ context = gtk_widget_get_style_context (windata->win); | |
+ gtk_style_context_save (context); | |
+ gtk_style_context_set_state (context, GTK_STATE_FLAG_SELECTED); | |
+ get_background_color (context, GTK_STATE_FLAG_SELECTED, &orig); | |
+ gtk_style_context_restore (context); | |
+ | |
+ // .notification-box .countdown:selected { background-color:#aabbcc; } | |
+ context = gtk_widget_get_style_context (pie); | |
+ gtk_style_context_save (context); | |
+ gtk_style_context_set_state (context, GTK_STATE_FLAG_SELECTED); | |
+ get_background_color (context, GTK_STATE_FLAG_SELECTED, &bg); | |
+ gtk_style_context_restore (context); | |
+ | |
+ if (gdk_rgba_equal (&orig, &bg)) | |
+ cairo_set_source_rgba (cr, 1.0, 1.0, 1.0, 0.3); | |
+ else | |
+ cairo_set_source_rgba (cr, bg.red, bg.green, bg.blue, bg.alpha); | |
+ | |
cairo_move_to(cr, PIE_RADIUS, PIE_RADIUS); | |
cairo_arc_negative(cr, PIE_RADIUS, PIE_RADIUS, PIE_RADIUS, | |
-G_PI/2, (-0.25 + arc_angle)*2*G_PI); | |
@@ -180,71 +198,45 @@ draw_pie(GtkWidget *pie, WindowData *windata, cairo_t *cr) | |
cairo_fill (cr); | |
} | |
-static void | |
-update_shape_region (cairo_surface_t *surface, | |
- WindowData *windata) | |
+static void update_shape_region (cairo_surface_t *surface, WindowData *windata) | |
{ | |
if (windata->width == windata->last_width && windata->height == windata->last_height) | |
- { | |
return; | |
- } | |
- if (windata->width == 0 || windata->height == 0) | |
- { | |
- GtkAllocation allocation; | |
- gtk_widget_get_allocation (windata->win, &allocation); | |
- | |
- windata->width = MAX (allocation.width, 1); | |
- windata->height = MAX (allocation.height, 1); | |
+ if (windata->composited) { | |
+ gtk_widget_shape_combine_region (windata->win, NULL); | |
} | |
- | |
- if (!windata->composited) { | |
+ else { | |
cairo_region_t *region; | |
- | |
region = gdk_cairo_region_create_from_surface (surface); | |
gtk_widget_shape_combine_region (windata->win, region); | |
cairo_region_destroy (region); | |
- } else { | |
- gtk_widget_shape_combine_region (windata->win, NULL); | |
- return; | |
+ windata->last_width = windata->width; | |
+ windata->last_height = windata->height; | |
+ gtk_widget_queue_draw (GTK_WIDGET (windata->win)); | |
} | |
- | |
- windata->last_width = windata->width; | |
- windata->last_height = windata->height; | |
} | |
-static void | |
-paint_window (GtkWidget *widget, | |
- cairo_t *cr, | |
- WindowData *windata) | |
+static void paint_window (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
{ | |
- cairo_surface_t *surface; | |
cairo_t *cr2; | |
+ cairo_surface_t *surface; | |
if (windata->width == 0 || windata->height == 0) { | |
GtkAllocation allocation; | |
- | |
- gtk_widget_get_allocation(windata->win, &allocation); | |
+ gtk_widget_get_allocation (windata->win, &allocation); | |
windata->width = allocation.width; | |
windata->height = allocation.height; | |
} | |
- surface = cairo_surface_create_similar(cairo_get_target(cr), | |
- CAIRO_CONTENT_COLOR_ALPHA, | |
- windata->width, | |
- windata->height); | |
- | |
+ surface = cairo_surface_create_similar (cairo_get_target (cr), CAIRO_CONTENT_COLOR_ALPHA, windata->width, windata->height); | |
cr2 = cairo_create (surface); | |
- | |
- /* transparent background */ | |
cairo_rectangle (cr2, 0, 0, windata->width, windata->height); | |
- cairo_set_source_rgba (cr2, 0.0, 0.0, 0.0, 0.0); | |
- cairo_fill (cr2); | |
- | |
- nodoka_rounded_rectangle (cr2, 0, 0, windata->width , windata->height, 6); | |
- fill_background(widget, windata, cr2); | |
+ cairo_set_source_rgba (cr2, 0.0, 0.0, 0.0, 0.0); // transparent background color | |
cairo_fill (cr2); | |
+ nodoka_rounded_rectangle (cr2, 0, 0, windata->width, windata->height, 6); | |
+ fill_background (widget, windata, cr2); | |
cairo_destroy (cr2); | |
cairo_save (cr); | |
@@ -254,58 +246,38 @@ paint_window (GtkWidget *widget, | |
cairo_restore (cr); | |
update_shape_region (surface, windata); | |
- | |
cairo_surface_destroy (surface); | |
} | |
-static gboolean | |
-on_draw (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
+static gboolean on_draw (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
{ | |
paint_window (widget, cr, windata); | |
- | |
return FALSE; | |
} | |
-/* Event handlers */ | |
-static gboolean | |
-configure_event_cb(GtkWidget *nw, | |
- GdkEventConfigure *event, | |
- WindowData *windata) | |
+static gboolean on_configure_event (GtkWidget* widget, GdkEventConfigure* event, WindowData* windata) | |
{ | |
windata->width = event->width; | |
windata->height = event->height; | |
- | |
- gtk_widget_queue_draw(nw); | |
- | |
+ gtk_widget_queue_draw (widget); | |
return FALSE; | |
} | |
-static gboolean | |
-countdown_expose_cb(GtkWidget *pie, | |
- cairo_t *cr, | |
- WindowData *windata) | |
+static gboolean countdown_expose_cb (GtkWidget *pie, cairo_t *cr, WindowData *windata) | |
{ | |
cairo_t *cr2; | |
cairo_surface_t *surface; | |
GtkAllocation alloc; | |
- cairo_set_operator (cr, CAIRO_OPERATOR_SOURCE); | |
- | |
+ cairo_set_operator (cr, CAIRO_OPERATOR_OVER); | |
gtk_widget_get_allocation (pie, &alloc); | |
- surface = cairo_surface_create_similar (cairo_get_target (cr), | |
- CAIRO_CONTENT_COLOR_ALPHA, | |
- alloc.width, | |
- alloc.height); | |
- | |
+ surface = cairo_surface_create_similar (cairo_get_target (cr), CAIRO_CONTENT_COLOR_ALPHA, alloc.width, alloc.height); | |
cr2 = cairo_create (surface); | |
- | |
- cairo_translate (cr2, -alloc.x, -alloc.y); | |
- fill_background (pie, windata, cr2); | |
- cairo_translate (cr2, alloc.x, alloc.y); | |
- draw_pie (pie, windata, cr2); | |
+ cairo_set_source_rgba (cr2, 0.0, 0.0, 0.0, 0.0); // transparent background color | |
+ cairo_paint (cr2); | |
+ draw_pie (pie, windata, cr2); // countdown | |
cairo_fill (cr2); | |
- | |
cairo_destroy (cr2); | |
cairo_save (cr); | |
@@ -317,26 +289,13 @@ countdown_expose_cb(GtkWidget *pie, | |
return TRUE; | |
} | |
-static gboolean on_configure_event (GtkWidget* widget, GdkEventConfigure* event, WindowData* windata) | |
-{ | |
- windata->width = event->width; | |
- windata->height = event->height; | |
- | |
- gtk_widget_queue_draw (widget); | |
- | |
- return FALSE; | |
-} | |
- | |
static void on_composited_changed (GtkWidget* window, WindowData* windata) | |
{ | |
windata->composited = gdk_screen_is_composited (gtk_widget_get_screen(window)); | |
- | |
gtk_widget_queue_draw (window); | |
} | |
-static void | |
-action_clicked_cb(GtkWidget *w, GdkEventButton *event, | |
- ActionInvokedCb action_cb) | |
+static void action_clicked_cb (GtkWidget *w, GdkEventButton *event, ActionInvokedCb action_cb) | |
{ | |
GtkWindow *nw = g_object_get_data(G_OBJECT(w), "_nw"); | |
const char *key = g_object_get_data(G_OBJECT(w), "_action_key"); | |
@@ -344,24 +303,16 @@ action_clicked_cb(GtkWidget *w, GdkEventButton *event, | |
action_cb(nw, key); | |
} | |
- | |
- | |
/* Required functions */ | |
/* Checking if we support this notification daemon version */ | |
-gboolean | |
-theme_check_init(unsigned int major_ver, unsigned int minor_ver, | |
- unsigned int micro_ver) | |
+gboolean theme_check_init (unsigned int major_ver, unsigned int minor_ver, unsigned int micro_ver) | |
{ | |
return major_ver == NOTIFICATION_DAEMON_MAJOR_VERSION && minor_ver == NOTIFICATION_DAEMON_MINOR_VERSION && micro_ver == NOTIFICATION_DAEMON_MICRO_VERSION; | |
} | |
/* Sending theme info to the notification daemon */ | |
-void | |
-get_theme_info(char **theme_name, | |
- char **theme_ver, | |
- char **author, | |
- char **homepage) | |
+void get_theme_info (char **theme_name, char **theme_ver, char **author, char **homepage) | |
{ | |
*theme_name = g_strdup("Coco"); | |
*theme_ver = g_strdup_printf("%d.%d.%d", NOTIFICATION_DAEMON_MAJOR_VERSION, | |
@@ -372,8 +323,7 @@ get_theme_info(char **theme_name, | |
} | |
/* Create new notification */ | |
-GtkWindow * | |
-create_notification(UrlClickedCb url_clicked) | |
+GtkWindow* create_notification (UrlClickedCb url_clicked) | |
{ | |
GtkWidget *win; | |
GtkWidget *main_vbox; | |
@@ -389,15 +339,13 @@ create_notification(UrlClickedCb url_clicked) | |
win = gtk_window_new(GTK_WINDOW_POPUP); | |
gtk_window_set_resizable(GTK_WINDOW(win), FALSE); | |
+ gtk_widget_set_app_paintable(win, TRUE); | |
windata->win = win; | |
- | |
- windata->rtl = gtk_widget_get_default_direction(); | |
windata->composited = FALSE; | |
screen = gtk_window_get_screen(GTK_WINDOW(win)); | |
visual = gdk_screen_get_rgba_visual(screen); | |
- if (visual != NULL) | |
- { | |
+ if (visual != NULL) { | |
gtk_widget_set_visual(win, visual); | |
if (gdk_screen_is_composited(screen)) | |
windata->composited = TRUE; | |
@@ -406,25 +354,23 @@ create_notification(UrlClickedCb url_clicked) | |
gtk_window_set_title(GTK_WINDOW(win), "Notification"); | |
gtk_window_set_type_hint(GTK_WINDOW(win), GDK_WINDOW_TYPE_HINT_NOTIFICATION); | |
gtk_widget_add_events(win, GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK); | |
- gtk_widget_realize(win); | |
+ gtk_widget_set_size_request(win, WIDTH, -1); | |
- g_object_set_data_full(G_OBJECT(win), "windata", windata, | |
- (GDestroyNotify)destroy_windata); | |
+ g_object_set_data_full(G_OBJECT(win), "windata", windata, (GDestroyNotify) destroy_windata); | |
atk_object_set_role(gtk_widget_get_accessible(win), ATK_ROLE_ALERT); | |
- g_signal_connect(G_OBJECT(win), "configure_event", | |
- G_CALLBACK(configure_event_cb), windata); | |
- | |
- main_vbox = gtk_box_new(GTK_ORIENTATION_VERTICAL, 0); | |
- gtk_widget_show(main_vbox); | |
+ main_vbox = gtk_box_new (GTK_ORIENTATION_VERTICAL, 0); | |
+ gtk_widget_show (main_vbox); | |
gtk_container_add (GTK_CONTAINER (win), main_vbox); | |
+ //gtk_container_set_border_width (GTK_CONTAINER (main_vbox), 0); | |
- g_signal_connect (G_OBJECT (main_vbox), "draw", | |
- G_CALLBACK (on_draw), windata); | |
- | |
- g_signal_connect (G_OBJECT (win), "configure-event", G_CALLBACK (on_configure_event), windata); | |
- | |
- g_signal_connect (G_OBJECT (win), "composited-changed", G_CALLBACK (on_composited_changed), windata); | |
+ #if GTK_CHECK_VERSION (4,0,0) | |
+ gtk_widget_add_css_class (main_vbox, "notification-box"); | |
+ gtk_widget_add_css_class (main_vbox, "coco-theme"); | |
+ #else | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (main_vbox), "notification-box"); | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (main_vbox), "coco-theme"); | |
+ #endif | |
windata->main_hbox = gtk_box_new (GTK_ORIENTATION_HORIZONTAL, 0); | |
gtk_widget_set_halign (windata->main_hbox, GTK_ALIGN_START); | |
@@ -435,7 +381,7 @@ create_notification(UrlClickedCb url_clicked) | |
gtk_box_pack_start (GTK_BOX(main_vbox), windata->main_hbox, FALSE, FALSE, 0); | |
gtk_container_set_border_width(GTK_CONTAINER(windata->main_hbox), 13); | |
- /* The icon goes at the left */ | |
+ /* The icon goes at the left */ | |
windata->iconbox = gtk_box_new(GTK_ORIENTATION_VERTICAL, 0); | |
gtk_widget_show(windata->iconbox); | |
gtk_box_pack_start(GTK_BOX(windata->main_hbox), windata->iconbox, | |
@@ -445,14 +391,13 @@ create_notification(UrlClickedCb url_clicked) | |
gtk_box_pack_start(GTK_BOX(windata->iconbox), windata->icon, | |
FALSE, FALSE, 0); | |
- /* The title and the text at the right */ | |
+ /* The title and the text at the right */ | |
vbox = gtk_box_new (GTK_ORIENTATION_VERTICAL, 0); | |
gtk_widget_set_halign (vbox, GTK_ALIGN_START); | |
gtk_widget_set_margin_start (vbox, 8); | |
gtk_widget_show (vbox); | |
gtk_box_pack_start (GTK_BOX (windata->main_hbox), vbox, TRUE, TRUE, 0); | |
- | |
windata->summary_label = gtk_label_new(NULL); | |
gtk_widget_show(windata->summary_label); | |
gtk_box_pack_start(GTK_BOX(vbox), windata->summary_label, FALSE, FALSE, 0); | |
@@ -470,7 +415,7 @@ create_notification(UrlClickedCb url_clicked) | |
gtk_label_set_yalign (GTK_LABEL (windata->body_label), 0.0); | |
gtk_label_set_line_wrap(GTK_LABEL(windata->body_label), TRUE); | |
gtk_label_set_line_wrap_mode (GTK_LABEL (windata->body_label), PANGO_WRAP_WORD_CHAR); | |
- gtk_label_set_max_width_chars (GTK_LABEL (windata->body_label), 50); | |
+ gtk_label_set_max_width_chars (GTK_LABEL (windata->body_label), 50); | |
g_signal_connect(G_OBJECT(windata->body_label), "activate-link", | |
G_CALLBACK(activate_link), windata); | |
@@ -480,15 +425,29 @@ create_notification(UrlClickedCb url_clicked) | |
windata->actions_box = gtk_box_new(GTK_ORIENTATION_HORIZONTAL, 6); | |
gtk_widget_set_halign(windata->actions_box, GTK_ALIGN_END); | |
+ | |
+ #if GTK_CHECK_VERSION (4,0,0) | |
+ gtk_widget_add_css_class (windata->summary_label, "summary"); | |
+ gtk_widget_add_css_class (windata->body_label, "body"); | |
+ gtk_widget_add_css_class (windata->actions_box, "actions-box"); | |
+ #else | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->summary_label), "summary"); | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->body_label), "body"); | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->actions_box), "actions-box"); | |
+ #endif | |
+ | |
gtk_widget_show(windata->actions_box); | |
gtk_box_pack_start(GTK_BOX(vbox), windata->actions_box, FALSE, TRUE, 0); | |
+ g_signal_connect (G_OBJECT (win), "draw", G_CALLBACK (on_draw), windata); | |
+ g_signal_connect (G_OBJECT (win), "configure-event", G_CALLBACK (on_configure_event), windata); | |
+ g_signal_connect (G_OBJECT (win), "composited-changed", G_CALLBACK (on_composited_changed), windata); | |
+ | |
return GTK_WINDOW(win); | |
} | |
/* Set the notification text */ | |
-void | |
-set_notification_text(GtkWindow *nw, const char *summary, const char *body) | |
+void set_notification_text (GtkWindow *nw, const char *summary, const char *body) | |
{ | |
char *str; | |
size_t str_len; | |
@@ -546,7 +505,7 @@ set_notification_text(GtkWindow *nw, const char *summary, const char *body) | |
if ((body_label_text == NULL) || (strlen (body_label_text) == 0)) { | |
goto render_fail; | |
} | |
- goto renrer_ok; | |
+ goto render_ok; | |
} | |
render_fail: | |
@@ -557,7 +516,7 @@ render_fail: | |
g_free (quoted); | |
g_free (str); | |
-renrer_ok: | |
+render_ok: | |
xmlCleanupParser (); | |
if (body == NULL || *body == '\0') | |
@@ -573,8 +532,7 @@ renrer_ok: | |
} | |
/* Set notification icon */ | |
-void | |
-set_notification_icon(GtkWindow *nw, GdkPixbuf *pixbuf) | |
+void set_notification_icon (GtkWindow *nw, GdkPixbuf *pixbuf) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
g_assert(windata != NULL); | |
@@ -584,10 +542,8 @@ set_notification_icon(GtkWindow *nw, GdkPixbuf *pixbuf) | |
if (pixbuf != NULL) | |
{ | |
int pixbuf_width = gdk_pixbuf_get_width(pixbuf); | |
- | |
gtk_widget_show(windata->icon); | |
- gtk_widget_set_size_request(windata->iconbox, | |
- MAX(BODY_X_OFFSET, pixbuf_width), -1); | |
+ gtk_widget_set_size_request(windata->iconbox, MAX(BODY_X_OFFSET, pixbuf_width), -1); | |
} | |
else | |
{ | |
@@ -597,16 +553,13 @@ set_notification_icon(GtkWindow *nw, GdkPixbuf *pixbuf) | |
} | |
/* Set notification arrow */ | |
-void | |
-set_notification_arrow(GtkWidget *nw, gboolean visible, int x, int y) | |
+void set_notification_arrow (GtkWidget *nw, gboolean visible, int x, int y) | |
{ | |
/* nothing */ | |
} | |
/* Add notification action */ | |
-void | |
-add_notification_action(GtkWindow *nw, const char *text, const char *key, | |
- ActionInvokedCb cb) | |
+void add_notification_action (GtkWindow *nw, const char *text, const char *key, ActionInvokedCb cb) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
GtkWidget *label; | |
@@ -625,13 +578,18 @@ add_notification_action(GtkWindow *nw, const char *text, const char *key, | |
if (!windata->pie_countdown) { | |
windata->pie_countdown = gtk_drawing_area_new(); | |
gtk_widget_set_halign (windata->pie_countdown, GTK_ALIGN_END); | |
+ gtk_widget_set_valign (windata->pie_countdown, GTK_ALIGN_CENTER); | |
gtk_widget_show(windata->pie_countdown); | |
+ #if GTK_CHECK_VERSION (4,0,0) | |
+ gtk_widget_add_css_class (windata->pie_countdown, "countdown"); | |
+ #else | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->pie_countdown), "countdown"); | |
+ #endif | |
+ | |
gtk_box_pack_end (GTK_BOX (windata->actions_box), windata->pie_countdown, FALSE, TRUE, 0); | |
- gtk_widget_set_size_request(windata->pie_countdown, | |
- PIE_WIDTH, PIE_HEIGHT); | |
- g_signal_connect(G_OBJECT(windata->pie_countdown), "draw", | |
- G_CALLBACK(countdown_expose_cb), windata); | |
+ gtk_widget_set_size_request(windata->pie_countdown, PIE_WIDTH, PIE_HEIGHT); | |
+ g_signal_connect(G_OBJECT(windata->pie_countdown), "draw", G_CALLBACK (countdown_expose_cb), windata); | |
} | |
} | |
@@ -686,8 +644,7 @@ add_button: | |
} | |
/* Clear notification actions */ | |
-void | |
-clear_notification_actions(GtkWindow *nw) | |
+void clear_notification_actions (GtkWindow *nw) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
@@ -699,8 +656,7 @@ clear_notification_actions(GtkWindow *nw) | |
} | |
/* Move notification window */ | |
-void | |
-move_notification(GtkWidget *nw, int x, int y) | |
+void move_notification (GtkWidget *nw, int x, int y) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
g_assert(windata != NULL); | |
@@ -708,7 +664,6 @@ move_notification(GtkWidget *nw, int x, int y) | |
gtk_window_move(GTK_WINDOW(nw), x, y); | |
} | |
- | |
/* Optional Functions */ | |
/* Destroy notification */ | |
@@ -718,8 +673,7 @@ move_notification(GtkWidget *nw, int x, int y) | |
/* Hide notification */ | |
/* Set notification timeout */ | |
-void | |
-set_notification_timeout(GtkWindow *nw, glong timeout) | |
+void set_notification_timeout (GtkWindow *nw, glong timeout) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
g_assert(windata != NULL); | |
@@ -728,7 +682,7 @@ set_notification_timeout(GtkWindow *nw, glong timeout) | |
} | |
/* Set notification hints */ | |
-void set_notification_hints(GtkWindow *nw, GVariant *hints) | |
+void set_notification_hints (GtkWindow *nw, GVariant *hints) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
guint8 urgency; | |
@@ -755,8 +709,7 @@ void set_notification_hints(GtkWindow *nw, GVariant *hints) | |
} | |
/* Notification tick */ | |
-void | |
-notification_tick(GtkWindow *nw, glong remaining) | |
+void notification_tick (GtkWindow *nw, glong remaining) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
windata->remaining = remaining; | |
diff --git a/src/themes/nodoka/nodoka-theme.c b/src/themes/nodoka/nodoka-theme.c | |
index 2ad102e..4dad2b2 100644 | |
--- a/src/themes/nodoka/nodoka-theme.c | |
+++ b/src/themes/nodoka/nodoka-theme.c | |
@@ -1,10 +1,7 @@ | |
/* | |
- * nodoka-theme.c | |
- * This file is part of notification-daemon-engine-nodoka | |
- * | |
* Copyright (C) 2012 - Stefano Karapetsas <[email protected]> | |
* Copyright (C) 2008 - Martin Sourada | |
- * Copyright (C) 2012-2021 MATE Developers | |
+ * Copyright (C) 2012-2025 MATE Developers | |
* | |
* notification-daemon-engine-nodoka is free software; you can redistribute it | |
* and/or modify it under the terms of the GNU General Public License as | |
@@ -22,16 +19,14 @@ | |
* Boston, MA 02110-1301 USA | |
*/ | |
- | |
- | |
#include "config.h" | |
#include <glib/gi18n.h> | |
#include <gtk/gtk.h> | |
- | |
+#include <libxml/parser.h> | |
+#include <libxml/xmlmemory.h> | |
#include <libxml/xpath.h> | |
-/* Define basic nodoka types */ | |
typedef void (*ActionInvokedCb)(GtkWindow *nw, const char *key); | |
typedef void (*UrlClickedCb)(GtkWindow *nw, const char *url); | |
@@ -82,7 +77,6 @@ typedef struct | |
} WindowData; | |
- | |
enum | |
{ | |
URGENCY_LOW, | |
@@ -90,22 +84,22 @@ enum | |
URGENCY_CRITICAL | |
}; | |
-gboolean theme_check_init(unsigned int major_ver, unsigned int minor_ver, | |
+gboolean theme_check_init (unsigned int major_ver, unsigned int minor_ver, | |
unsigned int micro_ver); | |
-void get_theme_info(char **theme_name, char **theme_ver, char **author, | |
+void get_theme_info (char **theme_name, char **theme_ver, char **author, | |
char **homepage); | |
-GtkWindow* create_notification(UrlClickedCb url_clicked); | |
-void set_notification_text(GtkWindow *nw, const char *summary, | |
+GtkWindow* create_notification (UrlClickedCb url_clicked); | |
+void set_notification_text (GtkWindow *nw, const char *summary, | |
const char *body); | |
-void set_notification_icon(GtkWindow *nw, GdkPixbuf *pixbuf); | |
-void set_notification_arrow(GtkWidget *nw, gboolean visible, int x, int y); | |
-void add_notification_action(GtkWindow *nw, const char *text, const char *key, | |
+void set_notification_icon (GtkWindow *nw, GdkPixbuf *pixbuf); | |
+void set_notification_arrow (GtkWidget *nw, gboolean visible, int x, int y); | |
+void add_notification_action (GtkWindow *nw, const char *text, const char *key, | |
ActionInvokedCb cb); | |
-void clear_notification_actions(GtkWindow *nw); | |
-void move_notification(GtkWidget *nw, int x, int y); | |
-void set_notification_timeout(GtkWindow *nw, glong timeout); | |
-void set_notification_hints(GtkWindow *nw, GVariant *hints); | |
-void notification_tick(GtkWindow *nw, glong remaining); | |
+void clear_notification_actions (GtkWindow *nw); | |
+void move_notification (GtkWidget *nw, int x, int y); | |
+void set_notification_timeout (GtkWindow *nw, glong timeout); | |
+void set_notification_hints (GtkWindow *nw, GVariant *hints); | |
+void notification_tick (GtkWindow *nw, glong remaining); | |
#define STRIPE_WIDTH 32 | |
#define WIDTH 400 | |
@@ -123,18 +117,28 @@ void notification_tick(GtkWindow *nw, glong remaining); | |
#define BACKGROUND_OPACITY 0.92 | |
#define GRADIENT_CENTER 0.7 | |
-/* Support Nodoka Functions */ | |
+static void get_background_color (GtkStyleContext *context, GtkStateFlags state, GdkRGBA *color) | |
+{ | |
+ GdkRGBA *c; | |
+ | |
+ g_return_if_fail (color != NULL); | |
+ g_return_if_fail (GTK_IS_STYLE_CONTEXT (context)); | |
-/* Handle clicking on link */ | |
-static gboolean | |
-activate_link (GtkLabel *label, const char *url, WindowData *windata) | |
+ gtk_style_context_get (context, state, | |
+ "background-color", &c, | |
+ NULL); | |
+ | |
+ *color = *c; | |
+ gdk_rgba_free (c); | |
+} | |
+ | |
+static gboolean activate_link (GtkLabel *label, const char *url, WindowData *windata) | |
{ | |
windata->url_clicked (GTK_WINDOW (windata->win), url); | |
return TRUE; | |
} | |
-static void | |
-get_size_of_widgets_monitor(GtkWidget *widget, int *width, int *height) | |
+static void get_size_of_widgets_monitor (GtkWidget *widget, int *width, int *height) | |
{ | |
GdkWindow *window = gtk_widget_get_window (widget); | |
GdkMonitor *monitor = gdk_display_get_monitor_at_window ( | |
@@ -147,8 +151,7 @@ get_size_of_widgets_monitor(GtkWidget *widget, int *width, int *height) | |
} | |
/* Set if we have arrow down or arrow up */ | |
-static GtkArrowType | |
-get_notification_arrow_type(GtkWidget *nw) | |
+static GtkArrowType get_notification_arrow_type (GtkWidget *nw) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
int monitor_height; | |
@@ -167,8 +170,7 @@ get_notification_arrow_type(GtkWidget *nw) | |
} | |
/* Set arrow parameters like offset and position */ | |
-static void | |
-set_arrow_parameters (WindowData *windata) | |
+static void set_arrow_parameters (WindowData *windata) | |
{ | |
int monitor_width; | |
int x,y; | |
@@ -251,14 +253,12 @@ set_arrow_parameters (WindowData *windata) | |
gtk_window_move(GTK_WINDOW(windata->win), x, y); | |
} | |
-static void | |
-destroy_windata(WindowData *windata) | |
+static void destroy_windata (WindowData *windata) | |
{ | |
g_free(windata); | |
} | |
-static void | |
-update_spacers(GtkWidget *nw) | |
+static void update_spacers (GtkWidget *nw) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
@@ -287,8 +287,7 @@ update_spacers(GtkWidget *nw) | |
} | |
} | |
-static void | |
-update_content_hbox_visibility(WindowData *windata) | |
+static void update_content_hbox_visibility (WindowData *windata) | |
{ | |
/* | |
* This is all a hack, but until we have a libview-style ContentBox, | |
@@ -306,12 +305,7 @@ update_content_hbox_visibility(WindowData *windata) | |
} | |
} | |
-/* Draw fuctions */ | |
-/* Standard rounded rectangle */ | |
-static void | |
-nodoka_rounded_rectangle (cairo_t * cr, | |
- double x, double y, double w, double h, | |
- int radius) | |
+static void nodoka_rounded_rectangle (cairo_t * cr, double x, double y, double w, double h, int radius) | |
{ | |
cairo_move_to (cr, x + radius, y); | |
cairo_arc (cr, x + w - radius, y + radius, radius, G_PI * 1.5, G_PI * 2); | |
@@ -320,11 +314,7 @@ nodoka_rounded_rectangle (cairo_t * cr, | |
cairo_arc (cr, x + radius, y + radius, radius, G_PI, G_PI * 1.5); | |
} | |
-/* Rounded rectangle with arrow */ | |
-static void | |
-nodoka_rounded_rectangle_with_arrow (cairo_t * cr, | |
- double x, double y, double w, double h, | |
- int radius, ArrowParameters * arrow) | |
+static void nodoka_rounded_rectangle_with_arrow (cairo_t * cr, double x, double y, double w, double h, int radius, ArrowParameters * arrow) | |
{ | |
gboolean arrow_up; | |
arrow_up = (arrow->point_begin.y > arrow->point_middle.y); | |
@@ -376,9 +366,7 @@ nodoka_rounded_rectangle_with_arrow (cairo_t * cr, | |
} | |
-/* Fill background */ | |
-static void | |
-fill_background(GtkWidget *widget, WindowData *windata, cairo_t *cr) | |
+static void fill_background (GtkWidget *widget, WindowData *windata, cairo_t *cr) | |
{ | |
double alpha; | |
if (windata->composited) | |
@@ -403,12 +391,14 @@ fill_background(GtkWidget *widget, WindowData *windata, cairo_t *cr) | |
cairo_fill (cr); | |
} | |
- | |
-static void | |
-draw_stripe(GtkWidget *widget, WindowData *windata, cairo_t *cr) | |
+static void draw_stripe (GtkWidget *widget, WindowData *windata, cairo_t *cr) | |
{ | |
+ int stripe_x = 0; | |
+ if (gtk_widget_get_direction (widget) == GTK_TEXT_DIR_RTL) | |
+ stripe_x = windata->width - STRIPE_WIDTH - stripe_x; | |
+ | |
cairo_save (cr); | |
- cairo_rectangle (cr, 0, 0, STRIPE_WIDTH, windata->height); | |
+ cairo_rectangle (cr, stripe_x, 0, STRIPE_WIDTH, windata->height); | |
cairo_clip (cr); | |
gdouble color_mult = 1.0; | |
@@ -463,7 +453,6 @@ draw_stripe(GtkWidget *widget, WindowData *windata, cairo_t *cr) | |
break; | |
} | |
- | |
cairo_pattern_t *pattern; | |
pattern = cairo_pattern_create_linear (0, 0, 0, windata->height); | |
cairo_pattern_add_color_stop_rgba (pattern, 0, top_color.red / color_mult, top_color.green / color_mult, top_color.blue / color_mult, alpha); | |
@@ -483,8 +472,7 @@ draw_stripe(GtkWidget *widget, WindowData *windata, cairo_t *cr) | |
cairo_restore (cr); | |
} | |
-static void | |
-draw_border(GtkWidget *widget, WindowData *windata, cairo_t *cr) | |
+static void draw_border (GtkWidget *widget, WindowData *windata, cairo_t *cr) | |
{ | |
double alpha; | |
if (windata->composited) | |
@@ -510,14 +498,34 @@ draw_border(GtkWidget *widget, WindowData *windata, cairo_t *cr) | |
cairo_stroke (cr); | |
} | |
-static void | |
-draw_pie(GtkWidget *pie, WindowData *windata, cairo_t *cr) | |
+static void draw_pie (GtkWidget *pie, WindowData *windata, cairo_t *cr) | |
{ | |
if (windata->timeout == 0) | |
return; | |
gdouble arc_angle = 1.0 - (gdouble)windata->remaining / (gdouble)windata->timeout; | |
- cairo_set_source_rgba (cr, 1.0, 0.4, 0.0, 0.3); | |
+ GtkStyleContext *context; | |
+ GdkRGBA orig, bg; | |
+ | |
+ // :selected { background-color:#aabbcc; } ignored -> 1.0, 0.4, 0.0, 0.3 | |
+ context = gtk_widget_get_style_context (windata->win); | |
+ gtk_style_context_save (context); | |
+ gtk_style_context_set_state (context, GTK_STATE_FLAG_SELECTED); | |
+ get_background_color (context, GTK_STATE_FLAG_SELECTED, &orig); | |
+ gtk_style_context_restore (context); | |
+ | |
+ // .notification-box .countdown:selected { background-color:#aabbcc; } | |
+ context = gtk_widget_get_style_context (pie); | |
+ gtk_style_context_save (context); | |
+ gtk_style_context_set_state (context, GTK_STATE_FLAG_SELECTED); | |
+ get_background_color (context, GTK_STATE_FLAG_SELECTED, &bg); | |
+ gtk_style_context_restore (context); | |
+ | |
+ if (gdk_rgba_equal (&orig, &bg)) | |
+ cairo_set_source_rgba (cr, 1.0, 0.4, 0.0, 0.3); | |
+ else | |
+ cairo_set_source_rgba (cr, bg.red, bg.green, bg.blue, bg.alpha); | |
+ | |
cairo_move_to(cr, PIE_RADIUS, PIE_RADIUS); | |
cairo_arc_negative(cr, PIE_RADIUS, PIE_RADIUS, PIE_RADIUS, | |
-G_PI/2, (-0.25 + arc_angle)*2*G_PI); | |
@@ -526,49 +534,32 @@ draw_pie(GtkWidget *pie, WindowData *windata, cairo_t *cr) | |
cairo_fill (cr); | |
} | |
-static void | |
-update_shape_region (cairo_surface_t *surface, | |
- WindowData *windata) | |
+static void update_shape_region (cairo_surface_t *surface, WindowData *windata) | |
{ | |
if (windata->width == windata->last_width && windata->height == windata->last_height) | |
- { | |
return; | |
- } | |
- | |
- if (windata->width == 0 || windata->height == 0) | |
- { | |
- GtkAllocation allocation; | |
- gtk_widget_get_allocation (windata->win, &allocation); | |
- windata->width = MAX (allocation.width, 1); | |
- windata->height = MAX (allocation.height, 1); | |
+ if (windata->composited) { | |
+ gtk_widget_shape_combine_region (windata->win, NULL); | |
} | |
- | |
- if (!windata->composited) { | |
+ else { | |
cairo_region_t *region; | |
- | |
region = gdk_cairo_region_create_from_surface (surface); | |
gtk_widget_shape_combine_region (windata->win, region); | |
cairo_region_destroy (region); | |
- } else { | |
- gtk_widget_shape_combine_region (windata->win, NULL); | |
- return; | |
+ windata->last_width = windata->width; | |
+ windata->last_height = windata->height; | |
+ gtk_widget_queue_draw (GTK_WIDGET (windata->win)); | |
} | |
- | |
- windata->last_width = windata->width; | |
- windata->last_height = windata->height; | |
} | |
-static void | |
-paint_window (GtkWidget *widget, | |
- cairo_t *cr, | |
- WindowData *windata) | |
+static void paint_window (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
{ | |
cairo_t *cr2; | |
cairo_surface_t *surface; | |
- GtkAllocation allocation; | |
if (windata->width == 0 || windata->height == 0) { | |
+ GtkAllocation allocation; | |
gtk_widget_get_allocation (windata->win, &allocation); | |
windata->width = allocation.width; | |
windata->height = allocation.height; | |
@@ -577,17 +568,11 @@ paint_window (GtkWidget *widget, | |
if (windata->arrow.has_arrow) | |
set_arrow_parameters (windata); | |
- surface = cairo_surface_create_similar (cairo_get_target (cr), | |
- CAIRO_CONTENT_COLOR_ALPHA, | |
- windata->width, | |
- windata->height); | |
- | |
+ surface = cairo_surface_create_similar (cairo_get_target (cr), CAIRO_CONTENT_COLOR_ALPHA, windata->width, windata->height); | |
cr2 = cairo_create (surface); | |
- | |
- /* transparent background */ | |
- cairo_rectangle (cr2, 0, 0, windata->width, windata->height); | |
- cairo_set_source_rgba (cr2, 0.0, 0.0, 0.0, 0.0); | |
- cairo_fill (cr2); | |
+ cairo_rectangle (cr2, 0, 0, windata->width, windata->height); | |
+ cairo_set_source_rgba (cr2, 0.0, 0.0, 0.0, 0.0); // transparent background color | |
+ cairo_fill (cr2); | |
if (windata->arrow.has_arrow) { | |
nodoka_rounded_rectangle_with_arrow (cr2, 0, 0, | |
@@ -602,12 +587,9 @@ paint_window (GtkWidget *widget, | |
6); | |
} | |
- cairo_fill (cr2); | |
- | |
- fill_background(widget, windata, cr2); | |
- draw_border(widget, windata, cr2); | |
- draw_stripe(widget, windata, cr2); | |
- | |
+ fill_background (widget, windata, cr2); | |
+ draw_border (widget, windata, cr2); | |
+ draw_stripe (widget, windata, cr2); | |
cairo_destroy (cr2); | |
cairo_save (cr); | |
@@ -617,29 +599,22 @@ paint_window (GtkWidget *widget, | |
cairo_restore (cr); | |
update_shape_region (surface, windata); | |
- | |
cairo_surface_destroy (surface); | |
} | |
-static gboolean | |
-on_draw (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
+static gboolean on_draw (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
{ | |
paint_window (widget, cr, windata); | |
- | |
return FALSE; | |
} | |
-/* Event handlers */ | |
-static gboolean | |
-configure_event_cb(GtkWidget *nw, | |
- GdkEventConfigure *event, | |
- WindowData *windata) | |
+static gboolean on_configure_event (GtkWidget* widget, GdkEventConfigure* event, WindowData* windata) | |
{ | |
windata->width = event->width; | |
windata->height = event->height; | |
- update_spacers(nw); | |
- gtk_widget_queue_draw(nw); | |
+ update_spacers (widget); | |
+ gtk_widget_queue_draw (widget); | |
return FALSE; | |
} | |
@@ -647,35 +622,24 @@ configure_event_cb(GtkWidget *nw, | |
static void on_composited_changed (GtkWidget* window, WindowData* windata) | |
{ | |
windata->composited = gdk_screen_is_composited (gtk_widget_get_screen(window)); | |
- | |
gtk_widget_queue_draw (window); | |
} | |
-static gboolean | |
-countdown_expose_cb(GtkWidget *pie, | |
- cairo_t *cr, | |
- WindowData *windata) | |
+static gboolean countdown_expose_cb (GtkWidget *pie, cairo_t *cr, WindowData *windata) | |
{ | |
cairo_t *cr2; | |
cairo_surface_t *surface; | |
GtkAllocation alloc; | |
- cairo_set_operator(cr, CAIRO_OPERATOR_SOURCE); | |
- | |
+ cairo_set_operator (cr, CAIRO_OPERATOR_OVER); | |
gtk_widget_get_allocation (pie, &alloc); | |
- surface = cairo_surface_create_similar (cairo_get_target (cr), | |
- CAIRO_CONTENT_COLOR_ALPHA, | |
- alloc.width, | |
- alloc.height); | |
+ surface = cairo_surface_create_similar (cairo_get_target (cr), CAIRO_CONTENT_COLOR_ALPHA, alloc.width, alloc.height); | |
cr2 = cairo_create (surface); | |
- | |
- cairo_translate (cr2, -alloc.x, -alloc.y); | |
- fill_background (pie, windata, cr2); | |
- cairo_translate (cr2, alloc.x, alloc.y); | |
- draw_pie (pie, windata, cr2); | |
+ cairo_set_source_rgba (cr2, 0.0, 0.0, 0.0, 0.0); // transparent background color | |
+ cairo_paint (cr2); | |
+ draw_pie (pie, windata, cr2); // countdown | |
cairo_fill (cr2); | |
- | |
cairo_destroy (cr2); | |
cairo_save (cr); | |
@@ -687,9 +651,7 @@ countdown_expose_cb(GtkWidget *pie, | |
return TRUE; | |
} | |
-static void | |
-action_clicked_cb(GtkWidget *w, GdkEventButton *event, | |
- ActionInvokedCb action_cb) | |
+static void action_clicked_cb (GtkWidget *w, GdkEventButton *event, ActionInvokedCb action_cb) | |
{ | |
GtkWindow *nw = g_object_get_data(G_OBJECT(w), "_nw"); | |
const char *key = g_object_get_data(G_OBJECT(w), "_action_key"); | |
@@ -697,24 +659,16 @@ action_clicked_cb(GtkWidget *w, GdkEventButton *event, | |
action_cb(nw, key); | |
} | |
- | |
- | |
/* Required functions */ | |
/* Checking if we support this notification daemon version */ | |
-gboolean | |
-theme_check_init(unsigned int major_ver, unsigned int minor_ver, | |
- unsigned int micro_ver) | |
+gboolean theme_check_init (unsigned int major_ver, unsigned int minor_ver, unsigned int micro_ver) | |
{ | |
return major_ver == NOTIFICATION_DAEMON_MAJOR_VERSION && minor_ver == NOTIFICATION_DAEMON_MINOR_VERSION && micro_ver == NOTIFICATION_DAEMON_MICRO_VERSION; | |
} | |
/* Sending theme info to the notification daemon */ | |
-void | |
-get_theme_info(char **theme_name, | |
- char **theme_ver, | |
- char **author, | |
- char **homepage) | |
+void get_theme_info (char **theme_name, char **theme_ver, char **author, char **homepage) | |
{ | |
*theme_name = g_strdup("Nodoka"); | |
*theme_ver = g_strdup_printf("%d.%d.%d", NOTIFICATION_DAEMON_MAJOR_VERSION, | |
@@ -725,8 +679,7 @@ get_theme_info(char **theme_name, | |
} | |
/* Create new notification */ | |
-GtkWindow * | |
-create_notification(UrlClickedCb url_clicked) | |
+GtkWindow* create_notification (UrlClickedCb url_clicked) | |
{ | |
GtkWidget *spacer; | |
GtkWidget *win; | |
@@ -746,14 +699,13 @@ create_notification(UrlClickedCb url_clicked) | |
win = gtk_window_new(GTK_WINDOW_POPUP); | |
gtk_window_set_resizable(GTK_WINDOW(win), FALSE); | |
+ gtk_widget_set_app_paintable(win, TRUE); | |
windata->win = win; | |
- | |
windata->composited = FALSE; | |
screen = gtk_window_get_screen(GTK_WINDOW(win)); | |
visual = gdk_screen_get_rgba_visual(screen); | |
- if (visual != NULL) | |
- { | |
+ if (visual != NULL) { | |
gtk_widget_set_visual(win, visual); | |
if (gdk_screen_is_composited(screen)) | |
windata->composited = TRUE; | |
@@ -762,24 +714,28 @@ create_notification(UrlClickedCb url_clicked) | |
gtk_window_set_title(GTK_WINDOW(win), "Notification"); | |
gtk_window_set_type_hint(GTK_WINDOW(win), GDK_WINDOW_TYPE_HINT_NOTIFICATION); | |
gtk_widget_add_events(win, GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK); | |
- gtk_widget_realize(win); | |
gtk_widget_set_size_request(win, WIDTH, -1); | |
- g_object_set_data_full(G_OBJECT(win), "windata", windata, | |
- (GDestroyNotify)destroy_windata); | |
+ g_object_set_data_full(G_OBJECT(win), "windata", windata, (GDestroyNotify) destroy_windata); | |
atk_object_set_role(gtk_widget_get_accessible(win), ATK_ROLE_ALERT); | |
- g_signal_connect(G_OBJECT(win), "configure_event", | |
- G_CALLBACK(configure_event_cb), windata); | |
- | |
+ main_vbox = gtk_box_new (GTK_ORIENTATION_VERTICAL, 0); | |
+ gtk_widget_show (main_vbox); | |
+ gtk_container_add (GTK_CONTAINER (win), main_vbox); | |
+ //gtk_container_set_border_width (GTK_CONTAINER (main_vbox), 0); | |
+ | |
+ #if GTK_CHECK_VERSION (4,0,0) | |
+ gtk_widget_add_css_class (main_vbox, "notification-box"); | |
+ gtk_widget_add_css_class (main_vbox, "nodoka-theme"); | |
+ #else | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (main_vbox), "notification-box"); | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (main_vbox), "nodoka-theme"); | |
+ #endif | |
+ | |
+ g_signal_connect (G_OBJECT (win), "draw", G_CALLBACK (on_draw), windata); | |
+ g_signal_connect (G_OBJECT (win), "configure-event", G_CALLBACK (on_configure_event), windata); | |
g_signal_connect (G_OBJECT (win), "composited-changed", G_CALLBACK (on_composited_changed), windata); | |
- main_vbox = gtk_box_new(GTK_ORIENTATION_VERTICAL, 0); | |
- gtk_widget_show(main_vbox); | |
- gtk_container_add(GTK_CONTAINER(win), main_vbox); | |
- | |
- g_signal_connect (G_OBJECT (main_vbox), "draw", G_CALLBACK (on_draw), windata); | |
- | |
windata->top_spacer = gtk_image_new(); | |
gtk_box_pack_start(GTK_BOX(main_vbox), windata->top_spacer, | |
FALSE, FALSE, 0); | |
@@ -866,7 +822,7 @@ create_notification(UrlClickedCb url_clicked) | |
gtk_label_set_yalign (GTK_LABEL (windata->body_label), 0.0); | |
gtk_label_set_line_wrap(GTK_LABEL(windata->body_label), TRUE); | |
gtk_label_set_line_wrap_mode (GTK_LABEL (windata->body_label), PANGO_WRAP_WORD_CHAR); | |
- gtk_label_set_max_width_chars (GTK_LABEL (windata->body_label), 50); | |
+ gtk_label_set_max_width_chars (GTK_LABEL (windata->body_label), 50); | |
g_signal_connect(G_OBJECT(windata->body_label), "activate-link", | |
G_CALLBACK(activate_link), windata); | |
@@ -876,6 +832,17 @@ create_notification(UrlClickedCb url_clicked) | |
windata->actions_box = gtk_box_new(GTK_ORIENTATION_HORIZONTAL, 6); | |
gtk_widget_set_halign (windata->actions_box, GTK_ALIGN_END); | |
+ | |
+ #if GTK_CHECK_VERSION (4,0,0) | |
+ gtk_widget_add_css_class (windata->summary_label, "summary"); | |
+ gtk_widget_add_css_class (windata->body_label, "body"); | |
+ gtk_widget_add_css_class (windata->actions_box, "actions-box"); | |
+ #else | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->summary_label), "summary"); | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->body_label), "body"); | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->actions_box), "actions-box"); | |
+ #endif | |
+ | |
gtk_widget_show(windata->actions_box); | |
gtk_box_pack_start(GTK_BOX(vbox), windata->actions_box, FALSE, TRUE, 0); | |
@@ -883,8 +850,7 @@ create_notification(UrlClickedCb url_clicked) | |
} | |
/* Set the notification text */ | |
-void | |
-set_notification_text(GtkWindow *nw, const char *summary, const char *body) | |
+void set_notification_text (GtkWindow *nw, const char *summary, const char *body) | |
{ | |
char *str; | |
size_t str_len; | |
@@ -941,7 +907,7 @@ set_notification_text(GtkWindow *nw, const char *summary, const char *body) | |
if ((body_label_text == NULL) || (strlen (body_label_text) == 0)) { | |
goto render_fail; | |
} | |
- goto renrer_ok; | |
+ goto render_ok; | |
} | |
render_fail: | |
@@ -952,7 +918,7 @@ render_fail: | |
g_free (quoted); | |
g_free (str); | |
-renrer_ok: | |
+render_ok: | |
xmlCleanupParser (); | |
if (body == NULL || *body == '\0') | |
@@ -970,8 +936,7 @@ renrer_ok: | |
} | |
/* Set notification icon */ | |
-void | |
-set_notification_icon(GtkWindow *nw, GdkPixbuf *pixbuf) | |
+void set_notification_icon (GtkWindow *nw, GdkPixbuf *pixbuf) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
g_assert(windata != NULL); | |
@@ -996,8 +961,7 @@ set_notification_icon(GtkWindow *nw, GdkPixbuf *pixbuf) | |
} | |
/* Set notification arrow */ | |
-void | |
-set_notification_arrow(GtkWidget *nw, gboolean visible, int x, int y) | |
+void set_notification_arrow (GtkWidget *nw, gboolean visible, int x, int y) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
g_assert(windata != NULL); | |
@@ -1010,9 +974,7 @@ set_notification_arrow(GtkWidget *nw, gboolean visible, int x, int y) | |
} | |
/* Add notification action */ | |
-void | |
-add_notification_action(GtkWindow *nw, const char *text, const char *key, | |
- ActionInvokedCb cb) | |
+void add_notification_action (GtkWindow *nw, const char *text, const char *key, ActionInvokedCb cb) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
GtkWidget *label; | |
@@ -1032,13 +994,18 @@ add_notification_action(GtkWindow *nw, const char *text, const char *key, | |
if (!windata->pie_countdown) { | |
windata->pie_countdown = gtk_drawing_area_new(); | |
gtk_widget_set_halign (windata->pie_countdown, GTK_ALIGN_END); | |
+ gtk_widget_set_valign (windata->pie_countdown, GTK_ALIGN_CENTER); | |
gtk_widget_show(windata->pie_countdown); | |
+ #if GTK_CHECK_VERSION (4,0,0) | |
+ gtk_widget_add_css_class (windata->pie_countdown, "countdown"); | |
+ #else | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->pie_countdown), "countdown"); | |
+ #endif | |
+ | |
gtk_box_pack_end (GTK_BOX (windata->actions_box), windata->pie_countdown, FALSE, TRUE, 0); | |
- gtk_widget_set_size_request(windata->pie_countdown, | |
- PIE_WIDTH, PIE_HEIGHT); | |
- g_signal_connect(G_OBJECT(windata->pie_countdown), "draw", | |
- G_CALLBACK(countdown_expose_cb), windata); | |
+ gtk_widget_set_size_request(windata->pie_countdown, PIE_WIDTH, PIE_HEIGHT); | |
+ g_signal_connect(G_OBJECT(windata->pie_countdown), "draw", G_CALLBACK(countdown_expose_cb), windata); | |
} | |
} | |
@@ -1093,8 +1060,7 @@ add_button: | |
} | |
/* Clear notification actions */ | |
-void | |
-clear_notification_actions(GtkWindow *nw) | |
+void clear_notification_actions (GtkWindow *nw) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
@@ -1106,8 +1072,7 @@ clear_notification_actions(GtkWindow *nw) | |
} | |
/* Move notification window */ | |
-void | |
-move_notification(GtkWidget *nw, int x, int y) | |
+void move_notification (GtkWidget *nw, int x, int y) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
g_assert(windata != NULL); | |
@@ -1122,7 +1087,6 @@ move_notification(GtkWidget *nw, int x, int y) | |
} | |
} | |
- | |
/* Optional Functions */ | |
/* Destroy notification */ | |
@@ -1132,8 +1096,7 @@ move_notification(GtkWidget *nw, int x, int y) | |
/* Hide notification */ | |
/* Set notification timeout */ | |
-void | |
-set_notification_timeout(GtkWindow *nw, glong timeout) | |
+void set_notification_timeout (GtkWindow *nw, glong timeout) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
g_assert(windata != NULL); | |
@@ -1142,7 +1105,7 @@ set_notification_timeout(GtkWindow *nw, glong timeout) | |
} | |
/* Set notification hints */ | |
-void set_notification_hints(GtkWindow *nw, GVariant *hints) | |
+void set_notification_hints (GtkWindow *nw, GVariant *hints) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
guint8 urgency; | |
@@ -1169,8 +1132,7 @@ void set_notification_hints(GtkWindow *nw, GVariant *hints) | |
} | |
/* Notification tick */ | |
-void | |
-notification_tick(GtkWindow *nw, glong remaining) | |
+void notification_tick (GtkWindow *nw, glong remaining) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
windata->remaining = remaining; | |
diff --git a/src/themes/slider/theme.c b/src/themes/slider/theme.c | |
index 8cc203c..87c147f 100644 | |
--- a/src/themes/slider/theme.c | |
+++ b/src/themes/slider/theme.c | |
@@ -1,9 +1,8 @@ | |
-/* -*- Mode: C; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- | |
- * | |
+/* | |
* Copyright (C) 2006-2007 Christian Hammond <[email protected]> | |
* Copyright (C) 2009 Red Hat, Inc. | |
* Copyright (C) 2011 Perberos <[email protected]> | |
- * Copyright (C) 2012-2021 MATE Developers | |
+ * Copyright (C) 2012-2025 MATE Developers | |
* | |
* This program is free software; you can redistribute it and/or modify | |
* it under the terms of the GNU General Public License as published by | |
@@ -25,7 +24,8 @@ | |
#include <glib/gi18n.h> | |
#include <gtk/gtk.h> | |
- | |
+#include <libxml/parser.h> | |
+#include <libxml/xmlmemory.h> | |
#include <libxml/xpath.h> | |
typedef void (*ActionInvokedCb) (GtkWindow* nw, const char* key); | |
@@ -65,22 +65,22 @@ enum { | |
URGENCY_CRITICAL | |
}; | |
-gboolean theme_check_init(unsigned int major_ver, unsigned int minor_ver, | |
+gboolean theme_check_init (unsigned int major_ver, unsigned int minor_ver, | |
unsigned int micro_ver); | |
-void get_theme_info(char **theme_name, char **theme_ver, char **author, | |
+void get_theme_info (char **theme_name, char **theme_ver, char **author, | |
char **homepage); | |
-GtkWindow* create_notification(UrlClickedCb url_clicked); | |
-void set_notification_text(GtkWindow *nw, const char *summary, | |
+GtkWindow* create_notification (UrlClickedCb url_clicked); | |
+void set_notification_text (GtkWindow *nw, const char *summary, | |
const char *body); | |
-void set_notification_icon(GtkWindow *nw, GdkPixbuf *pixbuf); | |
-void set_notification_arrow(GtkWidget *nw, gboolean visible, int x, int y); | |
-void add_notification_action(GtkWindow *nw, const char *text, const char *key, | |
+void set_notification_icon (GtkWindow *nw, GdkPixbuf *pixbuf); | |
+void set_notification_arrow (GtkWidget *nw, gboolean visible, int x, int y); | |
+void add_notification_action (GtkWindow *nw, const char *text, const char *key, | |
ActionInvokedCb cb); | |
-void clear_notification_actions(GtkWindow *nw); | |
-void move_notification(GtkWidget *nw, int x, int y); | |
-void set_notification_timeout(GtkWindow *nw, glong timeout); | |
-void set_notification_hints(GtkWindow *nw, GVariant *hints); | |
-void notification_tick(GtkWindow *nw, glong remaining); | |
+void clear_notification_actions (GtkWindow *nw); | |
+void move_notification (GtkWidget *nw, int x, int y); | |
+void set_notification_timeout (GtkWindow *nw, glong timeout); | |
+void set_notification_hints (GtkWindow *nw, GVariant *hints); | |
+void notification_tick (GtkWindow *nw, glong remaining); | |
gboolean get_always_stack(GtkWidget* nw); | |
#define WIDTH 400 | |
@@ -96,7 +96,7 @@ gboolean get_always_stack(GtkWidget* nw); | |
#define MAX_ICON_SIZE IMAGE_SIZE | |
-static void draw_round_rect(cairo_t* cr, gdouble aspect, gdouble x, gdouble y, gdouble corner_radius, gdouble width, gdouble height) | |
+static void draw_round_rect (cairo_t* cr, gdouble aspect, gdouble x, gdouble y, gdouble corner_radius, gdouble width, gdouble height) | |
{ | |
gdouble radius = corner_radius / aspect; | |
@@ -127,10 +127,7 @@ static void draw_round_rect(cairo_t* cr, gdouble aspect, gdouble x, gdouble y, g | |
cairo_arc(cr, x + radius, y + radius, radius, 180.0f * G_PI / 180.0f, 270.0f * G_PI / 180.0f); | |
} | |
-static void | |
-get_background_color (GtkStyleContext *context, | |
- GtkStateFlags state, | |
- GdkRGBA *color) | |
+static void get_background_color (GtkStyleContext *context, GtkStateFlags state, GdkRGBA *color) | |
{ | |
GdkRGBA *c; | |
@@ -145,7 +142,7 @@ get_background_color (GtkStyleContext *context, | |
gdk_rgba_free (c); | |
} | |
-static void fill_background(GtkWidget* widget, WindowData* windata, cairo_t* cr) | |
+static void fill_background (GtkWidget* widget, WindowData* windata, cairo_t* cr) | |
{ | |
GtkAllocation allocation; | |
GtkStyleContext *context; | |
@@ -177,102 +174,68 @@ static void fill_background(GtkWidget* widget, WindowData* windata, cairo_t* cr) | |
cairo_stroke(cr); | |
} | |
-static void | |
-update_shape_region (cairo_surface_t *surface, | |
- WindowData *windata) | |
+static void update_shape_region (cairo_surface_t *surface, WindowData *windata) | |
{ | |
if (windata->width == windata->last_width && windata->height == windata->last_height) | |
- { | |
return; | |
- } | |
- | |
- if (windata->width == 0 || windata->height == 0) | |
- { | |
- GtkAllocation allocation; | |
- gtk_widget_get_allocation (windata->win, &allocation); | |
- windata->width = MAX (allocation.width, 1); | |
- windata->height = MAX (allocation.height, 1); | |
+ if (windata->composited) { | |
+ gtk_widget_shape_combine_region (windata->win, NULL); | |
} | |
- | |
- if (!windata->composited) { | |
+ else { | |
cairo_region_t *region; | |
- | |
region = gdk_cairo_region_create_from_surface (surface); | |
gtk_widget_shape_combine_region (windata->win, region); | |
cairo_region_destroy (region); | |
- } else { | |
- gtk_widget_shape_combine_region (windata->win, NULL); | |
- return; | |
+ windata->last_width = windata->width; | |
+ windata->last_height = windata->height; | |
+ gtk_widget_queue_draw (GTK_WIDGET (windata->win)); | |
} | |
- | |
- windata->last_width = windata->width; | |
- windata->last_height = windata->height; | |
} | |
-static void paint_window (GtkWidget *widget, | |
- cairo_t *cr, | |
- WindowData *windata) | |
+static void paint_window (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
{ | |
- cairo_surface_t *surface; | |
cairo_t *cr2; | |
- GtkAllocation allocation; | |
+ cairo_surface_t *surface; | |
+ if (windata->width == 0 || windata->height == 0) { | |
+ GtkAllocation allocation; | |
gtk_widget_get_allocation (windata->win, &allocation); | |
- | |
- if (windata->width == 0 || windata->height == 0) | |
- { | |
- windata->width = MAX (allocation.width, 1); | |
- windata->height = MAX (allocation.height, 1); | |
+ windata->width = allocation.width; | |
+ windata->height = allocation.height; | |
} | |
- surface = cairo_surface_create_similar (cairo_get_target (cr), | |
- CAIRO_CONTENT_COLOR_ALPHA, | |
- windata->width, | |
- windata->height); | |
- | |
+ surface = cairo_surface_create_similar (cairo_get_target (cr), CAIRO_CONTENT_COLOR_ALPHA, windata->width, windata->height); | |
cr2 = cairo_create (surface); | |
- | |
- /* transparent background */ | |
cairo_rectangle (cr2, 0, 0, windata->width, windata->height); | |
- cairo_set_source_rgba (cr2, 0.0, 0.0, 0.0, 0.0); | |
+ cairo_set_source_rgba (cr2, 0.0, 0.0, 0.0, 0.0); // transparent background color | |
cairo_fill (cr2); | |
fill_background (widget, windata, cr2); | |
- | |
- cairo_destroy(cr2); | |
+ cairo_destroy (cr2); | |
cairo_save (cr); | |
cairo_set_operator (cr, CAIRO_OPERATOR_SOURCE); | |
- cairo_set_source_surface(cr, surface, 0, 0); | |
- cairo_paint(cr); | |
- update_shape_region (surface, windata); | |
+ cairo_set_source_surface (cr, surface, 0, 0); | |
+ cairo_paint (cr); | |
cairo_restore (cr); | |
- cairo_surface_destroy(surface); | |
-} | |
- | |
-static gboolean on_window_map(GtkWidget* widget, GdkEvent* event, WindowData* windata) | |
-{ | |
- return FALSE; | |
+ update_shape_region (surface, windata); | |
+ cairo_surface_destroy (surface); | |
} | |
-static gboolean | |
-on_draw (GtkWidget *widget, | |
- cairo_t *cr, | |
- WindowData *windata) | |
+static gboolean on_draw (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
{ | |
paint_window (widget, cr, windata); | |
- | |
return FALSE; | |
} | |
-static void destroy_windata(WindowData* windata) | |
+static void destroy_windata (WindowData* windata) | |
{ | |
g_free(windata); | |
} | |
-static void update_content_hbox_visibility(WindowData* windata) | |
+static void update_content_hbox_visibility (WindowData* windata) | |
{ | |
if (gtk_widget_get_visible(windata->icon) || gtk_widget_get_visible(windata->body_label) || gtk_widget_get_visible(windata->actions_box)) | |
{ | |
@@ -289,24 +252,18 @@ static gboolean on_configure_event(GtkWidget* widget, GdkEventConfigure* event, | |
windata->width = event->width; | |
windata->height = event->height; | |
- gtk_widget_queue_draw(widget); | |
+ gtk_widget_queue_draw (widget); | |
return FALSE; | |
} | |
-static void on_window_realize(GtkWidget* widget, WindowData* windata) | |
-{ | |
- /* Nothing */ | |
-} | |
- | |
-static void on_composited_changed(GtkWidget* window, WindowData* windata) | |
+static void on_composited_changed (GtkWidget* window, WindowData* windata) | |
{ | |
- windata->composited = gdk_screen_is_composited(gtk_widget_get_screen(window)); | |
- | |
- gtk_widget_queue_draw (windata->win); | |
+ windata->composited = gdk_screen_is_composited (gtk_widget_get_screen(window)); | |
+ gtk_widget_queue_draw (window); | |
} | |
-GtkWindow* create_notification(UrlClickedCb url_clicked) | |
+GtkWindow* create_notification (UrlClickedCb url_clicked) | |
{ | |
GtkWidget* win; | |
GtkWidget* main_vbox; | |
@@ -325,42 +282,41 @@ GtkWindow* create_notification(UrlClickedCb url_clicked) | |
win = gtk_window_new(GTK_WINDOW_POPUP); | |
gtk_window_set_resizable(GTK_WINDOW(win), FALSE); | |
gtk_widget_set_app_paintable(win, TRUE); | |
- g_signal_connect(G_OBJECT(win), "map-event", G_CALLBACK(on_window_map), windata); | |
- g_signal_connect(G_OBJECT(win), "draw", G_CALLBACK(on_draw), windata); | |
- g_signal_connect(G_OBJECT(win), "realize", G_CALLBACK(on_window_realize), windata); | |
- | |
windata->win = win; | |
- | |
windata->composited = FALSE; | |
- | |
screen = gtk_window_get_screen(GTK_WINDOW(win)); | |
- | |
visual = gdk_screen_get_rgba_visual(screen); | |
- if (visual != NULL) | |
- { | |
- gtk_widget_set_visual(win, visual); | |
+ if (visual != NULL) { | |
+ gtk_widget_set_visual(win, visual); | |
if (gdk_screen_is_composited(screen)) | |
- { | |
windata->composited = TRUE; | |
- } | |
} | |
- g_signal_connect(win, "composited-changed", G_CALLBACK(on_composited_changed), windata); | |
- | |
gtk_window_set_title(GTK_WINDOW(win), "Notification"); | |
gtk_window_set_type_hint(GTK_WINDOW(win), GDK_WINDOW_TYPE_HINT_NOTIFICATION); | |
gtk_widget_add_events(win, GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK); | |
+ gtk_widget_set_size_request(win, WIDTH, -1); | |
g_object_set_data_full(G_OBJECT(win), "windata", windata, (GDestroyNotify) destroy_windata); | |
atk_object_set_role(gtk_widget_get_accessible(win), ATK_ROLE_ALERT); | |
- g_signal_connect(G_OBJECT(win), "configure-event", G_CALLBACK(on_configure_event), windata); | |
+ main_vbox = gtk_box_new (GTK_ORIENTATION_VERTICAL, 0); | |
+ gtk_widget_show (main_vbox); | |
+ gtk_container_add (GTK_CONTAINER (win), main_vbox); | |
+ gtk_container_set_border_width (GTK_CONTAINER (main_vbox), 12); | |
+ | |
+ #if GTK_CHECK_VERSION (4,0,0) | |
+ gtk_widget_add_css_class (main_vbox, "notification-box"); | |
+ gtk_widget_add_css_class (main_vbox, "slider-theme"); | |
+ #else | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (main_vbox), "notification-box"); | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (main_vbox), "slider-theme"); | |
+ #endif | |
- main_vbox = gtk_box_new(GTK_ORIENTATION_VERTICAL, 0); | |
- gtk_widget_show(main_vbox); | |
- gtk_container_add(GTK_CONTAINER(win), main_vbox); | |
- gtk_container_set_border_width(GTK_CONTAINER(main_vbox), 12); | |
+ g_signal_connect (G_OBJECT (win), "draw", G_CALLBACK (on_draw), windata); | |
+ g_signal_connect (G_OBJECT (win), "configure-event", G_CALLBACK (on_configure_event), windata); | |
+ g_signal_connect (G_OBJECT (win), "composited-changed", G_CALLBACK (on_composited_changed), windata); | |
windata->main_hbox = gtk_box_new(GTK_ORIENTATION_HORIZONTAL, 0); | |
gtk_widget_show(windata->main_hbox); | |
@@ -431,7 +387,7 @@ GtkWindow* create_notification(UrlClickedCb url_clicked) | |
gtk_label_set_yalign (GTK_LABEL (windata->body_label), 0.0); | |
gtk_label_set_line_wrap(GTK_LABEL(windata->body_label), TRUE); | |
gtk_label_set_line_wrap_mode (GTK_LABEL (windata->body_label), PANGO_WRAP_WORD_CHAR); | |
- gtk_label_set_max_width_chars (GTK_LABEL (windata->body_label), 50); | |
+ gtk_label_set_max_width_chars (GTK_LABEL (windata->body_label), 50); | |
g_signal_connect_swapped(G_OBJECT(windata->body_label), "activate-link", G_CALLBACK(windata->url_clicked), win); | |
atkobj = gtk_widget_get_accessible(windata->body_label); | |
@@ -439,14 +395,24 @@ GtkWindow* create_notification(UrlClickedCb url_clicked) | |
windata->actions_box = gtk_box_new(GTK_ORIENTATION_HORIZONTAL, 6); | |
gtk_widget_set_halign (windata->actions_box, GTK_ALIGN_END); | |
- gtk_widget_show(windata->actions_box); | |
+ #if GTK_CHECK_VERSION (4,0,0) | |
+ gtk_widget_add_css_class (windata->summary_label, "summary"); | |
+ gtk_widget_add_css_class (windata->body_label, "body"); | |
+ gtk_widget_add_css_class (windata->actions_box, "actions-box"); | |
+ #else | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->summary_label), "summary"); | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->body_label), "body"); | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->actions_box), "actions-box"); | |
+ #endif | |
+ | |
+ gtk_widget_show(windata->actions_box); | |
gtk_box_pack_start (GTK_BOX (vbox), windata->actions_box, FALSE, TRUE, 0); | |
return GTK_WINDOW(win); | |
} | |
-void set_notification_hints(GtkWindow *nw, GVariant *hints) | |
+void set_notification_hints (GtkWindow *nw, GVariant *hints) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
guint8 urgency; | |
@@ -472,7 +438,7 @@ void set_notification_hints(GtkWindow *nw, GVariant *hints) | |
} | |
} | |
-void set_notification_timeout(GtkWindow *nw, glong timeout) | |
+void set_notification_timeout (GtkWindow *nw, glong timeout) | |
{ | |
WindowData* windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
@@ -481,7 +447,7 @@ void set_notification_timeout(GtkWindow *nw, glong timeout) | |
windata->timeout = timeout; | |
} | |
-void notification_tick(GtkWindow* nw, glong remaining) | |
+void notification_tick (GtkWindow* nw, glong remaining) | |
{ | |
WindowData* windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
@@ -493,7 +459,7 @@ void notification_tick(GtkWindow* nw, glong remaining) | |
} | |
} | |
-void set_notification_text(GtkWindow* nw, const char* summary, const char* body) | |
+void set_notification_text (GtkWindow* nw, const char* summary, const char* body) | |
{ | |
char* str; | |
size_t str_len; | |
@@ -555,7 +521,7 @@ void set_notification_text(GtkWindow* nw, const char* summary, const char* body) | |
if ((body_label_text == NULL) || (strlen (body_label_text) == 0)) { | |
goto render_fail; | |
} | |
- goto renrer_ok; | |
+ goto render_ok; | |
} | |
render_fail: | |
@@ -564,7 +530,7 @@ render_fail: | |
gtk_label_set_markup (GTK_LABEL (windata->body_label), quoted); | |
g_free (quoted); | |
-renrer_ok: | |
+render_ok: | |
xmlCleanupParser (); | |
if (body == NULL || *body == '\0') | |
@@ -627,7 +593,7 @@ static GdkPixbuf* scale_pixbuf(GdkPixbuf* pixbuf, int max_width, int max_height, | |
} | |
} | |
-void set_notification_icon(GtkWindow* nw, GdkPixbuf* pixbuf) | |
+void set_notification_icon (GtkWindow* nw, GdkPixbuf* pixbuf) | |
{ | |
WindowData* windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
@@ -660,17 +626,14 @@ void set_notification_icon(GtkWindow* nw, GdkPixbuf* pixbuf) | |
update_content_hbox_visibility(windata); | |
} | |
-void set_notification_arrow(GtkWidget* nw, gboolean visible, int x, int y) | |
+void set_notification_arrow (GtkWidget* nw, gboolean visible, int x, int y) | |
{ | |
WindowData* windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
g_assert(windata != NULL); | |
} | |
-static void | |
-paint_countdown (GtkWidget *pie, | |
- cairo_t* cr, | |
- WindowData* windata) | |
+static void paint_countdown (GtkWidget *pie, cairo_t* cr, WindowData* windata) | |
{ | |
GtkStyleContext* context; | |
GdkRGBA bg; | |
@@ -678,50 +641,41 @@ paint_countdown (GtkWidget *pie, | |
cairo_t* cr2; | |
cairo_surface_t* surface; | |
- context = gtk_widget_get_style_context(windata->win); | |
- | |
+ // :selected { background-color:#aabbcc; } or | |
+ // .notification-box .countdown:selected { background-color:#aabbcc; } | |
+ context = gtk_widget_get_style_context (pie); | |
gtk_style_context_save (context); | |
gtk_style_context_set_state (context, GTK_STATE_FLAG_SELECTED); | |
- | |
get_background_color (context, GTK_STATE_FLAG_SELECTED, &bg); | |
- | |
gtk_style_context_restore (context); | |
gtk_widget_get_allocation(pie, &allocation); | |
- cairo_set_operator(cr, CAIRO_OPERATOR_SOURCE); | |
- surface = cairo_surface_create_similar(cairo_get_target(cr), | |
- CAIRO_CONTENT_COLOR_ALPHA, | |
- allocation.width, | |
- allocation.height); | |
+ cairo_set_operator(cr, CAIRO_OPERATOR_OVER); | |
+ surface = cairo_surface_create_similar (cairo_get_target(cr), | |
+ CAIRO_CONTENT_COLOR_ALPHA, | |
+ allocation.width, | |
+ allocation.height); | |
cr2 = cairo_create (surface); | |
- | |
- fill_background (pie, windata, cr2); | |
- | |
if (windata->timeout > 0) | |
{ | |
gdouble pct = (gdouble) windata->remaining / (gdouble) windata->timeout; | |
- | |
gdk_cairo_set_source_rgba (cr2, &bg); | |
- | |
cairo_move_to (cr2, PIE_RADIUS, PIE_RADIUS); | |
cairo_arc_negative (cr2, PIE_RADIUS, PIE_RADIUS, PIE_RADIUS, -G_PI_2, -(pct * G_PI * 2) - G_PI_2); | |
cairo_line_to (cr2, PIE_RADIUS, PIE_RADIUS); | |
cairo_fill (cr2); | |
} | |
- | |
- cairo_destroy(cr2); | |
+ cairo_destroy (cr2); | |
cairo_save (cr); | |
cairo_set_source_surface (cr, surface, 0, 0); | |
cairo_paint (cr); | |
cairo_restore (cr); | |
- | |
cairo_surface_destroy(surface); | |
} | |
-static gboolean | |
-on_countdown_draw (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
+static gboolean on_countdown_draw (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
{ | |
paint_countdown (widget, cr, windata); | |
@@ -736,7 +690,7 @@ static void on_action_clicked(GtkWidget* w, GdkEventButton *event, ActionInvoked | |
action_cb(nw, key); | |
} | |
-void add_notification_action(GtkWindow* nw, const char* text, const char* key, ActionInvokedCb cb) | |
+void add_notification_action (GtkWindow* nw, const char* text, const char* key, ActionInvokedCb cb) | |
{ | |
WindowData* windata; | |
GtkWidget* label; | |
@@ -749,7 +703,7 @@ void add_notification_action(GtkWindow* nw, const char* text, const char* key, A | |
g_assert(windata != NULL); | |
- if (!gtk_widget_get_visible(windata->actions_box)) | |
+ if (gtk_widget_get_visible(windata->actions_box)) | |
{ | |
gtk_widget_show(windata->actions_box); | |
update_content_hbox_visibility(windata); | |
@@ -761,11 +715,15 @@ void add_notification_action(GtkWindow* nw, const char* text, const char* key, A | |
gtk_widget_set_valign (windata->pie_countdown, GTK_ALIGN_CENTER); | |
gtk_widget_show(windata->pie_countdown); | |
+ #if GTK_CHECK_VERSION (4,0,0) | |
+ gtk_widget_add_css_class (windata->pie_countdown, "countdown"); | |
+ #else | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->pie_countdown), "countdown"); | |
+ #endif | |
+ | |
gtk_box_pack_end (GTK_BOX (windata->actions_box), windata->pie_countdown, FALSE, TRUE, 0); | |
- gtk_widget_set_size_request(windata->pie_countdown, | |
- PIE_WIDTH, PIE_HEIGHT); | |
- g_signal_connect(G_OBJECT(windata->pie_countdown), "draw", | |
- G_CALLBACK(on_countdown_draw), windata); | |
+ gtk_widget_set_size_request(windata->pie_countdown, PIE_WIDTH, PIE_HEIGHT); | |
+ g_signal_connect(G_OBJECT(windata->pie_countdown), "draw", G_CALLBACK(on_countdown_draw), windata); | |
} | |
} | |
@@ -817,7 +775,7 @@ add_button: | |
gtk_widget_show_all(windata->actions_box); | |
} | |
-void clear_notification_actions(GtkWindow* nw) | |
+void clear_notification_actions (GtkWindow* nw) | |
{ | |
WindowData* windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
@@ -827,7 +785,7 @@ void clear_notification_actions(GtkWindow* nw) | |
gtk_container_foreach(GTK_CONTAINER(windata->actions_box), (GtkCallback) gtk_widget_destroy, NULL); | |
} | |
-void move_notification(GtkWidget* widget, int x, int y) | |
+void move_notification (GtkWidget* widget, int x, int y) | |
{ | |
WindowData* windata = g_object_get_data(G_OBJECT(widget), "windata"); | |
@@ -836,7 +794,7 @@ void move_notification(GtkWidget* widget, int x, int y) | |
gtk_window_move(GTK_WINDOW(windata->win), x, y); | |
} | |
-void get_theme_info(char** theme_name, char** theme_ver, char** author, char** homepage) | |
+void get_theme_info (char** theme_name, char** theme_ver, char** author, char** homepage) | |
{ | |
*theme_name = g_strdup("Slider"); | |
*theme_ver = g_strdup_printf("%d.%d.%d", NOTIFICATION_DAEMON_MAJOR_VERSION, NOTIFICATION_DAEMON_MINOR_VERSION, NOTIFICATION_DAEMON_MICRO_VERSION); | |
@@ -849,7 +807,7 @@ gboolean get_always_stack(GtkWidget* nw) | |
return TRUE; | |
} | |
-gboolean theme_check_init(unsigned int major_ver, unsigned int minor_ver, unsigned int micro_ver) | |
+gboolean theme_check_init (unsigned int major_ver, unsigned int minor_ver, unsigned int micro_ver) | |
{ | |
return major_ver == NOTIFICATION_DAEMON_MAJOR_VERSION && minor_ver == NOTIFICATION_DAEMON_MINOR_VERSION && micro_ver == NOTIFICATION_DAEMON_MICRO_VERSION; | |
} | |
diff --git a/src/themes/standard/theme.c b/src/themes/standard/theme.c | |
index ad44424..7a16559 100644 | |
--- a/src/themes/standard/theme.c | |
+++ b/src/themes/standard/theme.c | |
@@ -1,9 +1,8 @@ | |
-/* -*- Mode: C; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- | |
- * | |
+/* | |
* Copyright (C) 2006-2007 Christian Hammond <[email protected]> | |
* Copyright (C) 2009 Red Hat, Inc. | |
* Copyright (C) 2011 Perberos <[email protected]> | |
- * Copyright (C) 2012-2021 MATE Developers | |
+ * Copyright (C) 2012-2025 MATE Developers | |
* | |
* This program is free software; you can redistribute it and/or modify | |
* it under the terms of the GNU General Public License as published by | |
@@ -20,11 +19,13 @@ | |
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA | |
* 02110-1301, USA. | |
*/ | |
+ | |
#include "config.h" | |
#include <glib/gi18n.h> | |
#include <gtk/gtk.h> | |
- | |
+#include <libxml/parser.h> | |
+#include <libxml/xmlmemory.h> | |
#include <libxml/xpath.h> | |
typedef void (*ActionInvokedCb) (GtkWindow* nw, const char* key); | |
@@ -82,29 +83,28 @@ enum { | |
URGENCY_CRITICAL | |
}; | |
-gboolean theme_check_init(unsigned int major_ver, unsigned int minor_ver, | |
+gboolean theme_check_init (unsigned int major_ver, unsigned int minor_ver, | |
unsigned int micro_ver); | |
-void get_theme_info(char **theme_name, char **theme_ver, char **author, | |
+void get_theme_info (char **theme_name, char **theme_ver, char **author, | |
char **homepage); | |
-GtkWindow* create_notification(UrlClickedCb url_clicked); | |
-void set_notification_text(GtkWindow *nw, const char *summary, | |
+GtkWindow* create_notification (UrlClickedCb url_clicked); | |
+void set_notification_text (GtkWindow *nw, const char *summary, | |
const char *body); | |
-void set_notification_icon(GtkWindow *nw, GdkPixbuf *pixbuf); | |
-void set_notification_arrow(GtkWidget *nw, gboolean visible, int x, int y); | |
-void add_notification_action(GtkWindow *nw, const char *text, const char *key, | |
+void set_notification_icon (GtkWindow *nw, GdkPixbuf *pixbuf); | |
+void set_notification_arrow (GtkWidget *nw, gboolean visible, int x, int y); | |
+void add_notification_action (GtkWindow *nw, const char *text, const char *key, | |
ActionInvokedCb cb); | |
-void clear_notification_actions(GtkWindow *nw); | |
-void move_notification(GtkWidget *nw, int x, int y); | |
-void set_notification_timeout(GtkWindow *nw, glong timeout); | |
-void set_notification_hints(GtkWindow *nw, GVariant *hints); | |
-void notification_tick(GtkWindow *nw, glong remaining); | |
+void clear_notification_actions (GtkWindow *nw); | |
+void move_notification (GtkWidget *nw, int x, int y); | |
+void set_notification_timeout (GtkWindow *nw, glong timeout); | |
+void set_notification_hints (GtkWindow *nw, GVariant *hints); | |
+void notification_tick (GtkWindow *nw, glong remaining); | |
//#define ENABLE_GRADIENT_LOOK | |
- | |
#ifdef ENABLE_GRADIENT_LOOK | |
- #define STRIPE_WIDTH 45 | |
+#define STRIPE_WIDTH 45 | |
#else | |
- #define STRIPE_WIDTH 30 | |
+#define STRIPE_WIDTH 30 | |
#endif | |
#define WIDTH 400 | |
@@ -121,10 +121,7 @@ void notification_tick(GtkWindow *nw, glong remaining); | |
#define BACKGROUND_OPACITY 0.92 | |
#define BOTTOM_GRADIENT_HEIGHT 30 | |
-static void | |
-get_background_color (GtkStyleContext *context, | |
- GtkStateFlags state, | |
- GdkRGBA *color) | |
+static void get_background_color (GtkStyleContext *context, GtkStateFlags state, GdkRGBA *color) | |
{ | |
GdkRGBA *c; | |
@@ -139,7 +136,7 @@ get_background_color (GtkStyleContext *context, | |
gdk_rgba_free (c); | |
} | |
-static void fill_background(GtkWidget* widget, WindowData* windata, cairo_t* cr) | |
+static void fill_background (GtkWidget* widget, WindowData* windata, cairo_t* cr) | |
{ | |
GtkStyleContext *context; | |
GdkRGBA bg; | |
@@ -148,14 +145,11 @@ static void fill_background(GtkWidget* widget, WindowData* windata, cairo_t* cr) | |
gtk_widget_get_allocation(widget, &allocation); | |
- #ifdef ENABLE_GRADIENT_LOOK | |
- | |
- cairo_pattern_t *gradient; | |
- int gradient_y; | |
- | |
- gradient_y = allocation.height - BOTTOM_GRADIENT_HEIGHT; | |
- | |
- #endif | |
+#ifdef ENABLE_GRADIENT_LOOK | |
+ cairo_pattern_t *gradient; | |
+ int gradient_y; | |
+ gradient_y = allocation.height - BOTTOM_GRADIENT_HEIGHT; | |
+#endif | |
context = gtk_widget_get_style_context (windata->win); | |
@@ -179,30 +173,30 @@ static void fill_background(GtkWidget* widget, WindowData* windata, cairo_t* cr) | |
cairo_fill(cr); | |
- #ifdef ENABLE_GRADIENT_LOOK | |
- /* Add a very subtle gradient to the bottom of the notification */ | |
- gradient = cairo_pattern_create_linear(0, gradient_y, 0, allocation.height); | |
- cairo_pattern_add_color_stop_rgba(gradient, 0, 0, 0, 0, 0); | |
- cairo_pattern_add_color_stop_rgba(gradient, 1, 0, 0, 0, 0.15); | |
- cairo_rectangle(cr, 0, gradient_y, allocation.width, BOTTOM_GRADIENT_HEIGHT); | |
- | |
- cairo_set_source(cr, gradient); | |
- cairo_fill(cr); | |
- cairo_pattern_destroy(gradient); | |
- #endif | |
+#ifdef ENABLE_GRADIENT_LOOK | |
+ /* Add a very subtle gradient to the bottom of the notification */ | |
+ gradient = cairo_pattern_create_linear(0, gradient_y, 0, allocation.height); | |
+ cairo_pattern_add_color_stop_rgba(gradient, 0, 0, 0, 0, 0); | |
+ cairo_pattern_add_color_stop_rgba(gradient, 1, 0, 0, 0, 0.15); | |
+ cairo_rectangle(cr, 0, gradient_y, allocation.width, BOTTOM_GRADIENT_HEIGHT); | |
+ | |
+ cairo_set_source(cr, gradient); | |
+ cairo_fill(cr); | |
+ cairo_pattern_destroy(gradient); | |
+#endif | |
} | |
-static void draw_stripe(GtkWidget* widget, WindowData* windata, cairo_t* cr) | |
+static void draw_stripe (GtkWidget* widget, WindowData* windata, cairo_t* cr) | |
{ | |
GtkStyleContext* context; | |
GdkRGBA bg; | |
int stripe_x; | |
int stripe_y; | |
int stripe_height; | |
- #ifdef ENABLE_GRADIENT_LOOK | |
- cairo_pattern_t* gradient; | |
- double r, g, b; | |
- #endif | |
+#ifdef ENABLE_GRADIENT_LOOK | |
+ cairo_pattern_t* gradient; | |
+ double r, g, b; | |
+#endif | |
context = gtk_widget_get_style_context (widget); | |
@@ -247,24 +241,24 @@ static void draw_stripe(GtkWidget* widget, WindowData* windata, cairo_t* cr) | |
cairo_rectangle(cr, stripe_x, stripe_y, STRIPE_WIDTH, stripe_height); | |
- #ifdef ENABLE_GRADIENT_LOOK | |
- r = color.red / 65535.0; | |
- g = color.green / 65535.0; | |
- b = color.blue / 65535.0; | |
- | |
- gradient = cairo_pattern_create_linear(stripe_x, 0, STRIPE_WIDTH, 0); | |
- cairo_pattern_add_color_stop_rgba(gradient, 0, r, g, b, 1); | |
- cairo_pattern_add_color_stop_rgba(gradient, 1, r, g, b, 0); | |
- cairo_set_source(cr, gradient); | |
- cairo_fill(cr); | |
- cairo_pattern_destroy(gradient); | |
- #else | |
- gdk_cairo_set_source_rgba (cr, &bg); | |
- cairo_fill(cr); | |
- #endif | |
+#ifdef ENABLE_GRADIENT_LOOK | |
+ r = color.red / 65535.0; | |
+ g = color.green / 65535.0; | |
+ b = color.blue / 65535.0; | |
+ | |
+ gradient = cairo_pattern_create_linear(stripe_x, 0, STRIPE_WIDTH, 0); | |
+ cairo_pattern_add_color_stop_rgba(gradient, 0, r, g, b, 1); | |
+ cairo_pattern_add_color_stop_rgba(gradient, 1, r, g, b, 0); | |
+ cairo_set_source(cr, gradient); | |
+ cairo_fill(cr); | |
+ cairo_pattern_destroy(gradient); | |
+#else | |
+ gdk_cairo_set_source_rgba (cr, &bg); | |
+ cairo_fill(cr); | |
+#endif | |
} | |
-static GtkArrowType get_notification_arrow_type(GtkWidget* nw) | |
+static GtkArrowType get_notification_arrow_type (GtkWidget* nw) | |
{ | |
WindowData* windata; | |
GdkScreen* screen; | |
@@ -298,7 +292,7 @@ static GtkArrowType get_notification_arrow_type(GtkWidget* nw) | |
i++;\ | |
} G_STMT_END | |
-static void create_border_with_arrow(GtkWidget* nw, WindowData* windata) | |
+static void create_border_with_arrow (GtkWidget* nw, WindowData* windata) | |
{ | |
int width; | |
int height; | |
@@ -487,7 +481,7 @@ static void create_border_with_arrow(GtkWidget* nw, WindowData* windata) | |
g_free(shape_points); | |
} | |
-static void draw_border(GtkWidget* widget, WindowData *windata, cairo_t* cr) | |
+static void draw_border (GtkWidget* widget, WindowData *windata, cairo_t* cr) | |
{ | |
cairo_set_source_rgba(cr, 0.0, 0.0, 0.0, 1.0); | |
cairo_set_line_width(cr, 1.0); | |
@@ -519,54 +513,45 @@ static void draw_border(GtkWidget* widget, WindowData *windata, cairo_t* cr) | |
cairo_stroke(cr); | |
} | |
-static void | |
-paint_window (GtkWidget *widget, | |
- cairo_t *cr, | |
- WindowData *windata) | |
+static void paint_window (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
{ | |
- cairo_t* cr2; | |
- cairo_surface_t* surface; | |
- GtkAllocation allocation; | |
- | |
- gtk_widget_get_allocation(windata->win, &allocation); | |
- | |
- if (windata->width == 0) | |
- { | |
- windata->width = allocation.width; | |
- windata->height = allocation.height; | |
+ cairo_t *cr2; | |
+ cairo_surface_t *surface; | |
+ | |
+ if (windata->width == 0 || windata->height == 0) { | |
+ GtkAllocation allocation; | |
+ gtk_widget_get_allocation (windata->win, &allocation); | |
+ windata->width = allocation.width; | |
+ windata->height = allocation.height; | |
} | |
- cairo_set_operator(cr, CAIRO_OPERATOR_SOURCE); | |
- | |
- gtk_widget_get_allocation(widget, &allocation); | |
- | |
- surface = cairo_surface_create_similar (cairo_get_target (cr), | |
- CAIRO_CONTENT_COLOR_ALPHA, | |
- allocation.width, | |
- allocation.height); | |
- | |
+ surface = cairo_surface_create_similar (cairo_get_target (cr), CAIRO_CONTENT_COLOR_ALPHA, windata->width, windata->height); | |
cr2 = cairo_create (surface); | |
- | |
- fill_background(widget, windata, cr2); | |
- draw_border(widget, windata, cr2); | |
- draw_stripe(widget, windata, cr2); | |
+ cairo_rectangle (cr2, 0, 0, windata->width, windata->height); | |
+ cairo_set_source_rgba (cr2, 0.0, 0.0, 0.0, 0.0); // transparent background color | |
cairo_fill (cr2); | |
+ | |
+ fill_background (widget, windata, cr2); | |
+ draw_border (widget, windata, cr2); | |
+ draw_stripe (widget, windata, cr2); | |
cairo_destroy (cr2); | |
+ cairo_save (cr); | |
+ cairo_set_operator (cr, CAIRO_OPERATOR_SOURCE); | |
cairo_set_source_surface (cr, surface, 0, 0); | |
- cairo_paint(cr); | |
- cairo_surface_destroy(surface); | |
+ cairo_paint (cr); | |
+ cairo_restore (cr); | |
+ | |
+ cairo_surface_destroy (surface); | |
} | |
-static gboolean | |
-on_draw (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
+static gboolean on_draw (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
{ | |
paint_window (widget, cr, windata); | |
- | |
return FALSE; | |
} | |
-static void destroy_windata(WindowData* windata) | |
+static void destroy_windata (WindowData* windata) | |
{ | |
if (windata->window_region != NULL) | |
{ | |
@@ -576,7 +561,7 @@ static void destroy_windata(WindowData* windata) | |
g_free(windata); | |
} | |
-static void update_spacers(GtkWidget* nw) | |
+static void update_spacers (GtkWidget* nw) | |
{ | |
WindowData* windata; | |
@@ -607,7 +592,7 @@ static void update_spacers(GtkWidget* nw) | |
} | |
} | |
-static void update_content_hbox_visibility(WindowData* windata) | |
+static void update_content_hbox_visibility (WindowData* windata) | |
{ | |
/* | |
* This is all a hack, but until we have a libview-style ContentBox, | |
@@ -623,25 +608,31 @@ static void update_content_hbox_visibility(WindowData* windata) | |
} | |
} | |
-static gboolean configure_event_cb(GtkWidget* nw, GdkEventConfigure* event, WindowData* windata) | |
+static gboolean on_configure_event (GtkWidget* widget, GdkEventConfigure* event, WindowData* windata) | |
{ | |
windata->width = event->width; | |
windata->height = event->height; | |
- update_spacers(nw); | |
- gtk_widget_queue_draw(nw); | |
+ update_spacers (widget); | |
+ gtk_widget_queue_draw (widget); | |
return FALSE; | |
} | |
-static gboolean activate_link(GtkLabel* label, const char* url, WindowData* windata) | |
+static void on_composited_changed (GtkWidget* window, WindowData* windata) | |
+{ | |
+ windata->composited = gdk_screen_is_composited (gtk_widget_get_screen(window)); | |
+ gtk_widget_queue_draw (window); | |
+} | |
+ | |
+static gboolean activate_link (GtkLabel* label, const char* url, WindowData* windata) | |
{ | |
windata->url_clicked(GTK_WINDOW(windata->win), url); | |
return TRUE; | |
} | |
-GtkWindow* create_notification(UrlClickedCb url_clicked) | |
+GtkWindow* create_notification (UrlClickedCb url_clicked) | |
{ | |
GtkWidget* spacer; | |
GtkWidget* win; | |
@@ -662,42 +653,42 @@ GtkWindow* create_notification(UrlClickedCb url_clicked) | |
win = gtk_window_new(GTK_WINDOW_POPUP); | |
gtk_window_set_resizable(GTK_WINDOW(win), FALSE); | |
+ gtk_widget_set_app_paintable(win, TRUE); | |
windata->win = win; | |
- | |
windata->composited = FALSE; | |
- | |
- | |
screen = gtk_window_get_screen(GTK_WINDOW(win)); | |
- | |
visual = gdk_screen_get_rgba_visual(screen); | |
- if (visual != NULL) | |
- { | |
+ if (visual != NULL) { | |
gtk_widget_set_visual(win, visual); | |
- | |
if (gdk_screen_is_composited(screen)) | |
- { | |
windata->composited = TRUE; | |
- } | |
} | |
gtk_window_set_title(GTK_WINDOW(win), "Notification"); | |
gtk_window_set_type_hint(GTK_WINDOW(win), GDK_WINDOW_TYPE_HINT_NOTIFICATION); | |
gtk_widget_add_events(win, GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK); | |
- gtk_widget_realize(win); | |
gtk_widget_set_size_request(win, WIDTH, -1); | |
g_object_set_data_full(G_OBJECT(win), "windata", windata, (GDestroyNotify) destroy_windata); | |
atk_object_set_role(gtk_widget_get_accessible(win), ATK_ROLE_ALERT); | |
- g_signal_connect(G_OBJECT(win), "configure_event", G_CALLBACK(configure_event_cb), windata); | |
- | |
- main_vbox = gtk_box_new(GTK_ORIENTATION_VERTICAL, 0); | |
- gtk_widget_show(main_vbox); | |
+ main_vbox = gtk_box_new (GTK_ORIENTATION_VERTICAL, 0); | |
+ gtk_widget_show (main_vbox); | |
gtk_container_add (GTK_CONTAINER (win), main_vbox); | |
- gtk_container_set_border_width(GTK_CONTAINER(main_vbox), 1); | |
+ gtk_container_set_border_width (GTK_CONTAINER (main_vbox), 1); | |
- g_signal_connect (G_OBJECT (main_vbox), "draw", G_CALLBACK (on_draw), windata); | |
+ #if GTK_CHECK_VERSION (4,0,0) | |
+ gtk_widget_add_css_class (main_vbox, "notification-box"); | |
+ gtk_widget_add_css_class (main_vbox, "default-theme"); | |
+ #else | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (main_vbox), "notification-box"); | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (main_vbox), "default-theme"); | |
+ #endif | |
+ | |
+ g_signal_connect (G_OBJECT (win), "draw", G_CALLBACK (on_draw), windata); | |
+ g_signal_connect (G_OBJECT (win), "configure-event", G_CALLBACK (on_configure_event), windata); | |
+ g_signal_connect (G_OBJECT (win), "composited-changed", G_CALLBACK (on_composited_changed), windata); | |
windata->top_spacer = gtk_image_new(); | |
gtk_box_pack_start(GTK_BOX(main_vbox), windata->top_spacer, FALSE, FALSE, 0); | |
@@ -782,7 +773,7 @@ GtkWindow* create_notification(UrlClickedCb url_clicked) | |
gtk_label_set_yalign (GTK_LABEL (windata->body_label), 0.0); | |
gtk_label_set_line_wrap(GTK_LABEL(windata->body_label), TRUE); | |
gtk_label_set_line_wrap_mode (GTK_LABEL (windata->body_label), PANGO_WRAP_WORD_CHAR); | |
- gtk_label_set_max_width_chars (GTK_LABEL (windata->body_label), 50); | |
+ gtk_label_set_max_width_chars (GTK_LABEL (windata->body_label), 50); | |
g_signal_connect(G_OBJECT(windata->body_label), "activate-link", G_CALLBACK(activate_link), windata); | |
atkobj = gtk_widget_get_accessible(windata->body_label); | |
@@ -790,13 +781,24 @@ GtkWindow* create_notification(UrlClickedCb url_clicked) | |
windata->actions_box = gtk_box_new(GTK_ORIENTATION_HORIZONTAL, 6); | |
gtk_widget_set_halign (windata->actions_box, GTK_ALIGN_END); | |
+ | |
+ #if GTK_CHECK_VERSION (4,0,0) | |
+ gtk_widget_add_css_class (windata->summary_label, "summary"); | |
+ gtk_widget_add_css_class (windata->body_label, "body"); | |
+ gtk_widget_add_css_class (windata->actions_box, "actions-box"); | |
+ #else | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->summary_label), "summary"); | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->body_label), "body"); | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->actions_box), "actions-box"); | |
+ #endif | |
+ | |
gtk_widget_show(windata->actions_box); | |
gtk_box_pack_start(GTK_BOX(vbox), windata->actions_box, FALSE, TRUE, 0); | |
return GTK_WINDOW(win); | |
} | |
-void set_notification_hints(GtkWindow *nw, GVariant *hints) | |
+void set_notification_hints (GtkWindow *nw, GVariant *hints) | |
{ | |
WindowData *windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
guint8 urgency; | |
@@ -822,7 +824,7 @@ void set_notification_hints(GtkWindow *nw, GVariant *hints) | |
} | |
} | |
-void set_notification_timeout(GtkWindow* nw, glong timeout) | |
+void set_notification_timeout (GtkWindow* nw, glong timeout) | |
{ | |
WindowData* windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
@@ -831,7 +833,7 @@ void set_notification_timeout(GtkWindow* nw, glong timeout) | |
windata->timeout = timeout; | |
} | |
-void notification_tick(GtkWindow* nw, glong remaining) | |
+void notification_tick (GtkWindow* nw, glong remaining) | |
{ | |
WindowData* windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
@@ -843,7 +845,7 @@ void notification_tick(GtkWindow* nw, glong remaining) | |
} | |
} | |
-void set_notification_text(GtkWindow* nw, const char* summary, const char* body) | |
+void set_notification_text (GtkWindow* nw, const char* summary, const char* body) | |
{ | |
char* str; | |
size_t str_len; | |
@@ -903,7 +905,7 @@ void set_notification_text(GtkWindow* nw, const char* summary, const char* body) | |
if ((body_label_text == NULL) || (strlen (body_label_text) == 0)) { | |
goto render_fail; | |
} | |
- goto renrer_ok; | |
+ goto render_ok; | |
} | |
render_fail: | |
@@ -912,7 +914,7 @@ render_fail: | |
gtk_label_set_markup (GTK_LABEL (windata->body_label), quoted); | |
g_free (quoted); | |
-renrer_ok: | |
+render_ok: | |
xmlCleanupParser (); | |
if (body == NULL || *body == '\0') | |
@@ -937,7 +939,7 @@ renrer_ok: | |
gtk_widget_set_size_request(windata->summary_label, WIDTH - (1 * 2) - (10 * 2) - SPACER_LEFT - req.width - (6 * 2), -1); | |
} | |
-void set_notification_icon(GtkWindow* nw, GdkPixbuf* pixbuf) | |
+void set_notification_icon (GtkWindow* nw, GdkPixbuf* pixbuf) | |
{ | |
WindowData* windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
@@ -961,7 +963,7 @@ void set_notification_icon(GtkWindow* nw, GdkPixbuf* pixbuf) | |
update_content_hbox_visibility(windata); | |
} | |
-void set_notification_arrow(GtkWidget* nw, gboolean visible, int x, int y) | |
+void set_notification_arrow (GtkWidget* nw, gboolean visible, int x, int y) | |
{ | |
WindowData* windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
@@ -974,10 +976,7 @@ void set_notification_arrow(GtkWidget* nw, gboolean visible, int x, int y) | |
update_spacers(nw); | |
} | |
-static void | |
-paint_countdown (GtkWidget *pie, | |
- cairo_t *cr, | |
- WindowData *windata) | |
+static void paint_countdown (GtkWidget *pie, cairo_t *cr, WindowData *windata) | |
{ | |
GtkStyleContext *context; | |
GdkRGBA bg; | |
@@ -985,57 +984,48 @@ paint_countdown (GtkWidget *pie, | |
cairo_t* cr2; | |
cairo_surface_t* surface; | |
- context = gtk_widget_get_style_context (windata->win); | |
- | |
+ // :selected { background-color:#aabbcc; } or | |
+ // .notification-box .countdown:selected { background-color:#aabbcc; } | |
+ context = gtk_widget_get_style_context (pie); | |
gtk_style_context_save (context); | |
gtk_style_context_set_state (context, GTK_STATE_FLAG_SELECTED); | |
- | |
get_background_color (context, GTK_STATE_FLAG_SELECTED, &bg); | |
- | |
gtk_style_context_restore (context); | |
gtk_widget_get_allocation(pie, &alloc); | |
- cairo_set_operator(cr, CAIRO_OPERATOR_SOURCE); | |
+ cairo_set_operator(cr, CAIRO_OPERATOR_OVER); | |
surface = cairo_surface_create_similar (cairo_get_target(cr), | |
CAIRO_CONTENT_COLOR_ALPHA, | |
alloc.width, | |
alloc.height); | |
cr2 = cairo_create (surface); | |
- | |
- fill_background (pie, windata, cr2); | |
- | |
if (windata->timeout > 0) | |
{ | |
gdouble pct = (gdouble) windata->remaining / (gdouble) windata->timeout; | |
- | |
gdk_cairo_set_source_rgba (cr2, &bg); | |
- | |
cairo_move_to (cr2, PIE_RADIUS, PIE_RADIUS); | |
cairo_arc_negative (cr2, PIE_RADIUS, PIE_RADIUS, PIE_RADIUS, -G_PI_2, -(pct * G_PI * 2) - G_PI_2); | |
cairo_line_to (cr2, PIE_RADIUS, PIE_RADIUS); | |
cairo_fill (cr2); | |
} | |
- | |
- cairo_destroy(cr2); | |
+ cairo_destroy (cr2); | |
cairo_save (cr); | |
cairo_set_source_surface (cr, surface, 0, 0); | |
cairo_paint (cr); | |
cairo_restore (cr); | |
- | |
cairo_surface_destroy(surface); | |
} | |
-static gboolean | |
-on_countdown_draw (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
+static gboolean on_countdown_draw (GtkWidget *widget, cairo_t *cr, WindowData *windata) | |
{ | |
paint_countdown (widget, cr, windata); | |
return FALSE; | |
} | |
-static void action_clicked_cb(GtkWidget* w, GdkEventButton* event, ActionInvokedCb action_cb) | |
+static void action_clicked_cb (GtkWidget* w, GdkEventButton* event, ActionInvokedCb action_cb) | |
{ | |
GtkWindow* nw; | |
const char* key; | |
@@ -1044,7 +1034,7 @@ static void action_clicked_cb(GtkWidget* w, GdkEventButton* event, ActionInvoked | |
action_cb(nw, key); | |
} | |
-void add_notification_action(GtkWindow* nw, const char* text, const char* key, ActionInvokedCb cb) | |
+void add_notification_action (GtkWindow* nw, const char* text, const char* key, ActionInvokedCb cb) | |
{ | |
WindowData* windata; | |
GtkWidget* label; | |
@@ -1066,13 +1056,18 @@ void add_notification_action(GtkWindow* nw, const char* text, const char* key, A | |
if (!windata->pie_countdown) { | |
windata->pie_countdown = gtk_drawing_area_new(); | |
gtk_widget_set_halign (windata->pie_countdown, GTK_ALIGN_END); | |
+ gtk_widget_set_valign (windata->pie_countdown, GTK_ALIGN_CENTER); | |
gtk_widget_show(windata->pie_countdown); | |
+ #if GTK_CHECK_VERSION (4,0,0) | |
+ gtk_widget_add_css_class (windata->pie_countdown, "countdown"); | |
+ #else | |
+ gtk_style_context_add_class (gtk_widget_get_style_context (windata->pie_countdown), "countdown"); | |
+ #endif | |
+ | |
gtk_box_pack_end (GTK_BOX (windata->actions_box), windata->pie_countdown, FALSE, TRUE, 0); | |
- gtk_widget_set_size_request(windata->pie_countdown, | |
- PIE_WIDTH, PIE_HEIGHT); | |
- g_signal_connect(G_OBJECT(windata->pie_countdown), "draw", | |
- G_CALLBACK(on_countdown_draw), windata); | |
+ gtk_widget_set_size_request(windata->pie_countdown, PIE_WIDTH, PIE_HEIGHT); | |
+ g_signal_connect(G_OBJECT(windata->pie_countdown), "draw", G_CALLBACK(on_countdown_draw), windata); | |
} | |
} | |
@@ -1121,7 +1116,7 @@ add_button: | |
gtk_widget_show_all(windata->actions_box); | |
} | |
-void clear_notification_actions(GtkWindow* nw) | |
+void clear_notification_actions (GtkWindow* nw) | |
{ | |
WindowData* windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
@@ -1131,7 +1126,7 @@ void clear_notification_actions(GtkWindow* nw) | |
gtk_container_foreach(GTK_CONTAINER(windata->actions_box), (GtkCallback) gtk_widget_destroy, NULL); | |
} | |
-void move_notification(GtkWidget* nw, int x, int y) | |
+void move_notification (GtkWidget* nw, int x, int y) | |
{ | |
WindowData* windata = g_object_get_data(G_OBJECT(nw), "windata"); | |
@@ -1147,7 +1142,7 @@ void move_notification(GtkWidget* nw, int x, int y) | |
} | |
} | |
-void get_theme_info(char** theme_name, char** theme_ver, char** author, char** homepage) | |
+void get_theme_info (char** theme_name, char** theme_ver, char** author, char** homepage) | |
{ | |
*theme_name = g_strdup("Standard"); | |
@@ -1157,7 +1152,7 @@ void get_theme_info(char** theme_name, char** theme_ver, char** author, char** h | |
*homepage = g_strdup("http://www.galago-project.org/"); | |
} | |
-gboolean theme_check_init(unsigned int major_ver, unsigned int minor_ver, unsigned int micro_ver) | |
+gboolean theme_check_init (unsigned int major_ver, unsigned int minor_ver, unsigned int micro_ver) | |
{ | |
return major_ver == NOTIFICATION_DAEMON_MAJOR_VERSION && minor_ver == NOTIFICATION_DAEMON_MINOR_VERSION && micro_ver == NOTIFICATION_DAEMON_MICRO_VERSION; | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# GtkTreeView4: add classes (odd/even/sorted) to restore zebra striping | |
# https://github.com/GNOME/gtk/blob/4.12.3/gtk/deprecated/gtktreeview.c | |
Index: b/gtk/deprecated/gtktreeview.c | |
=================================================================== | |
--- a/gtk/deprecated/gtktreeview.c | |
+++ b/gtk/deprecated/gtktreeview.c | |
@@ -4609,6 +4609,18 @@ gtk_tree_view_bin_snapshot | |
gtk_style_context_add_class (context, "cell"); | |
+ if (list == first_column) | |
+ gtk_style_context_add_class (context, rtl ? "last" : "first"); | |
+ if (list == last_column) | |
+ gtk_style_context_add_class (context, rtl ? "first" : "last"); | |
+ if (gtk_tree_rbtree_node_get_index (tree, node) % 2 == 0) | |
+ gtk_style_context_add_class (context, "odd"); | |
+ else | |
+ gtk_style_context_add_class (context, "even"); | |
+ | |
+ if (flags & GTK_CELL_RENDERER_SORTED) | |
+ gtk_style_context_add_class (context, "sorted"); | |
+ | |
if (node == priv->cursor_node && has_can_focus_cell | |
&& ((column == priv->focus_column | |
&& priv->draw_keyfocus && |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
https://build.opensuse.org/package/show/home:luigifab/gtk3-classic & https://build.opensuse.org/package/show/home:luigifab/gtk4-classic
appearance__progress_text.gtk.3.patch : high cpu usage
appearance__progress_text.gtk.4.patch : some warnings (Gtk-CRITICAL gtk_widget_unparent: assertion GTK_IS_WIDGET (widget) failed) + no automatic min-width/height from text width/height
appearance__focus-visible.gtk4.patch : focus is not on the first toolbar button