utils: Use ISO weekday numbering for 'get_first_weekday' function
Change the 'get_first_weekday' function to number the weekdays Monday(1)-Sunday(7) like ISO does. Change the function name to reflect that. Add tests for different locales, although the tests depend on system-installed locales. Part-of: <https://gitlab.gnome.org/GNOME/gnome-calendar/-/merge_requests/822>
This commit is contained in:
@@ -116,7 +116,7 @@ set_week_start_day_from_variant (GcalContext *self,
|
|||||||
|
|
||||||
/* find the actual 'default' from locale */
|
/* find the actual 'default' from locale */
|
||||||
if (weekday->value == G_DESKTOP_WEEKDAY_DEFAULT)
|
if (weekday->value == G_DESKTOP_WEEKDAY_DEFAULT)
|
||||||
weekday = g_enum_get_value (g_type_class_get (G_DESKTOP_TYPE_WEEKDAY), gcal_util_get_first_weekday ());
|
weekday = g_enum_get_value (g_type_class_get (G_DESKTOP_TYPE_WEEKDAY), gcal_util_get_first_weekday_iso ());
|
||||||
|
|
||||||
if (self->week_start_day == weekday->value)
|
if (self->week_start_day == weekday->value)
|
||||||
return;
|
return;
|
||||||
@@ -391,7 +391,7 @@ gcal_context_class_init (GcalContextClass *klass)
|
|||||||
|
|
||||||
properties[PROP_WEEK_START_DAY] =
|
properties[PROP_WEEK_START_DAY] =
|
||||||
g_param_spec_enum ("week-start-day", NULL, NULL,
|
g_param_spec_enum ("week-start-day", NULL, NULL,
|
||||||
G_DESKTOP_TYPE_WEEKDAY, gcal_util_get_first_weekday (),
|
G_DESKTOP_TYPE_WEEKDAY, gcal_util_get_first_weekday_iso (),
|
||||||
G_PARAM_READABLE | G_PARAM_EXPLICIT_NOTIFY | G_PARAM_STATIC_STRINGS);
|
G_PARAM_READABLE | G_PARAM_EXPLICIT_NOTIFY | G_PARAM_STATIC_STRINGS);
|
||||||
|
|
||||||
g_object_class_install_properties (object_class, N_PROPS, properties);
|
g_object_class_install_properties (object_class, N_PROPS, properties);
|
||||||
@@ -535,7 +535,7 @@ gcal_context_get_time_format (GcalContext *self)
|
|||||||
GDesktopWeekday
|
GDesktopWeekday
|
||||||
gcal_context_get_week_start_day (GcalContext *self)
|
gcal_context_get_week_start_day (GcalContext *self)
|
||||||
{
|
{
|
||||||
g_return_val_if_fail (GCAL_IS_CONTEXT (self), gcal_util_get_first_weekday ());
|
g_return_val_if_fail (GCAL_IS_CONTEXT (self), gcal_util_get_first_weekday_iso ());
|
||||||
|
|
||||||
return self->week_start_day;
|
return self->week_start_day;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1083,7 +1083,7 @@ gcal_date_chooser_init (GcalDateChooser *self)
|
|||||||
self->date = g_date_time_new_now_local ();
|
self->date = g_date_time_new_now_local ();
|
||||||
g_date_time_get_ymd (self->date, &self->this_year, NULL, NULL);
|
g_date_time_get_ymd (self->date, &self->this_year, NULL, NULL);
|
||||||
|
|
||||||
self->week_start = gcal_util_get_first_weekday ();
|
self->week_start = gcal_util_get_first_weekday_iso ();
|
||||||
|
|
||||||
gtk_widget_init_template (GTK_WIDGET (self));
|
gtk_widget_init_template (GTK_WIDGET (self));
|
||||||
|
|
||||||
|
|||||||
@@ -194,7 +194,7 @@ allocate_overflow_popover (GcalMonthView *self,
|
|||||||
static inline void
|
static inline void
|
||||||
update_weekday_labels (GcalMonthView *self)
|
update_weekday_labels (GcalMonthView *self)
|
||||||
{
|
{
|
||||||
const gint first_weekday = gcal_util_get_first_weekday ();
|
const gint first_weekday = gcal_util_get_first_weekday_iso ();
|
||||||
|
|
||||||
for (gint i = 0; i < GCAL_N_WEEKDAYS; i++)
|
for (gint i = 0; i < GCAL_N_WEEKDAYS; i++)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -100,8 +100,6 @@ struct _GcalWeekHeader
|
|||||||
GtkWidget *overflow_label[GCAL_N_WEEKDAYS];
|
GtkWidget *overflow_label[GCAL_N_WEEKDAYS];
|
||||||
WeekdayHeader weekday_header[GCAL_N_WEEKDAYS];
|
WeekdayHeader weekday_header[GCAL_N_WEEKDAYS];
|
||||||
|
|
||||||
gint first_weekday;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Used for checking if the header is in collapsed state or expand state
|
* Used for checking if the header is in collapsed state or expand state
|
||||||
* false is collapse state true is expand state
|
* false is collapse state true is expand state
|
||||||
@@ -1762,8 +1760,6 @@ gcal_week_header_init (GcalWeekHeader *self)
|
|||||||
gtk_widget_set_visible (self->dnd.widget, FALSE);
|
gtk_widget_set_visible (self->dnd.widget, FALSE);
|
||||||
gtk_widget_set_parent (self->dnd.widget, GTK_WIDGET (self));
|
gtk_widget_set_parent (self->dnd.widget, GTK_WIDGET (self));
|
||||||
|
|
||||||
self->first_weekday = gcal_util_get_first_weekday ();
|
|
||||||
|
|
||||||
gtk_widget_init_template (GTK_WIDGET (self));
|
gtk_widget_init_template (GTK_WIDGET (self));
|
||||||
|
|
||||||
for (i = 0; i < GCAL_N_WEEKDAYS; i++)
|
for (i = 0; i < GCAL_N_WEEKDAYS; i++)
|
||||||
|
|||||||
@@ -83,7 +83,7 @@ gcal_date_time_get_start_of_week (GDateTime *date)
|
|||||||
|
|
||||||
g_assert (date != NULL);
|
g_assert (date != NULL);
|
||||||
|
|
||||||
first_weekday = gcal_util_get_first_weekday ();
|
first_weekday = gcal_util_get_first_weekday_iso ();
|
||||||
weekday = g_date_time_get_day_of_week (date) % GCAL_N_WEEKDAYS;
|
weekday = g_date_time_get_day_of_week (date) % GCAL_N_WEEKDAYS;
|
||||||
n_days_after_week_start = (GCAL_N_WEEKDAYS + weekday - first_weekday) % GCAL_N_WEEKDAYS;
|
n_days_after_week_start = (GCAL_N_WEEKDAYS + weekday - first_weekday) % GCAL_N_WEEKDAYS;
|
||||||
|
|
||||||
|
|||||||
+24
-14
@@ -213,36 +213,46 @@ gcal_util_get_desc_from_component (ECalComponent *component,
|
|||||||
/**
|
/**
|
||||||
* gcal_util_get_first_weekday:
|
* gcal_util_get_first_weekday:
|
||||||
*
|
*
|
||||||
* Copied from Clocks, which by itself is
|
* Finds the locale default first day of week
|
||||||
* copied from GtkCalendar.
|
* respecting the ISO day counting (Monday: 1 - Sunday: 7).
|
||||||
*
|
*
|
||||||
* Returns: the first weekday, from 0 to 6
|
* Prefer using `GcalContext:week-start-day` property or
|
||||||
|
* the `GcalContext:gcal_context_get_week_start_day()` method
|
||||||
|
* to get the current setting from gsettings-desktop-schemas.
|
||||||
|
* Use this utility method only as a fallback.
|
||||||
|
*
|
||||||
|
* Returns: the first weekday, from 1 to 7
|
||||||
*/
|
*/
|
||||||
gint
|
gint
|
||||||
gcal_util_get_first_weekday (void)
|
gcal_util_get_first_weekday_iso (void)
|
||||||
{
|
{
|
||||||
gint week_start;
|
gint week_start;
|
||||||
|
|
||||||
#ifdef HAVE__NL_TIME_FIRST_WEEKDAY
|
#ifdef HAVE__NL_TIME_FIRST_WEEKDAY
|
||||||
|
|
||||||
union { unsigned int word; char *string; } langinfo;
|
union { unsigned int baseline; char *offset; } langinfo;
|
||||||
gint week_1stday = 0;
|
gint iso_week_base = 7; /* default to Sunday (19971130) */
|
||||||
gint first_weekday = 1;
|
gint first_weekday = 1;
|
||||||
guint week_origin;
|
guint week_origin;
|
||||||
|
|
||||||
langinfo.string = nl_langinfo (_NL_TIME_FIRST_WEEKDAY);
|
/* first day of week index */
|
||||||
first_weekday = langinfo.string[0];
|
langinfo.offset = nl_langinfo (_NL_TIME_FIRST_WEEKDAY);
|
||||||
langinfo.string = nl_langinfo (_NL_TIME_WEEK_1STDAY);
|
first_weekday = langinfo.offset[0];
|
||||||
week_origin = langinfo.word;
|
|
||||||
|
/* find the baseline week origin */
|
||||||
|
langinfo.offset = nl_langinfo (_NL_TIME_WEEK_1STDAY);
|
||||||
|
week_origin = langinfo.baseline;
|
||||||
|
|
||||||
if (week_origin == 19971130) /* Sunday */
|
if (week_origin == 19971130) /* Sunday */
|
||||||
week_1stday = 0;
|
iso_week_base = 7;
|
||||||
else if (week_origin == 19971201) /* Monday */
|
else if (week_origin == 19971201) /* Monday */
|
||||||
week_1stday = 1;
|
iso_week_base = 1;
|
||||||
|
else if (week_origin == 19971129) /* unusual: Saturday */
|
||||||
|
iso_week_base = 6;
|
||||||
else
|
else
|
||||||
g_warning ("Unknown value of _NL_TIME_WEEK_1STDAY.\n");
|
g_warning ("Unknown value of _NL_TIME_WEEK_1STDAY.\n");
|
||||||
|
|
||||||
week_start = (week_1stday + first_weekday - 1) % GCAL_N_WEEKDAYS;
|
week_start = ((iso_week_base - 1 + (first_weekday - 1)) % GCAL_N_WEEKDAYS) + 1;
|
||||||
|
|
||||||
#else
|
#else
|
||||||
|
|
||||||
gchar *gtk_week_start;
|
gchar *gtk_week_start;
|
||||||
|
|||||||
@@ -63,7 +63,7 @@ GdkPaintable* gcal_util_get_circle_paintable_from_color (const GdkRGBA
|
|||||||
gchar* gcal_util_get_desc_from_component (ECalComponent *component,
|
gchar* gcal_util_get_desc_from_component (ECalComponent *component,
|
||||||
const gchar *joint_char);
|
const gchar *joint_char);
|
||||||
|
|
||||||
gint gcal_util_get_first_weekday (void);
|
gint gcal_util_get_first_weekday_iso (void);
|
||||||
|
|
||||||
ECalComponent* gcal_util_build_component_from_details (const gchar *summary,
|
ECalComponent* gcal_util_build_component_from_details (const gchar *summary,
|
||||||
GDateTime *initial_date,
|
GDateTime *initial_date,
|
||||||
|
|||||||
@@ -17,6 +17,7 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
#include <glib.h>
|
#include <glib.h>
|
||||||
|
#include <locale.h>
|
||||||
|
|
||||||
#include "gcal-utils.h"
|
#include "gcal-utils.h"
|
||||||
|
|
||||||
@@ -191,6 +192,47 @@ extract_meeting_url (void)
|
|||||||
|
|
||||||
/*********************************************************************************************************************/
|
/*********************************************************************************************************************/
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
const char *locale_name;
|
||||||
|
int week_start_index;
|
||||||
|
} LocaleIsoWeekDay;
|
||||||
|
|
||||||
|
static void
|
||||||
|
test_first_weekday (void)
|
||||||
|
{
|
||||||
|
LocaleIsoWeekDay test_cases[] = {
|
||||||
|
{ "C", 7 }, // Baseline standard (Sunday)
|
||||||
|
{ "en_US.UTF-8", 7 }, // US Standard (Sunday)
|
||||||
|
{ "de_DE.UTF-8", 1 }, // Euro Standard (Monday)
|
||||||
|
{ "en_GB.UTF-8", 1 }, // UK Standard (Monday)
|
||||||
|
{ "fa_IR.UTF-8", 6 } // Iran, Somalia, Afghanistan (Saturday)
|
||||||
|
};
|
||||||
|
|
||||||
|
const char* initial_locale = setlocale (LC_ALL, NULL);
|
||||||
|
|
||||||
|
for (size_t i = 0; i < G_N_ELEMENTS (test_cases); ++i)
|
||||||
|
{
|
||||||
|
LocaleIsoWeekDay testcase = test_cases[i];
|
||||||
|
char *current_locale = setlocale (LC_ALL, testcase.locale_name);
|
||||||
|
|
||||||
|
if (!current_locale)
|
||||||
|
{
|
||||||
|
g_message ("Locale %s not installed. Skipping", testcase.locale_name);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
g_message ("Testing locale %s", testcase.locale_name);
|
||||||
|
g_assert_cmpint (testcase.week_start_index, ==, gcal_util_get_first_weekday_iso ());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* restore locale */
|
||||||
|
setlocale (LC_ALL, initial_locale);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*********************************************************************************************************************/
|
||||||
|
|
||||||
gint
|
gint
|
||||||
main (gint argc,
|
main (gint argc,
|
||||||
gchar *argv[])
|
gchar *argv[])
|
||||||
@@ -202,6 +244,7 @@ main (gint argc,
|
|||||||
|
|
||||||
g_test_add_func ("/utils/date-time/date_time_from_icaltime", date_time_from_icaltime);
|
g_test_add_func ("/utils/date-time/date_time_from_icaltime", date_time_from_icaltime);
|
||||||
g_test_add_func ("/utils/misc/extract_meeting_url", extract_meeting_url);
|
g_test_add_func ("/utils/misc/extract_meeting_url", extract_meeting_url);
|
||||||
|
g_test_add_func ("/utils/misc/get_first_weekday", test_first_weekday);
|
||||||
|
|
||||||
return g_test_run ();
|
return g_test_run ();
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user