aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/device.c32
-rw-r--r--src/indicator-power.c135
-rw-r--r--src/indicator-power.h2
3 files changed, 99 insertions, 70 deletions
diff --git a/src/device.c b/src/device.c
index 898e18f..490ff1a 100644
--- a/src/device.c
+++ b/src/device.c
@@ -334,7 +334,7 @@ indicator_power_device_get_icon_names (const IndicatorPowerDevice * device)
gdouble percentage = indicator_power_device_get_percentage (device);
const UpDeviceKind kind = indicator_power_device_get_kind (device);
const UpDeviceState state = indicator_power_device_get_state (device);
- const gchar * kind_str = kind_str = up_device_kind_to_string (kind);
+ const gchar * kind_str = up_device_kind_to_string (kind);
GPtrArray * names = g_ptr_array_new ();
@@ -351,19 +351,19 @@ indicator_power_device_get_icon_names (const IndicatorPowerDevice * device)
else switch (state)
{
case UP_DEVICE_STATE_EMPTY:
- g_ptr_array_add (names, g_strdup("battery-empty-symbolic"));
+ g_ptr_array_add (names, g_strdup_printf("%s-empty-symbolic", kind_str));
g_ptr_array_add (names, g_strdup_printf("gpm-%s-empty", kind_str));
g_ptr_array_add (names, g_strdup_printf("gpm-%s-000", kind_str));
- g_ptr_array_add (names, g_strdup("battery-empty"));
+ g_ptr_array_add (names, g_strdup_printf("%s-empty", kind_str));
break;
case UP_DEVICE_STATE_FULLY_CHARGED:
- g_ptr_array_add (names, g_strdup("battery-full-charged-symbolic"));
- g_ptr_array_add (names, g_strdup("battery-full-charging-symbolic"));
+ g_ptr_array_add (names, g_strdup_printf("%s-full-charged-symbolic", kind_str));
+ g_ptr_array_add (names, g_strdup_printf("%s-full-charging-symbolic", kind_str));
g_ptr_array_add (names, g_strdup_printf("gpm-%s-full", kind_str));
g_ptr_array_add (names, g_strdup_printf("gpm-%s-100", kind_str));
- g_ptr_array_add (names, g_strdup("battery-full-charged"));
- g_ptr_array_add (names, g_strdup("battery-full-charging"));
+ g_ptr_array_add (names, g_strdup_printf("%s-full-charged", kind_str));
+ g_ptr_array_add (names, g_strdup_printf("%s-full-charging", kind_str));
break;
case UP_DEVICE_STATE_CHARGING:
@@ -374,9 +374,9 @@ indicator_power_device_get_icon_names (const IndicatorPowerDevice * device)
suffix_str = get_device_icon_suffix (percentage);
index_str = get_device_icon_index (percentage);
- g_ptr_array_add (names, g_strdup_printf ("battery-%s-charging-symbolic", suffix_str));
+ g_ptr_array_add (names, g_strdup_printf ("%s-%s-charging-symbolic", kind_str, suffix_str));
g_ptr_array_add (names, g_strdup_printf ("gpm-%s-%s-charging", kind_str, index_str));
- g_ptr_array_add (names, g_strdup_printf ("battery-%s-charging", suffix_str));
+ g_ptr_array_add (names, g_strdup_printf ("%s-%s-charging", kind_str, suffix_str));
break;
case UP_DEVICE_STATE_DISCHARGING:
@@ -392,14 +392,14 @@ indicator_power_device_get_icon_names (const IndicatorPowerDevice * device)
index_str = get_device_icon_index (percentage);
g_ptr_array_add (names, g_strdup_printf ("%s-%s", kind_str, index_str));
g_ptr_array_add (names, g_strdup_printf ("gpm-%s-%s", kind_str, index_str));
- g_ptr_array_add (names, g_strdup_printf ("battery-%s-symbolic", suffix_str));
- g_ptr_array_add (names, g_strdup_printf ("battery-%s", suffix_str));
+ g_ptr_array_add (names, g_strdup_printf ("%s-%s-symbolic", kind_str, suffix_str));
+ g_ptr_array_add (names, g_strdup_printf ("%s-%s", kind_str, suffix_str));
break;
default:
- g_ptr_array_add (names, g_strdup("battery-missing-symbolic"));
- g_ptr_array_add (names, g_strdup("gpm-battery-missing"));
- g_ptr_array_add (names, g_strdup("battery-missing"));
+ g_ptr_array_add (names, g_strdup_printf("%s-missing-symbolic", kind_str));
+ g_ptr_array_add (names, g_strdup_printf("gpm-%s-missing", kind_str));
+ g_ptr_array_add (names, g_strdup_printf("%s-missing", kind_str));
}
g_ptr_array_add (names, NULL); /* terminates the strv */
@@ -528,6 +528,10 @@ device_kind_to_localised_string (UpDeviceKind kind)
/* TRANSLATORS: tablet device */
text = _("Computer");
break;
+ case UP_DEVICE_KIND_UNKNOWN:
+ /* TRANSLATORS: unknown device */
+ text = _("Unknown");
+ break;
default:
g_warning ("enum unrecognised: %i", kind);
text = up_device_kind_to_string (kind);
diff --git a/src/indicator-power.c b/src/indicator-power.c
index 9829839..4118dcc 100644
--- a/src/indicator-power.c
+++ b/src/indicator-power.c
@@ -150,6 +150,8 @@ indicator_power_dispose (GObject *object)
dispose_devices (self);
+ g_clear_object (&priv->label);
+ g_clear_object (&priv->status_image);
g_clear_object (&priv->dbus_listener);
g_clear_object (&priv->settings);
@@ -350,76 +352,95 @@ build_menu (IndicatorPower *self)
gtk_widget_show_all (GTK_WIDGET (priv->menu));
}
-static IndicatorPowerDevice*
-get_primary_device (GSList * devices)
+/* sort devices from most interesting to least interesting on this criteria:
+ 1. discharging items from least time remaining until most time remaining
+ 2. discharging items with an unknown time remaining
+ 3. charging items from most time left to charge to least time left to charge
+ 4. charging items with an unknown time remaining
+ 5. everything else */
+static gint
+device_compare_func (gconstpointer ga, gconstpointer gb)
{
- IndicatorPowerDevice * primary_device = NULL;
- IndicatorPowerDevice * primary_device_charging = NULL;
- IndicatorPowerDevice * primary_device_discharging = NULL;
- gboolean charging = FALSE;
- gboolean discharging = FALSE;
- guint64 min_discharging_time = G_MAXUINT64;
- guint64 max_charging_time = 0;
- GSList * l;
-
- for (l=devices; l!=NULL; l=l->next)
+ int ret;
+ int state;
+ const IndicatorPowerDevice * a = INDICATOR_POWER_DEVICE(ga);
+ const IndicatorPowerDevice * b = INDICATOR_POWER_DEVICE(gb);
+ const int a_state = indicator_power_device_get_state (a);
+ const int b_state = indicator_power_device_get_state (b);
+ const gdouble a_percentage = indicator_power_device_get_percentage (a);
+ const gdouble b_percentage = indicator_power_device_get_percentage (b);
+ const time_t a_time = indicator_power_device_get_time (a);
+ const time_t b_time = indicator_power_device_get_time (b);
+
+ ret = 0;
+
+ state = UP_DEVICE_STATE_DISCHARGING;
+ if (!ret && ((a_state == state) || (b_state == state)))
{
- IndicatorPowerDevice * device = INDICATOR_POWER_DEVICE(l->data);
- const UpDeviceKind kind = indicator_power_device_get_kind (device);
- const UpDeviceState state = indicator_power_device_get_state (device);
- const gdouble percentage = indicator_power_device_get_percentage (device);
- const time_t time = indicator_power_device_get_time (device);
-
- /* Try to fix the case when we get a empty battery bay as a real battery */
- if (state == UP_DEVICE_STATE_UNKNOWN &&
- percentage == 0)
- continue;
-
- /* not battery */
- if (kind != UP_DEVICE_KIND_BATTERY)
- continue;
-
- if (state == UP_DEVICE_STATE_DISCHARGING)
+ if (a_state != state) /* b is discharging */
{
- discharging = TRUE;
- if (time < min_discharging_time)
- {
- min_discharging_time = time;
- primary_device_discharging = device;
- }
+ ret = 1;
}
- else if (state == UP_DEVICE_STATE_CHARGING)
+ else if (b_state != state) /* a is discharging */
{
- charging = TRUE;
- if (time == 0) /* Battery broken */
- {
- primary_device_charging = device;
- }
- if (time > max_charging_time)
- {
- max_charging_time = time;
- primary_device_charging = device;
- }
+ ret = -1;
}
- else
+ else /* both are discharging; least-time-left goes first */
{
- primary_device = device;
+ if (!a_time || !b_time) /* known time always trumps unknown time */
+ ret = a_time ? -1 : 1;
+ else if (a_time != b_time)
+ ret = a_time < b_time ? -1 : 1;
+ else
+ ret = a_percentage < b_percentage ? -1 : 1;
}
}
- if (discharging)
+ state = UP_DEVICE_STATE_CHARGING;
+ if (!ret && (((a_state == state) && a_time) || ((b_state == state) && b_time)))
{
- primary_device = primary_device_discharging;
+ if (a_state != state) /* b is charging */
+ {
+ ret = 1;
+ }
+ else if (b_state != state) /* a is charging */
+ {
+ ret = -1;
+ }
+ else /* both are discharging; most-time-to-charge goes first */
+ {
+ if (!a_time || !b_time) /* known time always trumps unknown time */
+ ret = a_time ? -1 : 1;
+ else if (a_time != b_time)
+ ret = a_time > b_time ? -1 : 1;
+ else
+ ret = a_percentage < b_percentage ? -1 : 1;
+ }
}
- else if (charging)
+
+ if (!ret)
+ ret = a_state - b_state;
+
+ return ret;
+}
+
+IndicatorPowerDevice *
+indicator_power_choose_primary_device (GSList * devices)
+{
+ IndicatorPowerDevice * primary = NULL;
+
+ if (devices != NULL)
{
- primary_device = primary_device_charging;
- }
+ GSList * tmp;
- if (primary_device != NULL)
- g_object_ref (primary_device);
+ tmp = g_slist_copy (devices);
+ tmp = g_slist_sort (tmp, device_compare_func);
+ primary = g_object_ref (tmp->data);
+
+ g_slist_free (tmp);
+ }
- return primary_device;
+ return primary;
}
static void
@@ -458,7 +479,7 @@ indicator_power_set_devices (IndicatorPower * self, GSList * devices)
g_slist_foreach (devices, (GFunc)g_object_ref, NULL);
dispose_devices (self);
priv->devices = g_slist_copy (devices);
- priv->device = get_primary_device (priv->devices);
+ priv->device = indicator_power_choose_primary_device (devices);
/* and our menus/visibility from the new device list */
if (priv->device != NULL)
@@ -489,6 +510,7 @@ get_label (IndicatorObject *io)
{
/* Create the label if it doesn't exist already */
priv->label = GTK_LABEL (gtk_label_new (""));
+ g_object_ref_sink (priv->label);
gtk_widget_set_visible (GTK_WIDGET (priv->label), FALSE);
}
@@ -508,6 +530,7 @@ get_image (IndicatorObject *io)
gicon = g_themed_icon_new (DEFAULT_ICON);
priv->status_image = GTK_IMAGE (gtk_image_new_from_gicon (gicon,
GTK_ICON_SIZE_LARGE_TOOLBAR));
+ g_object_ref_sink (priv->status_image);
g_object_unref (gicon);
}
diff --git a/src/indicator-power.h b/src/indicator-power.h
index a696b40..34d0d0e 100644
--- a/src/indicator-power.h
+++ b/src/indicator-power.h
@@ -55,4 +55,6 @@ GType indicator_power_get_type (void) G_GNUC_CONST;
void indicator_power_set_devices (IndicatorPower * power,
GSList * devices);
+IndicatorPowerDevice* indicator_power_choose_primary_device (GSList * devices);
+
G_END_DECLS