[recipes] Added unit conversion functionality and a corresponding user setting for both weight and volume unit



commit 85d07da3232a6546b5639012a0aa48999c58fe8a
Author: Paxana Amanda Xander <veganbikepunk gmail com>
Date:   Mon Aug 28 14:19:02 2017 -0700

    Added unit conversion functionality and a corresponding user setting for both weight and volume units

 data/org.gnome.Recipes.gschema.xml |   21 +++-
 src/gr-convert-units.c             |  318 ++++++++++++++++++++++++++++++++++++
 src/gr-convert-units.h             |   50 ++++++
 src/gr-ingredients-viewer.c        |   73 ++++++---
 src/meson.build                    |    1 +
 5 files changed, 438 insertions(+), 25 deletions(-)
---
diff --git a/data/org.gnome.Recipes.gschema.xml b/data/org.gnome.Recipes.gschema.xml
index e15641f..fd2d9dc 100644
--- a/data/org.gnome.Recipes.gschema.xml
+++ b/data/org.gnome.Recipes.gschema.xml
@@ -7,6 +7,12 @@
     <value nick="locale" value="2"/>
   </enum>
 
+  <enum id="org.gnome.recipes.MetricOrImperial">
+    <value nick="metric" value="0"/>
+    <value nick="imperial" value="1"/>
+    <value nick="locale" value="2"/>
+  </enum>
+
   <enum id="org.gnome.recipes.SortKey">
     <value nick="name" value="0"/>
     <value nick="recency" value="1"/>
@@ -95,7 +101,20 @@
         The setting determines whether the surprise dialog should be shown on startup.
       </description>
     </key>
-
+    <key name="volume-unit" enum="org.gnome.recipes.MetricOrImperial">
+      <default>'locale'</default>
+      <summary>The setting for which unit volumes should be displayed in. </summary>
+      <description>
+         The setting for which unit volumes should be displayed in. Default is 'locale',
+      </description>
+     </key>
+    <key name="weight-unit" enum="org.gnome.recipes.MetricOrImperial">
+      <default>'locale'</default>
+      <summary>The setting for which unit weights should be displayed in. </summary>
+      <description>
+         The setting for which unit weights should be displayed in. Default is 'locale',
+      </description>
+     </key>
   </schema>
 
 </schemalist>
