diff --git a/data/eu.polonkai.gergely.astrognome.gschema.xml b/data/eu.polonkai.gergely.astrognome.gschema.xml index b2b17a7..92ba0ed 100644 --- a/data/eu.polonkai.gergely.astrognome.gschema.xml +++ b/data/eu.polonkai.gergely.astrognome.gschema.xml @@ -22,6 +22,11 @@ The default house system The house system to use by default in new charts + + -1 + The ID of the default display theme to use + The database ID of the display theme to be used when a chart is created/opened. + @@ -44,11 +49,4 @@ The height of newly created windows. - - - false - Use the classical view - Use the classical view: planets only between Sun and Saturn, only Ptolemaic aspects, no antiscia. - - diff --git a/src/Makefile.am b/src/Makefile.am index 61e5bb9..e681b70 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -13,13 +13,14 @@ BUILT_SOURCES = \ $(NULL) astrognome_source_files = \ - ag-app.c \ - ag-window.c \ - ag-chart.c \ - ag-settings.c \ - ag-preferences.c \ - ag-db.c \ - astrognome.c \ + ag-app.c \ + ag-window.c \ + ag-chart.c \ + ag-settings.c \ + ag-preferences.c \ + ag-db.c \ + ag-display-theme.c \ + astrognome.c \ $(NULL) EXTRA_DIST = \ diff --git a/src/ag-app.c b/src/ag-app.c index 3ae09f9..9a2a5bc 100644 --- a/src/ag-app.c +++ b/src/ag-app.c @@ -8,11 +8,7 @@ #include "config.h" #include "astrognome.h" -typedef struct _AgAppPrivate { - WebKitUserContentManager *manager; -} AgAppPrivate; - -G_DEFINE_TYPE_WITH_PRIVATE(AgApp, ag_app, GTK_TYPE_APPLICATION); +G_DEFINE_TYPE(AgApp, ag_app, GTK_TYPE_APPLICATION); GtkWindow * ag_app_peek_first_window(AgApp *app) @@ -56,9 +52,8 @@ static GtkWidget * ag_app_create_window(AgApp *app) { GtkWidget *window; - AgAppPrivate *priv = ag_app_get_instance_private(app); - window = ag_window_new(app, priv->manager); + window = ag_window_new(app); gtk_application_add_window(GTK_APPLICATION(app), GTK_WINDOW(window)); gtk_widget_show_all(window); @@ -432,33 +427,6 @@ ag_app_new(void) static void ag_app_init(AgApp *app) { - AgAppPrivate *priv; - GBytes *css_data; - const gchar *css_source; - gsize css_length; - WebKitUserStyleSheet *stylesheet; - - priv = ag_app_get_instance_private(app); - priv->manager = webkit_user_content_manager_new(); - - css_data = g_resources_lookup_data( - "/eu/polonkai/gergely/Astrognome/ui/chart-default.css", - G_RESOURCE_LOOKUP_FLAGS_NONE, - NULL - ); - - if ((css_source = g_bytes_get_data(css_data, &css_length)) != NULL) { - stylesheet = webkit_user_style_sheet_new( - css_source, - WEBKIT_USER_CONTENT_INJECT_TOP_FRAME, - WEBKIT_USER_STYLE_LEVEL_USER, - NULL, NULL - ); - webkit_user_content_manager_add_style_sheet(priv->manager, stylesheet); - webkit_user_style_sheet_unref(stylesheet); - } - - g_bytes_unref(css_data); } static void diff --git a/src/ag-chart.c b/src/ag-chart.c index af7c1fd..2d73769 100644 --- a/src/ag-chart.c +++ b/src/ag-chart.c @@ -12,6 +12,7 @@ #include #include "config.h" +#include "astrognome.h" #include "ag-db.h" #include "ag-chart.h" #include "placidus.h" @@ -221,145 +222,18 @@ ag_chart_finalize(GObject *gobject) void ag_chart_add_planets(AgChart *chart) { + int i; AgChartPrivate *priv = ag_chart_get_instance_private(chart); - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_CHARIKLO, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_CHARIKLO) - ); + for (i = 0; i < used_planets_count; i++) { + gswe_moment_add_planet(GSWE_MOMENT(chart), used_planets[i], NULL); + priv->planet_list = g_list_prepend( + priv->planet_list, + GINT_TO_POINTER(used_planets[i]) + ); + } - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_VESTA, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_VESTA) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_JUNO, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_JUNO) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_PALLAS, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_PALLAS) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_CERES, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_CERES) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_NESSUS, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_NESSUS) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_PHOLUS, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_PHOLUS) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_CHIRON, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_CHIRON) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_MOON_APOGEE, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_MOON_APOGEE) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_MOON_NODE, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_MOON_NODE) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_PLUTO, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_PLUTO) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_NEPTUNE, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_NEPTUNE) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_URANUS, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_URANUS) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_SATURN, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_SATURN) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_JUPITER, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_JUPITER) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_MARS, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_MARS) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_VENUS, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_VENUS) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_MERCURY, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_MERCURY) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_MOON, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_MOON) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_SUN, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_SUN) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_VERTEX, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_VERTEX) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_ASCENDANT, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_ASCENDANT) - ); - - gswe_moment_add_planet(GSWE_MOMENT(chart), GSWE_PLANET_MC, NULL); - priv->planet_list = g_list_prepend( - priv->planet_list, - GINT_TO_POINTER(GSWE_PLANET_MC) - ); + priv->planet_list = g_list_reverse(priv->planet_list); } AgChart * @@ -1277,7 +1151,7 @@ AgChart *ag_chart_load_from_placidus_file(GFile *file, } AgChart * -ag_chart_new_from_db_save(AgDbSave *save_data, GError **err) +ag_chart_new_from_db_save(AgDbChartSave *save_data, GError **err) { GsweTimestamp *timestamp; gchar *house_system_enum_name; @@ -1675,7 +1549,7 @@ ag_chart_create_svg(AgChart *chart, gsize *length, GError **err) G_ENUM_CLASS(planets_class), gswe_planet_data_get_planet(planet_data) ); - xmlNewProp(node, BAD_CAST "name", BAD_CAST enum_value->value_name); + xmlNewProp(node, BAD_CAST "name", BAD_CAST enum_value->value_nick); value = g_malloc0(12); g_ascii_dtostr(value, 12, gswe_planet_data_get_position(planet_data)); @@ -1724,14 +1598,14 @@ ag_chart_create_svg(AgChart *chart, gsize *length, GError **err) G_ENUM_CLASS(planets_class), gswe_planet_data_get_planet(planet_data) ); - xmlNewProp(node, BAD_CAST "body1", BAD_CAST enum_value->value_name); + xmlNewProp(node, BAD_CAST "body1", BAD_CAST enum_value->value_nick); planet_data = gswe_aspect_data_get_planet2(aspect_data); enum_value = g_enum_get_value( G_ENUM_CLASS(planets_class), gswe_planet_data_get_planet(planet_data) ); - xmlNewProp(node, BAD_CAST "body2", BAD_CAST enum_value->value_name); + xmlNewProp(node, BAD_CAST "body2", BAD_CAST enum_value->value_nick); enum_value = g_enum_get_value( G_ENUM_CLASS(aspects_class), @@ -1769,20 +1643,20 @@ ag_chart_create_svg(AgChart *chart, gsize *length, GError **err) G_ENUM_CLASS(planets_class), gswe_planet_data_get_planet(planet_data) ); - xmlNewProp(node, BAD_CAST "body1", BAD_CAST enum_value->value_name); + xmlNewProp(node, BAD_CAST "body1", BAD_CAST enum_value->value_nick); planet_data = gswe_antiscion_data_get_planet2(antiscion_data); enum_value = g_enum_get_value( G_ENUM_CLASS(planets_class), gswe_planet_data_get_planet(planet_data) ); - xmlNewProp(node, BAD_CAST "body2", BAD_CAST enum_value->value_name); + xmlNewProp(node, BAD_CAST "body2", BAD_CAST enum_value->value_nick); enum_value = g_enum_get_value( G_ENUM_CLASS(antiscia_class), gswe_antiscion_data_get_axis(antiscion_data) ); - xmlNewProp(node, BAD_CAST "axis", BAD_CAST enum_value->value_name); + xmlNewProp(node, BAD_CAST "axis", BAD_CAST enum_value->value_nick); } g_type_class_unref(planets_class); @@ -1908,12 +1782,12 @@ ag_chart_get_note(AgChart *chart) return priv->note; } -AgDbSave * +AgDbChartSave * ag_chart_get_db_save(AgChart *chart, gint db_id) { GsweCoordinates *coords; AgChartPrivate *priv = ag_chart_get_instance_private(chart); - AgDbSave *save_data = g_new0(AgDbSave, 1); + AgDbChartSave *save_data = g_new0(AgDbChartSave, 1); GsweTimestamp *timestamp = gswe_moment_get_timestamp(GSWE_MOMENT(chart)); GEnumClass *house_system_class; GEnumValue *house_system_enum; diff --git a/src/ag-chart.h b/src/ag-chart.h index 08cc3dc..12e97ec 100644 --- a/src/ag-chart.h +++ b/src/ag-chart.h @@ -57,7 +57,7 @@ AgChart *ag_chart_load_from_agc(GFile *file, AgChart *ag_chart_load_from_placidus_file(GFile *file, GError **err); -AgChart *ag_chart_new_from_db_save(AgDbSave *save_data, GError **err); +AgChart *ag_chart_new_from_db_save(AgDbChartSave *save_data, GError **err); void ag_chart_save_to_file(AgChart *chart, GFile *file, @@ -92,7 +92,7 @@ void ag_chart_set_note(AgChart *chart, const gchar *note); const gchar *ag_chart_get_note(AgChart *chart); -AgDbSave *ag_chart_get_db_save(AgChart *chart, gint db_id); +AgDbChartSave *ag_chart_get_db_save(AgChart *chart, gint db_id); #define AG_CHART_ERROR (ag_chart_error_quark()) GQuark ag_chart_error_quark(void); diff --git a/src/ag-db.c b/src/ag-db.c index fb32e92..bb9fdca 100644 --- a/src/ag-db.c +++ b/src/ag-db.c @@ -22,50 +22,50 @@ G_DEFINE_QUARK(ag_db_error_quark, ag_db_error); G_DEFINE_TYPE_WITH_PRIVATE(AgDb, ag_db, G_TYPE_OBJECT); -typedef enum { - COLUMN_ID, - COLUMN_NAME, - COLUMN_COUNTRY, - COLUMN_CITY, - COLUMN_LONGITUDE, - COLUMN_LATITUDE, - COLUMN_ALTITUDE, - COLUMN_YEAR, - COLUMN_MONTH, - COLUMN_DAY, - COLUMN_HOUR, - COLUMN_MINUTE, - COLUMN_SECOND, - COLUMN_TIMEZONE, - COLUMN_HOUSE_SYSTEM, - COLUMN_NOTE, +enum { + COLUMN_CHART_ID, + COLUMN_CHART_NAME, + COLUMN_CHART_COUNTRY, + COLUMN_CHART_CITY, + COLUMN_CHART_LONGITUDE, + COLUMN_CHART_LATITUDE, + COLUMN_CHART_ALTITUDE, + COLUMN_CHART_YEAR, + COLUMN_CHART_MONTH, + COLUMN_CHART_DAY, + COLUMN_CHART_HOUR, + COLUMN_CHART_MINUTE, + COLUMN_CHART_SECOND, + COLUMN_CHART_TIMEZONE, + COLUMN_CHART_HOUSE_SYSTEM, + COLUMN_CHART_NOTE, /* Leave this as the last element */ - COLUMN_COUNT -} ChartTableColumn; + COLUMN_CHART_COUNT +}; typedef struct { - ChartTableColumn id; + int id; gchar *name; -} ChartTableColumnDef; +} TableColumnDef; -static ChartTableColumnDef chart_table_column[] = { - { COLUMN_ID, "id" }, - { COLUMN_NAME, "name" }, - { COLUMN_COUNTRY, "country_name" }, - { COLUMN_CITY, "city_name" }, - { COLUMN_LONGITUDE, "longitude" }, - { COLUMN_LATITUDE, "latitude" }, - { COLUMN_ALTITUDE, "altitude" }, - { COLUMN_YEAR, "year" }, - { COLUMN_MONTH, "month" }, - { COLUMN_DAY, "day" }, - { COLUMN_HOUR, "hour" }, - { COLUMN_MINUTE, "minute" }, - { COLUMN_SECOND, "second" }, - { COLUMN_TIMEZONE, "timezone" }, - { COLUMN_HOUSE_SYSTEM, "house_system" }, - { COLUMN_NOTE, "note" }, +static TableColumnDef chart_table_column[] = { + { COLUMN_CHART_ID, "id" }, + { COLUMN_CHART_NAME, "name" }, + { COLUMN_CHART_COUNTRY, "country_name" }, + { COLUMN_CHART_CITY, "city_name" }, + { COLUMN_CHART_LONGITUDE, "longitude" }, + { COLUMN_CHART_LATITUDE, "latitude" }, + { COLUMN_CHART_ALTITUDE, "altitude" }, + { COLUMN_CHART_YEAR, "year" }, + { COLUMN_CHART_MONTH, "month" }, + { COLUMN_CHART_DAY, "day" }, + { COLUMN_CHART_HOUR, "hour" }, + { COLUMN_CHART_MINUTE, "minute" }, + { COLUMN_CHART_SECOND, "second" }, + { COLUMN_CHART_TIMEZONE, "timezone" }, + { COLUMN_CHART_HOUSE_SYSTEM, "house_system" }, + { COLUMN_CHART_NOTE, "note" }, }; /** @@ -542,12 +542,12 @@ ag_db_get(void) /** * ag_db_save_data_free: - * @save_data: the #AgDbSave struct to free + * @save_data: the #AgDbChartSave struct to free * * Frees @save_data and all its fields */ void -ag_db_save_data_free(AgDbSave *save_data) +ag_db_chart_save_free(AgDbChartSave *save_data) { if (!save_data) { return; @@ -577,7 +577,7 @@ ag_db_save_data_free(AgDbSave *save_data) } /** - * ag_db_save_chart: + * ag_db_chart_save: * @db: the #AgDb object to operate on * @save_data: the data to save. * @err: a #GError for storing errors @@ -589,7 +589,7 @@ ag_db_save_data_free(AgDbSave *save_data) * Returns: TRUE if the save succeeds, FALSE otherwise */ gboolean -ag_db_save_chart(AgDb *db, AgDbSave *save_data, GError **err) +ag_db_chart_save(AgDb *db, AgDbChartSave *save_data, GError **err) { GError *local_err = NULL; gboolean save_success = TRUE; @@ -780,7 +780,7 @@ ag_db_save_chart(AgDb *db, AgDbSave *save_data, GError **err) } /** - * ag_db_get_chart_list: + * ag_db_chart_get_list: * @db: the #AgDb object to operate on * @err: a #GError * @@ -788,15 +788,15 @@ ag_db_save_chart(AgDb *db, AgDbSave *save_data, GError **err) * value may be NULL even if there are no charts or if there was an error, you * may want to check @err if the return value is NULL. * - * Please be aware that the #AgDbSave objects of the returned value are not + * Please be aware that the #AgDbChartSave objects of the returned value are not * fully realised chart records. To get one, you need to call - * ag_db_get_chart_data_by_id() + * ag_db_chart_get_data_by_id() * - * Returns: (element-type AgDbSave) (transfer full): the list of all charts, or - * or NULL if there are none, or if there is an error. + * Returns: (element-type AgDbChartSave) (transfer full): the list of all + * charts, or NULL if there are none, or if there is an error. */ GList * -ag_db_get_chart_list(AgDb *db, GError **err) +ag_db_chart_get_list(AgDb *db, GError **err) { GdaDataModelIter *iter; GList *ret = NULL; @@ -814,8 +814,8 @@ ag_db_get_chart_list(AgDb *db, GError **err) iter = gda_data_model_create_iter(result); while (gda_data_model_iter_move_next(iter)) { - const GValue *value; - AgDbSave *save_data = g_new0(AgDbSave, 1); + const GValue *value; + AgDbChartSave *save_data = g_new0(AgDbChartSave, 1); value = gda_data_model_iter_get_value_at(iter, 0); save_data->db_id = g_value_get_int(value); @@ -830,19 +830,19 @@ ag_db_get_chart_list(AgDb *db, GError **err) } /** - * ag_db_get_chart_data_by_id: + * ag_db_chart_get_data_by_id: * @db: the #AgDb object to operate on * @row_id: the ID field of the requested chart * @err: a #GError * * Fetches the specified row from the chart table. * - * Returns: (transfer full): A fully filled #AgDbSave record of the chart + * Returns: (transfer full): A fully filled #AgDbChartSave record of the chart */ -AgDbSave * -ag_db_get_chart_data_by_id(AgDb *db, guint row_id, GError **err) +AgDbChartSave * +ag_db_chart_get_data_by_id(AgDb *db, guint row_id, GError **err) { - AgDbSave *save_data; + AgDbChartSave *save_data; const GValue *value; gchar *query, *columns; @@ -852,7 +852,7 @@ ag_db_get_chart_data_by_id(AgDb *db, guint row_id, GError **err) columns = NULL; - for (i = 1; i < COLUMN_COUNT; i++) { + for (i = 1; i < COLUMN_CHART_COUNT; i++) { gchar *tmp; if (i == 1) { @@ -892,18 +892,28 @@ ag_db_get_chart_data_by_id(AgDb *db, guint row_id, GError **err) return NULL; } - save_data = g_new0(AgDbSave, 1); + save_data = g_new0(AgDbChartSave, 1); /* id */ - value = gda_data_model_get_value_at(result, COLUMN_ID, 0, NULL); + value = gda_data_model_get_value_at( + result, + COLUMN_CHART_ID, + 0, + NULL + ); save_data->db_id = g_value_get_int(value); /* name */ - value = gda_data_model_get_value_at(result, COLUMN_NAME, 0, NULL); + value = gda_data_model_get_value_at( + result, + COLUMN_CHART_NAME, + 0, + NULL + ); save_data->name = g_strdup(g_value_get_string(value)); /* country */ - value = gda_data_model_get_value_at(result, COLUMN_COUNTRY, 0, NULL); + value = gda_data_model_get_value_at(result, COLUMN_CHART_COUNTRY, 0, NULL); if (GDA_VALUE_HOLDS_NULL(value)) { save_data->country = NULL; @@ -911,7 +921,7 @@ ag_db_get_chart_data_by_id(AgDb *db, guint row_id, GError **err) save_data->country = g_strdup(g_value_get_string(value)); } - value = gda_data_model_get_value_at(result, COLUMN_CITY, 0, NULL); + value = gda_data_model_get_value_at(result, COLUMN_CHART_CITY, 0, NULL); if (GDA_VALUE_HOLDS_NULL(value)) { save_data->city = NULL; @@ -919,23 +929,23 @@ ag_db_get_chart_data_by_id(AgDb *db, guint row_id, GError **err) save_data->city = g_strdup(g_value_get_string(value)); } - value = gda_data_model_get_value_at( + value = gda_data_model_get_value_at( result, - COLUMN_LONGITUDE, + COLUMN_CHART_LONGITUDE, 0, NULL ); save_data->longitude = g_value_get_double(value); - value = gda_data_model_get_value_at( + value = gda_data_model_get_value_at( result, - COLUMN_LATITUDE, + COLUMN_CHART_LATITUDE, 0, NULL ); save_data->latitude = g_value_get_double(value); - value = gda_data_model_get_value_at(result, COLUMN_ALTITUDE, 0, NULL); + value = gda_data_model_get_value_at(result, COLUMN_CHART_ALTITUDE, 0, NULL); if (GDA_VALUE_HOLDS_NULL(value)) { save_data->altitude = DEFAULT_ALTITUDE; @@ -943,56 +953,61 @@ ag_db_get_chart_data_by_id(AgDb *db, guint row_id, GError **err) save_data->altitude = g_value_get_double(value); } - value = gda_data_model_get_value_at(result, COLUMN_YEAR, 0, NULL); + value = gda_data_model_get_value_at( + result, + COLUMN_CHART_YEAR, + 0, + NULL + ); save_data->year = g_value_get_int(value); - value = gda_data_model_get_value_at( + value = gda_data_model_get_value_at( result, - COLUMN_MONTH, + COLUMN_CHART_MONTH, 0, NULL ); save_data->month = g_value_get_uint(value); - value = gda_data_model_get_value_at(result, COLUMN_DAY, 0, NULL); + value = gda_data_model_get_value_at(result, COLUMN_CHART_DAY, 0, NULL); save_data->day = g_value_get_uint(value); - value = gda_data_model_get_value_at(result, COLUMN_HOUR, 0, NULL); + value = gda_data_model_get_value_at(result, COLUMN_CHART_HOUR, 0, NULL); save_data->hour = g_value_get_uint(value); - value = gda_data_model_get_value_at( + value = gda_data_model_get_value_at( result, - COLUMN_MINUTE, + COLUMN_CHART_MINUTE, 0, NULL ); save_data->minute = g_value_get_uint(value); - value = gda_data_model_get_value_at( + value = gda_data_model_get_value_at( result, - COLUMN_SECOND, + COLUMN_CHART_SECOND, 0, NULL ); save_data->second = g_value_get_uint(value); - value = gda_data_model_get_value_at( + value = gda_data_model_get_value_at( result, - COLUMN_TIMEZONE, + COLUMN_CHART_TIMEZONE, 0, NULL ); save_data->timezone = g_value_get_double(value); - value = gda_data_model_get_value_at( + value = gda_data_model_get_value_at( result, - COLUMN_HOUSE_SYSTEM, + COLUMN_CHART_HOUSE_SYSTEM, 0, NULL ); save_data->house_system = g_strdup(g_value_get_string(value)); - value = gda_data_model_get_value_at(result, COLUMN_NOTE, 0, NULL); + value = gda_data_model_get_value_at(result, COLUMN_CHART_NOTE, 0, NULL); if (GDA_VALUE_HOLDS_NULL(value)) { save_data->note = NULL; @@ -1038,17 +1053,19 @@ string_collate(const gchar *str1, const gchar *str2) } /** - * ag_db_save_identical: - * @a: the first #AgDbSave structure - * @b: the second #AgDbSave structure + * ag_db_chart_save_identical: + * @a: the first #AgDbChartSave structure + * @b: the second #AgDbChartSave structure * - * Compares two #AgDbSave structures and their contents. + * Compares two #AgDbChartSave structures and their contents. * * Returns: TRUE if the two structs hold equal values (strings are also compared * with string_collate()), FALSE otherwise */ gboolean -ag_db_save_identical(const AgDbSave *a, const AgDbSave *b, gboolean chart_only) +ag_db_chart_save_identical(const AgDbChartSave *a, + const AgDbChartSave *b, + gboolean chart_only) { if (a == b) { g_debug("identical: Equal"); @@ -1156,7 +1173,7 @@ ag_db_save_identical(const AgDbSave *a, const AgDbSave *b, gboolean chart_only) } gboolean -ag_db_delete_chart(AgDb *db, gint row_id, GError **err) +ag_db_chart_delete(AgDb *db, gint row_id, GError **err) { AgDbPrivate *priv = ag_db_get_instance_private(db); GValue id = G_VALUE_INIT; diff --git a/src/ag-db.h b/src/ag-db.h index de97188..575d0c9 100644 --- a/src/ag-db.h +++ b/src/ag-db.h @@ -30,7 +30,7 @@ struct _AgDbClass { GObjectClass parent_class; }; -typedef struct _AgDbSave { +typedef struct _AgDbChartSave { gint db_id; gchar *name; gchar *country; @@ -47,7 +47,7 @@ typedef struct _AgDbSave { gdouble timezone; gchar *house_system; gchar *note; -} AgDbSave; +} AgDbChartSave; typedef enum { AG_DB_ERROR_NO_CHART, @@ -58,21 +58,21 @@ GType ag_db_get_type(void) G_GNUC_CONST; AgDb *ag_db_get(void); -void ag_db_save_data_free(AgDbSave *save_data); +void ag_db_chart_save_free(AgDbChartSave *save_data); -gboolean ag_db_save_chart(AgDb *db, - AgDbSave *save_data, - GError **err); +gboolean ag_db_chart_save(AgDb *db, + AgDbChartSave *save_data, + GError **err); -GList *ag_db_get_chart_list(AgDb *db, GError **err); +GList *ag_db_chart_get_list(AgDb *db, GError **err); -AgDbSave *ag_db_get_chart_data_by_id(AgDb *db, guint row_id, GError **err); +AgDbChartSave *ag_db_chart_get_data_by_id(AgDb *db, guint row_id, GError **err); -gboolean ag_db_delete_chart(AgDb *db, gint row_id, GError **err); +gboolean ag_db_chart_delete(AgDb *db, gint row_id, GError **err); -gboolean ag_db_save_identical(const AgDbSave *a, - const AgDbSave *b, - gboolean chart_only); +gboolean ag_db_chart_save_identical(const AgDbChartSave *a, + const AgDbChartSave *b, + gboolean chart_only); #define AG_DB_ERROR (ag_db_error_quark()) GQuark ag_db_error_quark(void); diff --git a/src/ag-display-theme.c b/src/ag-display-theme.c new file mode 100644 index 0000000..ac65c6f --- /dev/null +++ b/src/ag-display-theme.c @@ -0,0 +1,276 @@ +#include +#include + +#include "astrognome.h" +#include "ag-display-theme.h" + +static gchar *planet_all = ".planet {\n" \ + " visibility: visible;\n" \ + "}\n"; + +static gchar *planet_none = ".planet {\n" \ + " visibility: hidden;\n" \ + " }\n"; + +static gchar *planet_tmpl = ".planet-%s {\n" \ + " visibility: %s !important;\n" \ + "}\n"; + +static gchar *aspect_all = ".aspect {\n" \ + " visibility: visible;\n" \ + "}\n"; + +static gchar *aspect_none = ".aspect {\n" \ + " visibility: hidden;\n" \ + " }\n"; + +static gchar *aspect_tmpl = ".aspect-%s {\n" \ + " visibility: %s !important;\n" \ + "}\n"; + +static gchar *antiscion_all = ".antiscion {\n" \ + " visibility: visible;\n" \ + "}\n"; + +static gchar *antiscion_none = ".antiscion {\n" \ + " visibility: hidden;\n" \ + "}\n"; + +static gchar *antiscion_tmpl = ".antiscion-%s {\n" \ + " visibility: %s !important;\n" \ + "}\n"; + +static AgDisplayTheme **builtin_themes = NULL; +static gchar *builtin_theme_name[AG_DISPLAY_THEME_COUNT] = { + NC_("Display theme name", "Everything"), + NC_("Display theme name", "Classic"), +}; + +gchar * +ag_display_theme_to_css(AgDisplayTheme *theme) +{ + GList *i; + gchar *ret; + GString *css = NULL; + + if (theme->planets_include) { + css = g_string_new(planet_none); + } else { + css = g_string_new(planet_all); + } + + for (i = theme->planets; i; i = g_list_next(i)) { + const gchar *planet_name; + + planet_name = ag_planet_id_to_nick(GPOINTER_TO_INT(i->data)); + + g_string_append_printf( + css, + planet_tmpl, + planet_name, + (theme->planets_include) ? "visible" : "hidden" + ); + } + + if (theme->aspects_include) { + g_string_append(css, aspect_none); + } else { + g_string_append(css, aspect_all); + } + + for (i = theme->aspects; i; i = g_list_next(i)) { + const gchar *aspect_name; + + aspect_name = ag_aspect_id_to_nick(GPOINTER_TO_INT(i->data)); + + g_string_append_printf( + css, + aspect_tmpl, + aspect_name, + (theme->aspects_include) ? "visible" : "hidden" + ); + } + + if (theme->antiscia_include) { + g_string_append(css, antiscion_none); + } else { + g_string_append(css, antiscion_all); + } + + for (i = theme->antiscia; i; i = g_list_next(i)) { + const gchar *antiscion_axis_name; + + antiscion_axis_name = ag_antiscion_axis_id_to_nick( + GPOINTER_TO_INT(i->data) + ); + + g_string_append_printf( + css, + antiscion_tmpl, + antiscion_axis_name, + (theme->antiscia_include) ? "visible" : "hidden" + ); + } + + ret = g_string_free(css, FALSE); + + g_debug("%s", ret); + + return ret; +} + +static AgDisplayTheme * +ag_display_theme_get_builtin(gint id) +{ + AgDisplayTheme *theme; + + // Builtin themes all have a negative ID + g_return_val_if_fail(id < 0, NULL); + // And must be greater then AG_DISPLAY_THEME_COUNT + g_return_val_if_fail(id >= -AG_DISPLAY_THEME_COUNT, NULL); + + if (builtin_themes == NULL) { + builtin_themes = g_new0(AgDisplayTheme *, AG_DISPLAY_THEME_COUNT); + } + + // If the theme is already created, return it + if (builtin_themes[-id] != NULL) { + return builtin_themes[-id]; + } + + theme = builtin_themes[-id] = g_new0(AgDisplayTheme, 1); + + switch (id) { + case AG_DISPLAY_THEME_ALL: + theme->id = id; + theme->name = gettext(builtin_theme_name[-id - 1]); + theme->builtin = TRUE; + theme->planets_include = FALSE; + theme->planets = NULL; + theme->aspects_include = FALSE; + theme->aspects = NULL; + theme->antiscia_include = FALSE; + theme->antiscia = NULL; + + break; + + case AG_DISPLAY_THEME_CLASSIC: + // TODO: If SWE-GLib would support it, we could programatically get + // classic planets and aspects here, thus, if it is messed up, + // we need to fix it only once. + theme->id = id; + theme->name = gettext(builtin_theme_name[-id - 1]); + theme->builtin = TRUE; + theme->planets_include = TRUE; + theme->planets = NULL; + theme->aspects_include = TRUE; + theme->aspects = NULL; + theme->antiscia_include = TRUE; + theme->antiscia = NULL; + + theme->planets = g_list_prepend( + theme->planets, + GINT_TO_POINTER(GSWE_PLANET_SUN) + ); + theme->planets = g_list_prepend( + theme->planets, + GINT_TO_POINTER(GSWE_PLANET_MOON) + ); + theme->planets = g_list_prepend( + theme->planets, + GINT_TO_POINTER(GSWE_PLANET_MERCURY) + ); + theme->planets = g_list_prepend( + theme->planets, + GINT_TO_POINTER(GSWE_PLANET_VENUS) + ); + theme->planets = g_list_prepend( + theme->planets, + GINT_TO_POINTER(GSWE_PLANET_MARS) + ); + theme->planets = g_list_prepend( + theme->planets, + GINT_TO_POINTER(GSWE_PLANET_JUPITER) + ); + theme->planets = g_list_prepend( + theme->planets, + GINT_TO_POINTER(GSWE_PLANET_SATURN) + ); + theme->planets = g_list_prepend( + theme->planets, + GINT_TO_POINTER(GSWE_PLANET_MOON_NODE) + ); + + theme->aspects = g_list_prepend( + theme->aspects, + GINT_TO_POINTER(GSWE_ASPECT_CONJUCTION) + ); + theme->aspects = g_list_prepend( + theme->aspects, + GINT_TO_POINTER(GSWE_ASPECT_OPPOSITION) + ); + theme->aspects = g_list_prepend( + theme->aspects, + GINT_TO_POINTER(GSWE_ASPECT_TRINE) + ); + theme->aspects = g_list_prepend( + theme->aspects, + GINT_TO_POINTER(GSWE_ASPECT_SQUARE) + ); + theme->aspects = g_list_prepend( + theme->aspects, + GINT_TO_POINTER(GSWE_ASPECT_SEXTILE) + ); + + break; + + default: + g_free(theme); + g_warning("Trying to instantiate unknown builtin theme %d", id); + return NULL; + } + + return theme; +} + +GList * +ag_display_theme_get_list(void) +{ + int i; + GList *ret = NULL; + + for (i = 1; i <= AG_DISPLAY_THEME_COUNT; i++) { + AgDisplayTheme *theme = ag_display_theme_get_builtin(-i); + + ret = g_list_append(ret, theme); + } + + return ret; +} + +AgDisplayTheme * +ag_display_theme_get_by_id(int id) +{ + if (id < 0) { + return ag_display_theme_get_builtin(id); + } + + g_warning("Invalid theme ID. Falling back to display everything."); + + return ag_display_theme_get_builtin(AG_DISPLAY_THEME_ALL); +} + +void +ag_display_theme_free(AgDisplayTheme *display_theme) +{ + if (!display_theme || display_theme->builtin) + { + return; + } + + g_free(display_theme->name); + g_list_free(display_theme->planets); + g_list_free(display_theme->aspects); + g_list_free(display_theme->antiscia); + g_free(display_theme); +} diff --git a/src/ag-display-theme.h b/src/ag-display-theme.h new file mode 100644 index 0000000..801384c --- /dev/null +++ b/src/ag-display-theme.h @@ -0,0 +1,33 @@ +#ifndef __AG_DISPLAY_THEME_H__ +#define __AG_DISPLAY_THEME_H__ + +#include + +typedef struct _AgDisplayTheme { + gint id; + gchar *name; + gboolean builtin; + gboolean planets_include; + GList *planets; + gboolean aspects_include; + GList *aspects; + gboolean antiscia_include; + GList *antiscia; +} AgDisplayTheme; + +enum { + AG_DISPLAY_THEME_ALL = -1, + AG_DISPLAY_THEME_CLASSIC = -2, + AG_DISPLAY_THEME_PREV, + AG_DISPLAY_THEME_COUNT = - AG_DISPLAY_THEME_PREV + 1 +}; + +gchar *ag_display_theme_to_css(AgDisplayTheme *display_theme); + +AgDisplayTheme *ag_display_theme_get_by_id(int id); + +GList *ag_display_theme_get_list(void); + +void ag_display_theme_free(AgDisplayTheme *display_theme); + +#endif /* __AG_DISPLAY_THEME_H__ */ diff --git a/src/ag-preferences.c b/src/ag-preferences.c index aaffa8b..9a7008b 100644 --- a/src/ag-preferences.c +++ b/src/ag-preferences.c @@ -1,8 +1,10 @@ #include #include +#include #include "ag-settings.h" #include "ag-preferences.h" +#include "ag-display-theme.h" static GtkWidget *prefs_dialog = NULL; @@ -12,6 +14,8 @@ typedef struct _AgPreferencesPrivate { GtkCheckButton *aspect_chars; GtkWidget *house_system; GtkListStore *house_system_model; + GtkWidget *display_theme; + GtkListStore *display_theme_model; AgSettings *settings; } AgPreferencesPrivate; @@ -75,6 +79,16 @@ ag_preferences_class_init(AgPreferencesClass *klass) AgPreferences, house_system_model ); + gtk_widget_class_bind_template_child_private( + widget_class, + AgPreferences, + display_theme + ); + gtk_widget_class_bind_template_child_private( + widget_class, + AgPreferences, + display_theme_model + ); } static void @@ -98,14 +112,68 @@ ag_preferences_add_house_system(GsweHouseSystemInfo *house_system_info, ); } +static void +ag_preferences_add_display_theme(AgDisplayTheme *display_theme, + AgPreferencesPrivate *priv) +{ + GtkTreeIter iter; + gchar *id_string = g_strdup_printf("%d", display_theme->id); + + g_debug("Adding theme with ID %d ('%s')", display_theme->id, id_string); + + gtk_list_store_append(priv->display_theme_model, &iter); + gtk_list_store_set( + priv->display_theme_model, &iter, + 0, id_string, + 1, display_theme->name, + -1 + ); + g_free(id_string); +} + +static gboolean +ag_preferences_display_theme_get(GValue *value, + GVariant *variant, + gpointer user_data) +{ + gint32 id = g_variant_get_int32(variant); + gchar *id_string = g_strdup_printf("%d", id); + + g_debug("Converted %d to '%s'", id, id_string); + + g_value_take_string(value, id_string); + + return TRUE; +} + +static GVariant * +ag_preferences_display_theme_set(const GValue *value, + const GVariantType *expected_type, + gpointer user_data) +{ + const gchar *id_string; + gint32 id; + GVariant *variant; + + id_string = g_value_get_string(value); + id = atoi(id_string); + + g_debug("Converted '%s' to %d", id_string, id); + + variant = g_variant_new_int32(id); + + return variant; +} + static void ag_preferences_init(AgPreferences *prefs) { GSettings *settings_window, *settings_main; - GList *house_system_list = gswe_all_house_systems(); - AgPreferencesPrivate *priv = ag_preferences_get_instance_private(prefs); GtkCellRenderer *cell_renderer; + GList *house_system_list = gswe_all_house_systems(), + *display_theme_list = ag_display_theme_get_list(); + AgPreferencesPrivate *priv = ag_preferences_get_instance_private(prefs); gtk_widget_init_template(GTK_WIDGET(prefs)); priv->settings = ag_settings_get(); @@ -127,6 +195,24 @@ ag_preferences_init(AgPreferences *prefs) NULL ); + g_list_foreach( + display_theme_list, + (GFunc)ag_preferences_add_display_theme, + priv + ); + cell_renderer = gtk_cell_renderer_text_new(); + gtk_cell_layout_pack_start( + GTK_CELL_LAYOUT(priv->display_theme), + cell_renderer, + TRUE + ); + gtk_cell_layout_set_attributes( + GTK_CELL_LAYOUT(priv->display_theme), + cell_renderer, + "text", 1, + NULL + ); + settings_window = ag_settings_peek_window_settings(priv->settings); g_settings_bind( settings_window, @@ -158,6 +244,17 @@ ag_preferences_init(AgPreferences *prefs) "active-id", G_SETTINGS_BIND_DEFAULT ); + g_settings_bind_with_mapping( + settings_main, + "default-display-theme", + priv->display_theme, + "active-id", + G_SETTINGS_BIND_DEFAULT, + ag_preferences_display_theme_get, + ag_preferences_display_theme_set, + NULL, + NULL + ); } void diff --git a/src/ag-settings.c b/src/ag-settings.c index f38e2ac..ddb560c 100644 --- a/src/ag-settings.c +++ b/src/ag-settings.c @@ -2,15 +2,13 @@ #define SETTINGS_SCHEMA_ID_MAIN "eu.polonkai.gergely.Astrognome" #define SETTINGS_SCHEMA_ID_WINDOW "eu.polonkai.gergely.Astrognome.state.window" -#define SETTINGS_SCHEMA_ID_CHART "eu.polonkai.gergely.Astrognome.state.chart" static AgSettings *singleton = NULL; -struct _AgSettingsPrivate { +typedef struct _AgSettingsPrivate { GSettings *settings_main; GSettings *settings_window; - GSettings *settings_chart; -}; +} AgSettingsPrivate; G_DEFINE_TYPE_WITH_PRIVATE(AgSettings, ag_settings, G_TYPE_OBJECT); @@ -21,7 +19,6 @@ ag_settings_init(AgSettings *settings) priv->settings_main = g_settings_new(SETTINGS_SCHEMA_ID_MAIN); priv->settings_window = g_settings_new(SETTINGS_SCHEMA_ID_WINDOW); - priv->settings_chart = g_settings_new(SETTINGS_SCHEMA_ID_CHART); } static void @@ -32,7 +29,6 @@ ag_settings_dispose(GObject *object) ); g_clear_object(&priv->settings_window); - g_clear_object(&priv->settings_chart); g_clear_object(&priv->settings_main); G_OBJECT_CLASS(ag_settings_parent_class)->dispose(object); @@ -84,11 +80,3 @@ ag_settings_peek_window_settings(AgSettings *settings) return priv->settings_window; } - -GSettings * -ag_settings_peek_chart_settings(AgSettings *settings) -{ - AgSettingsPrivate *priv = ag_settings_get_instance_private(settings); - - return priv->settings_chart; -} diff --git a/src/ag-settings.h b/src/ag-settings.h index 5fe469e..6ce0ae9 100644 --- a/src/ag-settings.h +++ b/src/ag-settings.h @@ -23,7 +23,6 @@ G_BEGIN_DECLS typedef struct _AgSettings AgSettings; typedef struct _AgSettingsClass AgSettingsClass; -typedef struct _AgSettingsPrivate AgSettingsPrivate; struct _AgSettings { GObject parent_instance; @@ -39,7 +38,6 @@ AgSettings *ag_settings_get(void); GSettings *ag_settings_peek_main_settings(AgSettings *settings); GSettings *ag_settings_peek_window_settings(AgSettings *settings); -GSettings *ag_settings_peek_chart_settings(AgSettings *settings); G_END_DECLS diff --git a/src/ag-window.c b/src/ag-window.c index 494fbb3..5be051f 100644 --- a/src/ag-window.c +++ b/src/ag-window.c @@ -16,6 +16,7 @@ #include "ag-chart.h" #include "ag-settings.h" #include "ag-db.h" +#include "ag-display-theme.h" struct _AgWindowPrivate { GtkWidget *header_bar; @@ -40,6 +41,7 @@ struct _AgWindowPrivate { GtkWidget *second; GtkWidget *timezone; GtkWidget *house_system; + GtkWidget *display_theme; GtkWidget *tab_list; GtkWidget *tab_chart; @@ -57,11 +59,14 @@ struct _AgWindowPrivate { GtkTextBuffer *note_buffer; GtkListStore *house_system_model; GtkListStore *db_chart_data; - AgDbSave *saved_data; + AgDbChartSave *saved_data; GtkEntryCompletion *country_comp; GtkEntryCompletion *city_comp; gchar *selected_country; gchar *selected_city; + GList *style_sheets; + AgDisplayTheme *theme; + GtkListStore *display_theme_model; }; struct cc_search { @@ -643,7 +648,7 @@ ag_window_chart_changed(AgChart *chart, AgWindow *window) static void ag_window_recalculate_chart(AgWindow *window, gboolean set_everything) { - AgDbSave *edit_data, + AgDbChartSave *edit_data, *chart_data; AgWindowPrivate *priv = ag_window_get_instance_private(window); gboolean south, @@ -673,7 +678,7 @@ ag_window_recalculate_chart(AgWindow *window, gboolean set_everything) gtk_spin_button_update(GTK_SPIN_BUTTON(current)); } - edit_data = g_new0(AgDbSave, 1); + edit_data = g_new0(AgDbChartSave, 1); edit_data->db_id = db_id; @@ -748,16 +753,16 @@ ag_window_recalculate_chart(AgWindow *window, gboolean set_everything) : NULL ; - if (ag_db_save_identical(edit_data, chart_data, !set_everything)) { + if (ag_db_chart_save_identical(edit_data, chart_data, !set_everything)) { g_debug("No redrawing needed"); - ag_db_save_data_free(edit_data); - ag_db_save_data_free(chart_data); + ag_db_chart_save_free(edit_data); + ag_db_chart_save_free(chart_data); return; } - ag_db_save_data_free(chart_data); + ag_db_chart_save_free(chart_data); g_debug("Recalculating chart data"); @@ -799,7 +804,7 @@ ag_window_recalculate_chart(AgWindow *window, gboolean set_everything) ag_chart_set_note(priv->chart, edit_data->note); } - ag_db_save_data_free(edit_data); + ag_db_chart_save_free(edit_data); } static void @@ -989,7 +994,7 @@ ag_window_can_close(AgWindow *window, gboolean display_dialog) gint db_id = (priv->saved_data) ? priv->saved_data->db_id : -1; - AgDbSave *save_data = NULL; + AgDbChartSave *save_data = NULL; AgDb *db = ag_db_get(); GError *err = NULL; gboolean ret = TRUE; @@ -999,7 +1004,7 @@ ag_window_can_close(AgWindow *window, gboolean display_dialog) save_data = ag_chart_get_db_save(priv->chart, db_id); if ( - !ag_db_save_identical(priv->saved_data, save_data, FALSE) + !ag_db_chart_save_identical(priv->saved_data, save_data, FALSE) || !(priv->saved_data) || (priv->saved_data->db_id == -1) ) { @@ -1020,7 +1025,7 @@ ag_window_can_close(AgWindow *window, gboolean display_dialog) switch (response) { case GTK_RESPONSE_YES: - if (!ag_db_save_chart(db, save_data, &err)) { + if (!ag_db_chart_save(db, save_data, &err)) { ag_app_message_dialog( GTK_WINDOW(window), GTK_MESSAGE_ERROR, @@ -1051,7 +1056,7 @@ ag_window_can_close(AgWindow *window, gboolean display_dialog) } } - ag_db_save_data_free(save_data); + ag_db_chart_save_free(save_data); return ret; } @@ -1066,7 +1071,7 @@ ag_window_save_action(GSimpleAction *action, AgDb *db = ag_db_get(); GError *err = NULL; gint old_id; - AgDbSave *save_data; + AgDbChartSave *save_data; ag_window_recalculate_chart(window, TRUE); @@ -1074,7 +1079,7 @@ ag_window_save_action(GSimpleAction *action, old_id = (priv->saved_data) ? priv->saved_data->db_id : -1; save_data = ag_chart_get_db_save(priv->chart, old_id); - if (!ag_db_save_chart(db, save_data, &err)) { + if (!ag_db_chart_save(db, save_data, &err)) { ag_app_message_dialog( GTK_WINDOW(window), GTK_MESSAGE_ERROR, @@ -1083,7 +1088,7 @@ ag_window_save_action(GSimpleAction *action, ); } - ag_db_save_data_free(priv->saved_data); + ag_db_chart_save_free(priv->saved_data); priv->saved_data = save_data; } } @@ -1108,6 +1113,130 @@ ag_window_delete_event_callback(AgWindow *window, return (!ag_window_can_close(window, TRUE)); } +static void +ag_window_clear_style_sheets(AgWindow *window) +{ + WebKitUserContentManager *manager; + AgWindowPrivate *priv = ag_window_get_instance_private(window); + + g_debug("Clearing style sheets"); + + manager = webkit_web_view_get_user_content_manager( + WEBKIT_WEB_VIEW(priv->chart_web_view) + ); + + webkit_user_content_manager_remove_all_style_sheets(manager); + g_list_free_full( + priv->style_sheets, + (GDestroyNotify)webkit_user_style_sheet_unref + ); + priv->style_sheets = NULL; +} + +static void +ag_window_add_style_sheet(AgWindow *window, const gchar *path) +{ + gchar *css_source; + gboolean source_free = FALSE; + AgWindowPrivate *priv = ag_window_get_instance_private(window); + + if (strncmp("gres://", path, 7) == 0) { + gchar *res_path = g_strdup_printf( + "/eu/polonkai/gergely/Astrognome/%s", + path + 7 + ); + GBytes *css_data = g_resources_lookup_data( + res_path, + G_RESOURCE_LOOKUP_FLAGS_NONE, + NULL + ); + + css_source = g_strdup(g_bytes_get_data(css_data, NULL)); + source_free = TRUE; + g_bytes_unref(css_data); + } else if (strncmp("raw:", path, 4) == 0) { + css_source = (gchar *)path + 4; + } else { + GFile *css_file = g_file_new_for_uri(path); + GError *err = NULL; + + g_file_load_contents( + css_file, + NULL, + &css_source, NULL, + NULL, + &err + ); + source_free = TRUE; + g_object_unref(css_file); + } + + if (css_source) { + WebKitUserStyleSheet *style_sheet = webkit_user_style_sheet_new( + css_source, + WEBKIT_USER_CONTENT_INJECT_TOP_FRAME, + WEBKIT_USER_STYLE_LEVEL_USER, + NULL, NULL + ); + + priv->style_sheets = g_list_append(priv->style_sheets, style_sheet); + + if (source_free) { + g_free(css_source); + } + } +} + +static void +ag_window_update_style_sheets(AgWindow *window) +{ + GList *item; + WebKitUserContentManager *manager; + AgWindowPrivate *priv = ag_window_get_instance_private(window); + + g_debug("Updating style sheets"); + + manager = webkit_web_view_get_user_content_manager( + WEBKIT_WEB_VIEW(priv->chart_web_view) + ); + + webkit_user_content_manager_remove_all_style_sheets(manager); + + for (item = priv->style_sheets; item; item = g_list_next(item)) { + WebKitUserStyleSheet *style_sheet = item->data; + + webkit_user_content_manager_add_style_sheet(manager, style_sheet); + } +} + +static void +ag_window_set_theme(AgWindow *window, AgDisplayTheme *theme) +{ + gchar *css, + *css_final; + + g_debug("Setting theme to %s", (theme) ? theme->name : "no theme"); + ag_window_clear_style_sheets(window); + + // Add the default style sheet + ag_window_add_style_sheet( + window, + "gres://ui/chart-default.css" + ); + + if (theme) { + css = ag_display_theme_to_css(theme); + css_final = g_strdup_printf("raw:%s", css); + g_free(css); + + ag_window_add_style_sheet(window, css_final); + + g_free(css_final); + } + + ag_window_update_style_sheets(window); +} + static void ag_window_tab_changed_cb(GtkStack *stack, GParamSpec *pspec, AgWindow *window) { @@ -1125,6 +1254,23 @@ ag_window_tab_changed_cb(GtkStack *stack, GParamSpec *pspec, AgWindow *window) if (strcmp("chart", active_tab_name) == 0) { gtk_widget_set_size_request(active_tab, 600, 600); + if (priv->theme == NULL) { + AgSettings *settings; + GSettings *main_settings; + gint default_theme; + + settings = ag_settings_get(); + main_settings = ag_settings_peek_main_settings(settings); + default_theme = g_settings_get_int( + main_settings, + "default-display-theme" + ); + g_object_unref(settings); + + priv->theme = ag_display_theme_get_by_id(default_theme); + + ag_window_set_theme(window, priv->theme); + } } if (strcmp("list", active_tab_name) == 0) { @@ -1203,6 +1349,37 @@ ag_window_set_default_house_system(GtkTreeModel *model, return FALSE; } +static gboolean +ag_window_set_default_display_theme(GtkTreeModel *model, + GtkTreePath *path, + GtkTreeIter *iter, + AgWindow *window) +{ + gint row_display_theme; + AgWindowPrivate *priv = ag_window_get_instance_private(window); + AgSettings *settings = ag_settings_get(); + GSettings *main_settings = ag_settings_peek_main_settings(settings); + gint default_theme = g_settings_get_int( + main_settings, + "default-display-theme" + ); + + g_clear_object(&settings); + gtk_tree_model_get( + model, iter, + 0, &row_display_theme, + -1 + ); + + if (default_theme == row_display_theme) { + gtk_combo_box_set_active_iter(GTK_COMBO_BOX(priv->display_theme), iter); + + return TRUE; + } + + return FALSE; +} + static void ag_window_new_chart_action(GSimpleAction *action, GVariant *parameter, @@ -1262,7 +1439,7 @@ ag_window_back_action(GSimpleAction *action, if (ag_window_can_close(window, TRUE)) { g_clear_object(&(priv->chart)); - ag_db_save_data_free(priv->saved_data); + ag_db_chart_save_free(priv->saved_data); priv->saved_data = NULL; ag_window_load_chart_list(window); @@ -1355,7 +1532,7 @@ ag_window_delete_action(GSimpleAction *action, id = atoi(id_str); g_free(id_str); - if (!ag_db_delete_chart(db, id, &err)) { + if (!ag_db_chart_delete(db, id, &err)) { ag_app_message_dialog( GTK_WINDOW(window), GTK_MESSAGE_ERROR, @@ -1399,8 +1576,8 @@ ag_window_connection_action(GSimpleAction *action, ); static gchar *js = "aspects = document.getElementById('aspects');\n" \ "antiscia = document.getElementById('antiscia');\n" \ - "aspects.setAttribute('visibility', '%s');\n" \ - "antiscia.setAttribute('visibility', '%s');\n"; + "aspects.setAttribute('display', '%s');\n" \ + "antiscia.setAttribute('display', '%s');\n"; current_state = g_action_get_state(G_ACTION(action)); @@ -1414,10 +1591,10 @@ ag_window_connection_action(GSimpleAction *action, if (strcmp("aspects", state) == 0) { g_debug("Switching to aspects"); - js_code = g_strdup_printf(js, "visible", "hidden"); + js_code = g_strdup_printf(js, "block", "none"); } else if (strcmp("antiscia", state) == 0) { g_debug("Switching to antiscia"); - js_code = g_strdup_printf(js, "hidden", "visible"); + js_code = g_strdup_printf(js, "none", "block"); } else { g_warning("Connection type '%s' is invalid", state); } @@ -1480,6 +1657,21 @@ ag_window_add_house_system(GsweHouseSystemInfo *house_system_info, ); } +static void +ag_window_add_display_theme(AgDisplayTheme *display_theme, + AgWindowPrivate *priv) +{ + GtkTreeIter iter; + + gtk_list_store_append(priv->display_theme_model, &iter); + gtk_list_store_set( + priv->display_theme_model, &iter, + 0, display_theme->id, + 1, display_theme->name, + -1 + ); +} + static void ag_window_list_item_activated_cb(GdMainView *view, const gchar *id, @@ -1507,7 +1699,7 @@ ag_window_list_item_activated_cb(GdMainView *view, g_debug("Loading chart with ID %d", row_id); - if ((priv->saved_data = ag_db_get_chart_data_by_id( + if ((priv->saved_data = ag_db_chart_get_data_by_id( db, row_id, &err)) == NULL) { @@ -1534,7 +1726,7 @@ ag_window_list_item_activated_cb(GdMainView *view, "Error: %s", err->message ); - ag_db_save_data_free(priv->saved_data); + ag_db_chart_save_free(priv->saved_data); priv->saved_data = NULL; return; @@ -1612,17 +1804,46 @@ ag_window_city_matches(GtkEntryCompletion *city_comp, return ret; } +gboolean +ag_window_chart_context_cb(WebKitWebView *web_view, + GtkWidget *default_menu, + WebKitHitTestResult *hit_test_result, + gboolean triggered_with_keyboard, + gpointer user_data) +{ + return TRUE; +} + static void ag_window_init(AgWindow *window) { - GtkAccelGroup *accel_group; - GSettings *main_settings; - GList *house_system_list; - GtkCellRenderer *house_system_renderer; - AgWindowPrivate *priv = ag_window_get_instance_private(window); + GtkAccelGroup *accel_group; + GSettings *main_settings; + GList *house_system_list, + *display_theme_list; + GtkCellRenderer *house_system_renderer, + *display_theme_renderer; + WebKitUserContentManager *manager = webkit_user_content_manager_new(); + AgWindowPrivate *priv = ag_window_get_instance_private(window); gtk_widget_init_template(GTK_WIDGET(window)); + priv->chart_web_view = webkit_web_view_new_with_user_content_manager( + manager + ); + gtk_box_pack_end( + GTK_BOX(priv->tab_chart), + priv->chart_web_view, + TRUE, TRUE, 0 + ); + + g_signal_connect( + priv->chart_web_view, + "context-menu", + G_CALLBACK(ag_window_chart_context_cb), + NULL + ); + priv->settings = ag_settings_get(); main_settings = ag_settings_peek_main_settings(priv->settings); @@ -1678,6 +1899,32 @@ ag_window_init(AgWindow *window) NULL ); + display_theme_list = ag_display_theme_get_list(); + g_list_foreach( + display_theme_list, + (GFunc)ag_window_add_display_theme, + priv + ); + g_list_free_full(display_theme_list, (GDestroyNotify)ag_display_theme_free); + gtk_tree_model_foreach( + GTK_TREE_MODEL(priv->display_theme_model), + (GtkTreeModelForeachFunc)ag_window_set_default_display_theme, + window + ); + + display_theme_renderer = gtk_cell_renderer_text_new(); + gtk_cell_layout_pack_start( + GTK_CELL_LAYOUT(priv->display_theme), + display_theme_renderer, + TRUE + ); + gtk_cell_layout_set_attributes( + GTK_CELL_LAYOUT(priv->display_theme), + display_theme_renderer, + "text", 1, + NULL + ); + priv->tab_list = GTK_WIDGET(gd_main_view_new(GD_MAIN_VIEW_ICON)); gtk_stack_add_titled( GTK_STACK(priv->stack), @@ -1930,6 +2177,26 @@ ag_window_city_changed_callback(GtkSearchEntry *city, AgWindow *window) } } +void +ag_window_display_theme_changed_cb(GtkComboBox *combo_box, + AgWindow *window) +{ + GtkTreeIter iter; + gint theme_id; + AgDisplayTheme *theme; + AgWindowPrivate *priv = ag_window_get_instance_private(window); + + gtk_combo_box_get_active_iter(combo_box, &iter); + gtk_tree_model_get( + GTK_TREE_MODEL(priv->display_theme_model), &iter, + 0, &theme_id, + -1 + ); + + theme = ag_display_theme_get_by_id(theme_id); + ag_window_set_theme(window, theme); +} + static void ag_window_class_init(AgWindowClass *klass) { @@ -2074,6 +2341,16 @@ ag_window_class_init(AgWindowClass *klass) AgWindow, points_eq ); + gtk_widget_class_bind_template_child_private( + widget_class, + AgWindow, + display_theme + ); + gtk_widget_class_bind_template_child_private( + widget_class, + AgWindow, + display_theme_model + ); gtk_widget_class_bind_template_callback( widget_class, @@ -2095,16 +2372,10 @@ ag_window_class_init(AgWindowClass *klass) widget_class, ag_window_city_changed_callback ); -} - -gboolean -ag_window_chart_context_cb(WebKitWebView *web_view, - GtkWidget *default_menu, - WebKitHitTestResult *hit_test_result, - gboolean triggered_with_keyboard, - gpointer user_data) -{ - return TRUE; + gtk_widget_class_bind_template_callback( + widget_class, + ag_window_display_theme_changed_cb + ); } static gboolean @@ -2124,26 +2395,10 @@ ag_window_configure_event_cb(GtkWidget *widget, } GtkWidget * -ag_window_new(AgApp *app, WebKitUserContentManager *manager) +ag_window_new(AgApp *app) { - AgWindow *window = g_object_new(AG_TYPE_WINDOW, NULL); - AgWindowPrivate *priv = ag_window_get_instance_private(window); - - priv->chart_web_view = webkit_web_view_new_with_user_content_manager( - manager - ); - gtk_box_pack_end( - GTK_BOX(priv->tab_chart), - priv->chart_web_view, - TRUE, TRUE, 0 - ); - - g_signal_connect( - priv->chart_web_view, - "context-menu", - G_CALLBACK(ag_window_chart_context_cb), - NULL - ); + AgWindow *window = g_object_new(AG_TYPE_WINDOW, NULL); + AgWindowPrivate *priv = ag_window_get_instance_private(window); // TODO: translate this error message! webkit_web_view_load_html( @@ -2192,7 +2447,7 @@ ag_window_set_chart(AgWindow *window, AgChart *chart) g_clear_object(&(priv->chart)); } - ag_db_save_data_free(priv->saved_data); + ag_db_chart_save_free(priv->saved_data); priv->chart = chart; g_signal_connect( @@ -2278,7 +2533,7 @@ ag_window_change_tab(AgWindow *window, const gchar *tab_name) } static void -ag_window_add_chart_to_list(AgDbSave *save_data, AgWindow *window) +ag_window_add_chart_to_list(AgDbChartSave *save_data, AgWindow *window) { GtkTreeIter iter; AgWindowPrivate *priv = ag_window_get_instance_private(window); @@ -2313,7 +2568,7 @@ ag_window_load_chart_list(AgWindow *window) { AgDb *db = ag_db_get(); GError *err = NULL; - GList *chart_list = ag_db_get_chart_list(db, &err); + GList *chart_list = ag_db_chart_get_list(db, &err); ag_window_clear_chart_list(window); /* With only a few charts, this should be fine. Maybe implementing lazy diff --git a/src/ag-window.h b/src/ag-window.h index 3ebb563..0475451 100644 --- a/src/ag-window.h +++ b/src/ag-window.h @@ -2,7 +2,6 @@ #define __AG_WINDOW_H__ #include -#include #include "ag-app.h" #include "ag-chart.h" @@ -41,7 +40,7 @@ struct _AgWindowClass { GType ag_window_get_type(void) G_GNUC_CONST; -GtkWidget *ag_window_new(AgApp *app, WebKitUserContentManager *manager); +GtkWidget *ag_window_new(AgApp *app); void ag_window_set_chart(AgWindow *window, AgChart *chart); diff --git a/src/astrognome.c b/src/astrognome.c index bd2fe06..85e71db 100644 --- a/src/astrognome.c +++ b/src/astrognome.c @@ -27,6 +27,7 @@ GtkFileFilter *filter_hor = NULL; GtkTreeModel *country_list = NULL; GtkTreeModel *city_list = NULL; GHashTable *xinclude_positions; +gsize used_planets_count; const char *moonStateName[] = { "New Moon", @@ -40,6 +41,32 @@ const char *moonStateName[] = { "Dark Moon" }; +const GswePlanet used_planets[] = { + GSWE_PLANET_MC, + GSWE_PLANET_ASCENDANT, + GSWE_PLANET_VERTEX, + GSWE_PLANET_SUN, + GSWE_PLANET_MOON, + GSWE_PLANET_MERCURY, + GSWE_PLANET_VENUS, + GSWE_PLANET_MARS, + GSWE_PLANET_JUPITER, + GSWE_PLANET_SATURN, + GSWE_PLANET_URANUS, + GSWE_PLANET_NEPTUNE, + GSWE_PLANET_PLUTO, + GSWE_PLANET_MOON_NODE, + GSWE_PLANET_MOON_APOGEE, + GSWE_PLANET_CHIRON, + GSWE_PLANET_PHOLUS, + GSWE_PLANET_NESSUS, + GSWE_PLANET_CERES, + GSWE_PLANET_PALLAS, + GSWE_PLANET_JUNO, + GSWE_PLANET_VESTA, + GSWE_PLANET_CHARIKLO +}; + void init_filters(void) { @@ -188,6 +215,102 @@ ag_house_system_nick_to_id(const gchar *nick) return GSWE_HOUSE_SYSTEM_NONE; } +const gchar * +ag_planet_id_to_nick(GswePlanet planet) +{ + GEnumClass *planet_class; + GEnumValue *enum_value; + + planet_class = g_type_class_ref(GSWE_TYPE_PLANET); + enum_value = g_enum_get_value(planet_class, planet); + + if (enum_value) { + return enum_value->value_nick; + } + + return NULL; +} + +GswePlanet +ag_planet_nick_to_id(const gchar *nick) +{ + GEnumClass *planet_class; + GEnumValue *enum_value; + + planet_class = g_type_class_ref(GSWE_TYPE_PLANET); + enum_value = g_enum_get_value_by_nick(planet_class, nick); + + if (enum_value) { + return enum_value->value; + } + + return GSWE_PLANET_NONE; +} + +const gchar * +ag_aspect_id_to_nick(GsweAspect aspect) +{ + GEnumClass *aspect_class; + GEnumValue *enum_value; + + aspect_class = g_type_class_ref(GSWE_TYPE_ASPECT); + enum_value = g_enum_get_value(aspect_class, aspect); + + if (enum_value) { + return enum_value->value_nick; + } + + return NULL; +} + +GsweAspect +ag_aspect_nick_to_id(const gchar *nick) +{ + GEnumClass *aspect_class; + GEnumValue *enum_value; + + aspect_class = g_type_class_ref(GSWE_TYPE_ASPECT); + enum_value = g_enum_get_value_by_nick(aspect_class, nick); + + if (enum_value) { + return enum_value->value; + } + + return GSWE_ASPECT_NONE; +} + +const gchar * +ag_antiscion_axis_id_to_nick(GsweAntiscionAxis antiscion_axis) +{ + GEnumClass *antiscion_axis_class; + GEnumValue *enum_value; + + antiscion_axis_class = g_type_class_ref(GSWE_TYPE_ANTISCION_AXIS); + enum_value = g_enum_get_value(antiscion_axis_class, antiscion_axis); + + if (enum_value) { + return enum_value->value_nick; + } + + return NULL; +} + +GsweAntiscionAxis +ag_antiscion_axis_nick_to_id(const gchar *nick) +{ + GEnumClass *antiscion_axis_class; + GEnumValue *enum_value; + + antiscion_axis_class = g_type_class_ref(GSWE_TYPE_ANTISCION_AXIS); + enum_value = g_enum_get_value_by_nick(antiscion_axis_class, nick); + + if (enum_value) { + return enum_value->value; + } + + return GSWE_ANTISCION_AXIS_NONE; +} + /** * ag_get_user_data_dir: * @@ -261,6 +384,7 @@ main(int argc, char *argv[]) textdomain(GETTEXT_PACKAGE); #endif + used_planets_count = sizeof(used_planets) / sizeof(GswePlanet); LIBXML_TEST_VERSION; xmlSubstituteEntitiesDefault(1); xmlLoadExtDtdDefaultValue = 1; diff --git a/src/astrognome.h b/src/astrognome.h index efcc1c4..9697c32 100644 --- a/src/astrognome.h +++ b/src/astrognome.h @@ -10,11 +10,13 @@ typedef struct { gboolean new_window; } AstrognomeOptions; -extern GtkFileFilter *filter_all; -extern GtkFileFilter *filter_chart; -extern GtkFileFilter *filter_hor; -extern GtkTreeModel *country_list; -extern GtkTreeModel *city_list; +extern GtkFileFilter *filter_all; +extern GtkFileFilter *filter_chart; +extern GtkFileFilter *filter_hor; +extern GtkTreeModel *country_list; +extern GtkTreeModel *city_list; +extern const GswePlanet used_planets[]; +extern gsize used_planets_count; enum { AG_COUNTRY_CODE, @@ -35,6 +37,16 @@ enum { const gchar *ag_house_system_id_to_nick(GsweHouseSystem house_system); GsweHouseSystem ag_house_system_nick_to_id(const gchar *nick); + +const gchar *ag_planet_id_to_nick(GswePlanet planet); +GswePlanet ag_planet_nick_to_id(const gchar *nick); + +const gchar *ag_aspect_id_to_nick(GsweAspect aspect); +GsweAspect ag_aspect_nick_to_id(const gchar *nick); + +const gchar *ag_antiscion_axis_id_to_nick(GsweAntiscionAxis antiscion_axis); +GsweAntiscionAxis ag_antiscion_axis_nick_to_id(const gchar *nick); + GFile *ag_get_user_data_dir(void); #ifndef GDOUBLE_FROM_LE diff --git a/src/resources/ui/ag-preferences.ui b/src/resources/ui/ag-preferences.ui index 9b40de3..6047083 100644 --- a/src/resources/ui/ag-preferences.ui +++ b/src/resources/ui/ag-preferences.ui @@ -10,11 +10,19 @@ + + + + + + + +