diff --git a/src/gr-convert-units.c b/src/gr-convert-units.c
new file mode 100644
index 0000000..3174c34
--- /dev/null
+++ b/src/gr-convert-units.c
@@ -0,0 +1,318 @@
+/* gr-convert-units.c:
+ *
+ * Copyright (C) 2017 Paxana Xander <paxana paxana me>
+ *
+ * Licensed under the GNU General Public License Version 3
+ *
+ * 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
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "config.h"
+
+#include <string.h>
+#include <stdlib.h>
+#include <locale.h>
+#include <langinfo.h>
+#include <math.h>
+
+#include <glib/gi18n.h>
+#include <gtk/gtk.h>
+
+#include "gr-settings.h"
+#include "gr-unit.h"
+#include "gr-convert-units.h"
+#include "gr-number.h"
+#include "gr-utils.h"
+
+GrTemperatureUnit
+gr_convert_get_temperature_unit (void)
+{
+        int unit;
+        GSettings *settings = gr_settings_get ();
+
+        unit = g_settings_get_enum (settings, "temperature-unit");
+
+        if (unit == GR_TEMPERATURE_UNIT_LOCALE) {
+        #ifdef LC_MEASUREMENT
+                const char *fmt;
+
+                fmt = nl_langinfo (_NL_MEASUREMENT_MEASUREMENT);
+
+                if (fmt && *fmt == 2)
+                        unit = GR_TEMPERATURE_UNIT_FAHRENHEIT;
+                else
+        #endif
+                        unit = GR_TEMPERATURE_UNIT_CELSIUS;
+        }
+
+        return unit;
+}
+
+GrPreferredUnit
+gr_convert_get_volume_unit (void)
+ {
+    int unit;
+    GSettings *settings = gr_settings_get ();
+
+    unit = g_settings_get_enum (settings, "volume-unit");
+
+    if (unit == GR_PREFERRED_UNIT_LOCALE) {
+#ifdef LC_MEASUREMENT
+                const char *fmt;
+
+            fmt = nl_langinfo (_NL_MEASUREMENT_MEASUREMENT);
+            if (fmt && *fmt == 2)
+                unit = GR_PREFERRED_UNIT_IMPERIAL;
+            else
+#endif
+                unit = GR_PREFERRED_UNIT_METRIC;
+        }
+
+        return unit;
+}
+
+GrPreferredUnit
+gr_convert_get_weight_unit (void)
+{
+        int unit;
+        GSettings *settings = gr_settings_get ();
+
+        unit = g_settings_get_enum (settings, "weight-unit");
+
+        if (unit == GR_PREFERRED_UNIT_LOCALE) {
+#ifdef LC_MEASUREMENT
+                 const char *fmt;
+
+                fmt = nl_langinfo (_NL_MEASUREMENT_MEASUREMENT);
+                if (fmt && *fmt == 2)
+                        unit = GR_PREFERRED_UNIT_IMPERIAL;
+                else
+#endif
+                        unit = GR_PREFERRED_UNIT_METRIC;
+        }
+        return unit;
+}
+
+void
+gr_convert_temp (int *num, int *unit, int user_unit)
+{
+        int num1 = *num;
+        int unit1 = *unit;
+
+        if (unit1 == GR_TEMPERATURE_UNIT_CELSIUS &&
+            user_unit == GR_TEMPERATURE_UNIT_FAHRENHEIT) {
+                num1 = (num1 * 1.8) + 32;
+                unit1 = user_unit;
+        }
+        else if (unit1 == GR_TEMPERATURE_UNIT_FAHRENHEIT &&
+                 user_unit == GR_TEMPERATURE_UNIT_CELSIUS) {
+                num1 = (num1 - 32) / 1.8;
+                unit1 = user_unit;
+        }
+
+        *unit = unit1;
+        *num = num1;
+}
+
+void
+gr_convert_volume (double *amount, GrUnit *unit, GrPreferredUnit user_volume_unit)
+{
+        double amount1 = *amount;
+        GrUnit unit1 = *unit;
+
+        if (user_volume_unit == GR_PREFERRED_UNIT_IMPERIAL) {
+                switch (unit1) {
+                case GR_UNIT_MILLILITER:
+                        amount1 = amount1 / 4.92892;
+                        unit1 = GR_UNIT_TEASPOON;
+                        break;
+
+                case GR_UNIT_DECILITER:
+                        amount1 = amount1 * 20.2884;
+                        unit1 = GR_UNIT_TEASPOON;
+                        break;
+
+                case GR_UNIT_LITER:
+                        amount1 = amount1 * 202.884;
+                        unit1 = GR_UNIT_TEASPOON;
+                        break;
+
+                case GR_UNIT_TEASPOON:
+                        amount1 = amount1;
+                        unit1 = GR_UNIT_TEASPOON;
+                        break;
+
+                case GR_UNIT_TABLESPOON:
+                        amount1 = amount1 * 3;
+                        unit1 = GR_UNIT_TEASPOON;
+                        break;
+
+                case GR_UNIT_CUP:
+                        amount1 = amount1 * 48;
+                        unit1 = GR_UNIT_TEASPOON;
+                        break;
+
+                case GR_UNIT_PINT:
+                        amount1 = amount1 * 96;
+                        unit1 = GR_UNIT_TEASPOON;
+                        break;
+
+                case GR_UNIT_QUART:
+                        amount1 = amount1 * 192;
+                        unit1 = GR_UNIT_TEASPOON;
+                        break;
+
+                case GR_UNIT_GALLON:
+                        amount1 = amount1 * 768;
+                        unit1 = GR_UNIT_TEASPOON;
+                        break;
+
+                case GR_UNIT_FLUID_OUNCE:
+                        amount1 = amount1 * 6;
+                        unit1 = GR_UNIT_TEASPOON;
+                        break;
+
+                default: ;
+                }
+        }
+        if (user_volume_unit == GR_PREFERRED_UNIT_METRIC) {
+                switch (unit1) {
+                case GR_UNIT_TEASPOON:
+                        amount1 = amount1 * 4.92892;
+                        unit1 = GR_UNIT_MILLILITER;
+                        break;
+
+                case GR_UNIT_TABLESPOON:
+                        amount1 = amount1 * 14.79;
+                        unit1 = GR_UNIT_MILLILITER;
+                        break;
+
+                case GR_UNIT_CUP:
+                        amount1 = amount1 * 236.59;
+                        unit1 = GR_UNIT_MILLILITER;
+                        break;
+
+                case GR_UNIT_PINT:
+                        amount1 = amount1 * 473.176;
+                        unit1 = GR_UNIT_MILLILITER;
+                        break;
+
+                case GR_UNIT_QUART:
+                        amount1 = amount1 * 946.353;
+                        unit1 = GR_UNIT_MILLILITER;
+                        break;
+
+                case GR_UNIT_GALLON:
+                        amount1 = amount1 * 3785.41;
+                        unit1 = GR_UNIT_MILLILITER;
+                        break;
+
+                case GR_UNIT_FLUID_OUNCE:
+                        amount1 = amount1 * 29.5735;
+                        unit1 = GR_UNIT_MILLILITER;
+                        break;
+
+                case GR_UNIT_MILLILITER:
+                        amount1 = amount1;
+                        unit1 = GR_UNIT_MILLILITER;
+                        break;
+
+                case GR_UNIT_DECILITER:
+                        amount1 = amount1 * 100;
+                        unit1 = GR_UNIT_MILLILITER;
+                        break;
+
+                case GR_UNIT_LITER:
+                        amount1 = amount1 * 1000;
+                        unit1 = GR_UNIT_MILLILITER;
+                        break;
+
+                default: ;
+                }
+        }
+
+        *amount = amount1;
+        *unit = unit1;
+}
+
+void
+gr_convert_weight (double *amount, GrUnit *unit, GrPreferredUnit user_weight_unit)
+{
+        double amount1 = *amount;
+        GrUnit unit1 = *unit;
+
+        if (user_weight_unit == GR_PREFERRED_UNIT_IMPERIAL) {
+                switch (unit1) {
+                case GR_UNIT_GRAM:
+                        amount1 = amount1 * 0.035274;
+                        unit1 = GR_UNIT_OUNCE;
+                        break;
+
+                case GR_UNIT_KILOGRAM:
+                        amount1 = amount1 * 35.274;
+                        unit1 = GR_UNIT_OUNCE;
+                        break;
+
+                case GR_UNIT_OUNCE:
+                        amount1 = amount1;
+                        unit1 = GR_UNIT_OUNCE;
+                        break;
+
+                case GR_UNIT_POUND:
+                        amount1 = amount1 * 16;
+                        unit1 = GR_UNIT_OUNCE;
+                        break;
+
+                case GR_UNIT_STONE:
+                        amount1 = amount1 * 224;
+                        unit1 = GR_UNIT_OUNCE;
+                        break;
+
+                default: ;
+                }
+        }
+        if (user_weight_unit == GR_PREFERRED_UNIT_METRIC) {
+                switch (unit1) {
+                case GR_UNIT_OUNCE:
+                        amount1 = amount1 * 28.3495;
+                        unit1 = GR_UNIT_GRAM;
+                        break;
+
+                case GR_UNIT_POUND:
+                        amount1 = amount1 * 453.592;
+                        unit1 = GR_UNIT_GRAM;
+                        break;
+
+                case GR_UNIT_STONE:
+                        amount1 = amount1 * 6350.29;
+                        unit1 = GR_UNIT_GRAM;
+                        break;
+
+                case GR_UNIT_GRAM:
+                        amount1 = amount1;
+                        unit1 = GR_UNIT_GRAM;
+                        break;
+
+                case GR_UNIT_KILOGRAM:
+                        amount1 = amount1 * 1000;
+                        unit1 = GR_UNIT_GRAM;
+                        break;
+
+                default: ;
+                }
+         }
+
+         *amount = amount1;
+         *unit = unit1;
+}
diff --git a/src/gr-convert-units.h b/src/gr-convert-units.h
new file mode 100644
index 0000000..cb56a3e
--- /dev/null
+++ b/src/gr-convert-units.h
@@ -0,0 +1,50 @@
+/* gr-chef.h:
+*
+* Copyright (C) 2016 Paxana Xander <paxana paxana me>
+*
+* Licensed under the GNU General Public License Version 3
+*
+* 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
+* the Free Software Foundation, either version 3 of the License, or
+* (at your option) any later version.
+*
+* This program is distributed in the hope that it will be useful,
+* but WITHOUT ANY WARRANTY; without even the implied warranty of
+* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+* GNU General Public License for more details.
+*
+* You should have received a copy of the GNU General Public License
+* along with this program.  If not, see <http://www.gnu.org/licenses/>.
+*/
+
+
+#pragma once
+
+#include <glib-object.h>
+#include <gtk/gtk.h>
+#include <libgd/gd.h>
+#include "gr-recipe.h"
+
+G_BEGIN_DECLS
+
+typedef enum {
+        GR_TEMPERATURE_UNIT_CELSIUS    = 0,
+        GR_TEMPERATURE_UNIT_FAHRENHEIT = 1,
+        GR_TEMPERATURE_UNIT_LOCALE     = 2
+} GrTemperatureUnit;
+ 
+typedef enum {
+        GR_PREFERRED_UNIT_METRIC    = 0,
+        GR_PREFERRED_UNIT_IMPERIAL = 1,
+        GR_PREFERRED_UNIT_LOCALE     = 2
+} GrPreferredUnit;
+
+GrTemperatureUnit   gr_convert_get_temperature_unit     (void);
+GrPreferredUnit     gr_convert_get_volume_unit          (void);
+GrPreferredUnit     gr_convert_get_weight_unit          (void);
+void                gr_convert_temp                     (int *num, int *unit, int user_unit);
+void                gr_convert_volume                   (double *amount, GrUnit *unit, GrPreferredUnit 
user_volume_unit);
+void                gr_convert_weight                   (double *amount, GrUnit *unit, GrPreferredUnit 
user_weight_unit);
+
+G_END_DECLS
diff --git a/src/gr-ingredients-viewer.c b/src/gr-ingredients-viewer.c
index f2f8018..31a6ed9 100644
--- a/src/gr-ingredients-viewer.c
+++ b/src/gr-ingredients-viewer.c
@@ -18,20 +18,22 @@
  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
  */
 
-#include "config.h"
-
-#include <string.h>
-
-#include "gr-ingredients-viewer.h"
-#include "gr-ingredients-viewer-row.h"
-#include "gr-ingredients-list.h"
-#include "gr-ingredient.h"
-#include "gr-utils.h"
-
-#ifdef ENABLE_GSPELL
-#include <gspell/gspell.h>
-#endif
-
+ #include "config.h"
+ 
+ #include <string.h>
+ 
+ #include "gr-ingredients-viewer.h"
+ #include "gr-ingredients-viewer-row.h"
+ #include "gr-ingredients-list.h"
+ #include "gr-ingredient.h"
+ #include "gr-utils.h"
+ #include "gr-number.h"
+ #include "gr-convert-units.h"
+ #include "gr-unit.h"
+ 
+ #ifdef ENABLE_GSPELL
+ #include <gspell/gspell.h>
+ #endif
 
 struct _GrIngredientsViewer
 {
@@ -316,20 +318,43 @@ gr_ingredients_viewer_set_ingredients (GrIngredientsViewer *viewer,
         ingredients = gr_ingredients_list_new (text);
         ings = gr_ingredients_list_get_ingredients (ingredients, viewer->title);
         for (i = 0; ings && ings[i]; i++) {
-                g_autofree char *s = NULL;
-                g_auto(GStrv) strv = NULL;
-                const char *amount;
-                const char *unit;
+                double amount;
+                GrUnit unit;
                 GtkWidget *row;
+                GrDimension dimension;
+                double scale = viewer->scale;
+
+                unit = gr_ingredients_list_get_unit (ingredients, viewer->title, ings[i]);
+                amount = gr_ingredients_list_get_amount (ingredients, viewer->title, ings[i]) * scale;
+                dimension = gr_unit_get_dimension (unit);
+
+                if (dimension) {
+                        if (dimension == GR_DIMENSION_VOLUME) {
+                                GrPreferredUnit user_volume_unit = gr_convert_get_volume_unit ();
+                                gr_convert_volume (&amount, &unit, user_volume_unit);
+                        }
+
+                        if (dimension == GR_DIMENSION_MASS) {
+                                GrPreferredUnit user_weight_unit = gr_convert_get_weight_unit ();
+                                gr_convert_weight (&amount, &unit, user_weight_unit);
+                        }
+                }
+
+                char *a_final = gr_number_format (amount);
+                const char *u_final = gr_unit_get_name (unit);
+
+                char for_display[128];
+                if (u_final == NULL) {
+                        snprintf (for_display, sizeof for_display, "%s", a_final);
+                }
+                else {
+                        snprintf (for_display, sizeof for_display, "%s %s", a_final, u_final);
+                }
 
-                s = gr_ingredients_list_scale_unit (ingredients, viewer->title, ings[i], viewer->scale);
-                strv = g_strsplit (s, " ", 2);
-                amount = strv[0];
-                unit = strv[1] ? strv[1] : "";
+                u_final = for_display;
 
                 row = g_object_new (GR_TYPE_INGREDIENTS_VIEWER_ROW,
-                                    "amount", amount,
-                                    "unit", unit,
+                                    "unit", u_final,
                                     "ingredient", ings[i],
                                     "size-group", viewer->group,
                                     "editable", viewer->editable,
diff --git a/src/meson.build b/src/meson.build
index 2d8b6f3..459fb9d 100644
--- a/src/meson.build
+++ b/src/meson.build
@@ -58,6 +58,7 @@ src += ['main.c',
        'gr-chef.c',
        'gr-chef-dialog.c',
        'gr-chef-tile.c',
+       'gr-convert-units.c',
        'gr-cooking-page.c',
        'gr-cooking-view.c',
        'gr-cuisine.c',


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