Merge lp:~gordallott/unity/unity.fix-bg-hash-crashers into lp:unity

Proposed by Gord Allott
Status: Merged
Approved by: Gord Allott
Approved revision: no longer in the source branch.
Merged at revision: 1385
Proposed branch: lp:~gordallott/unity/unity.fix-bg-hash-crashers
Merge into: lp:unity
Diff against target: 414 lines (+165/-101)
3 files modified
plugins/unityshell/src/BGHash.cpp (+148/-96)
plugins/unityshell/src/BGHash.h (+9/-1)
tests/TestBGHash.cpp (+8/-4)
To merge this branch: bzr merge lp:~gordallott/unity/unity.fix-bg-hash-crashers
Reviewer Review Type Date Requested Status
Sam Spilsbury (community) Approve
Review via email: mp+72020@code.launchpad.net

Description of the change

Fixes a few (hopefully linked) bugs in the bghash code, the race seems to be fixed on my machine as well as the crazy alpha problem, segfaults should be gone too

To post a comment you must log in.
Revision history for this message
Sam Spilsbury (smspillaz) wrote :

Looks good to me

review: Approve

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
=== modified file 'plugins/unityshell/src/BGHash.cpp'
--- plugins/unityshell/src/BGHash.cpp 2011-08-12 04:16:44 +0000
+++ plugins/unityshell/src/BGHash.cpp 2011-08-18 11:16:32 +0000
@@ -18,6 +18,7 @@
1818
19#include "BGHash.h"19#include "BGHash.h"
20#include <Nux/Nux.h>20#include <Nux/Nux.h>
21#include <NuxCore/Logger.h>
21#include <gdk-pixbuf/gdk-pixbuf.h>22#include <gdk-pixbuf/gdk-pixbuf.h>
22#include <libgnome-desktop/gnome-bg.h>23#include <libgnome-desktop/gnome-bg.h>
23#include <unity-misc/gnome-bg-slideshow.h>24#include <unity-misc/gnome-bg-slideshow.h>
@@ -25,6 +26,11 @@
25#include "UBusMessages.h"26#include "UBusMessages.h"
26#include "UnityCore/GLibWrapper.h"27#include "UnityCore/GLibWrapper.h"
2728
29namespace
30{
31 nux::logging::Logger logger("unity.BGHash");
32}
33
28namespace {34namespace {
29 int level_of_recursion;35 int level_of_recursion;
30 const int MAX_LEVEL_OF_RECURSION = 16;36 const int MAX_LEVEL_OF_RECURSION = 16;
@@ -37,9 +43,9 @@
37 _bg_slideshow (NULL),43 _bg_slideshow (NULL),
38 _current_slide (NULL),44 _current_slide (NULL),
39 _slideshow_handler(0),45 _slideshow_handler(0),
40 _current_color (nux::color::DimGray),46 _current_color (unity::colors::Aubergine),
41 _new_color (nux::color::DimGray),47 _new_color (unity::colors::Aubergine),
42 _old_color (nux::color::DimGray),48 _old_color (unity::colors::Aubergine),
43 _hires_time_start(10),49 _hires_time_start(10),
44 _hires_time_end(20),50 _hires_time_end(20),
45 _ubus_handle_request_colour(0)51 _ubus_handle_request_colour(0)
@@ -47,9 +53,6 @@
47 background_monitor = gnome_bg_new ();53 background_monitor = gnome_bg_new ();
48 client = g_settings_new ("org.gnome.desktop.background");54 client = g_settings_new ("org.gnome.desktop.background");
4955
50 glib::Object<GdkPixbuf> pixbuf(GetPixbufFromBG());
51 LoadPixbufToHash(pixbuf);
52
53 signal_manager_.Add(56 signal_manager_.Add(
54 new glib::Signal<void, GnomeBG*>(background_monitor,57 new glib::Signal<void, GnomeBG*>(background_monitor,
55 "changed",58 "changed",
@@ -64,6 +67,9 @@
6467
65 gnome_bg_load_from_preferences (background_monitor, client);68 gnome_bg_load_from_preferences (background_monitor, client);
6669
70 glib::Object<GdkPixbuf> pixbuf(GetPixbufFromBG());
71 LoadPixbufToHash(pixbuf);
72
67 g_timeout_add (0, (GSourceFunc)ForceUpdate, (gpointer)this);73 g_timeout_add (0, (GSourceFunc)ForceUpdate, (gpointer)this);
6874
69 // avoids making a new object method when all we are doing is75 // avoids making a new object method when all we are doing is
@@ -90,7 +96,7 @@
90 gboolean BGHash::ForceUpdate (BGHash *self)96 gboolean BGHash::ForceUpdate (BGHash *self)
91 {97 {
92 self->OnBackgroundChanged(self->background_monitor);98 self->OnBackgroundChanged(self->background_monitor);
93 return FALSE; 99 return FALSE;
94 }100 }
95101
96 void BGHash::OnGSettingsChanged (GSettings *settings, gchar *key)102 void BGHash::OnGSettingsChanged (GSettings *settings, gchar *key)
@@ -101,98 +107,135 @@
101 void BGHash::OnBackgroundChanged (GnomeBG *bg)107 void BGHash::OnBackgroundChanged (GnomeBG *bg)
102 {108 {
103 const gchar *filename = gnome_bg_get_filename (bg);109 const gchar *filename = gnome_bg_get_filename (bg);
104 if (_bg_slideshow != NULL)110 if (filename == NULL)
105 {111 {
106 slideshow_unref (_bg_slideshow);112 // we might have a gradient instead
107 _bg_slideshow = NULL;113 GdkColor color_primary, color_secondary;
108 _current_slide = NULL;114 GDesktopBackgroundShading shading_type;
109 }115 nux::Color parsed_color;
110116
111 if (_slideshow_handler)117 gnome_bg_get_color (bg, &shading_type, &color_primary, &color_secondary);
112 {118 if (shading_type == G_DESKTOP_BACKGROUND_SHADING_HORIZONTAL ||
113 g_source_remove (_slideshow_handler);119 shading_type == G_DESKTOP_BACKGROUND_SHADING_SOLID)
114 _slideshow_handler = 0;120 {
115 }121 parsed_color = nux::Color(static_cast<float>(color_primary.red) / 65535,
116122 static_cast<float>(color_primary.green) / 65535,
117 if (g_str_has_suffix (filename, "xml"))123 static_cast<float>(color_primary.blue) / 65535,
118 {124 1.0f);
119 GError *error = NULL;125 }
120126 else
127 {
128 nux::Color primary = nux::Color(static_cast<float>(color_primary.red) / 65535,
129 static_cast<float>(color_primary.green) / 65535,
130 static_cast<float>(color_primary.blue) / 65535,
131 1.0f);
132
133 nux::Color secondary = nux::Color(static_cast<float>(color_secondary.red) / 65535,
134 static_cast<float>(color_secondary.green) / 65535,
135 static_cast<float>(color_secondary.blue) / 65535,
136 1.0f);
137
138 parsed_color = (primary + secondary) * 0.5f;
139 }
140
141 nux::Color new_color = MatchColor (parsed_color);
142 TransitionToNewColor (new_color);
143 }
144 else
145 {
121 if (_bg_slideshow != NULL)146 if (_bg_slideshow != NULL)
122 {147 {
123 slideshow_unref (_bg_slideshow);148 slideshow_unref (_bg_slideshow);
124 _bg_slideshow = NULL;149 _bg_slideshow = NULL;
125 }150 _current_slide = NULL;
126151 }
127 _bg_slideshow = read_slideshow_file (filename, &error);152
128153 if (_slideshow_handler)
129 if (error != NULL)154 {
130 {155 g_source_remove (_slideshow_handler);
131 g_warning ("BGHash.cpp: could not load filename %s: %s", filename, error->message);156 _slideshow_handler = 0;
132 g_error_free (error);157 }
133 }158
134 else if (_bg_slideshow == NULL)159 if (g_str_has_suffix (filename, "xml"))
135 {160 {
136 g_warning ("BGHash.cpp: could not load filename %s", filename);161 GError *error = NULL;
137 }162
138 else163 if (_bg_slideshow != NULL)
139 {164 {
140 // we loaded fine, hook up to the slideshow165 slideshow_unref (_bg_slideshow);
141 time_t current_time = time(0);166 _bg_slideshow = NULL;
142 double now = (double) current_time;167 }
143168
144 double time_diff = now - _bg_slideshow->start_time;169 _bg_slideshow = read_slideshow_file (filename, &error);
145 double progress = fmod (time_diff, _bg_slideshow->total_duration);170
146171 if (error != NULL)
147 // progress now holds how many seconds we are in to this slideshow.172 {
148 // iterate over the slideshows until we get in to the current slideshow173 LOG_WARNING(logger) << "Could not load filename \"" << filename << "\": " << error->message;
149 Slide *slide_iteration;174 g_error_free (error);
150 Slide *slide_current = NULL;175 }
151 double elapsed = 0;176 else if (_bg_slideshow == NULL)
152 double time_to_next_change = 0;177 {
153 GList *list;178 LOG_WARNING(logger) << "Could not load filename \"" << filename << "\"";
154
155 for (list = _bg_slideshow->slides->head; list != NULL; list = list->next)
156 {
157 slide_iteration = reinterpret_cast<Slide *>(list->data);
158 if (elapsed + slide_iteration->duration > progress)
159 {
160 slide_current = slide_iteration;
161 time_to_next_change = slide_current->duration- (progress - elapsed);
162 break;
163 }
164
165 elapsed += slide_iteration->duration;
166 }
167
168 if (slide_current == NULL)
169 {
170 slide_current = reinterpret_cast<Slide *>(g_queue_peek_head(_bg_slideshow->slides));
171 time_to_next_change = slide_current->duration;
172 }
173
174 // time_to_next_change now holds the seconds until the next slide change
175 // the next slide change may or may not be a fixed slide.
176 _slideshow_handler = g_timeout_add ((guint)(time_to_next_change * 1000),
177 (GSourceFunc)OnSlideshowTransition,
178 (gpointer)this);
179
180 // find our current slide now
181 if (slide_current->file1 == NULL)
182 {
183 g_warning ("BGHash.cpp: could not load filename %s - slide has no filename", filename);
184 }179 }
185 else180 else
186 {181 {
187 FileSize *fs = reinterpret_cast<FileSize *>(slide_current->file1->data);182 // we loaded fine, hook up to the slideshow
188 filename = reinterpret_cast<gchar *>(fs->file);183 time_t current_time = time(0);
184 double now = (double) current_time;
185
186 double time_diff = now - _bg_slideshow->start_time;
187 double progress = fmod (time_diff, _bg_slideshow->total_duration);
188
189 // progress now holds how many seconds we are in to this slideshow.
190 // iterate over the slideshows until we get in to the current slideshow
191 Slide *slide_iteration;
192 Slide *slide_current = NULL;
193 double elapsed = 0;
194 double time_to_next_change = 0;
195 GList *list;
196
197 for (list = _bg_slideshow->slides->head; list != NULL; list = list->next)
198 {
199 slide_iteration = reinterpret_cast<Slide *>(list->data);
200 if (elapsed + slide_iteration->duration > progress)
201 {
202 slide_current = slide_iteration;
203 time_to_next_change = slide_current->duration- (progress - elapsed);
204 break;
205 }
206
207 elapsed += slide_iteration->duration;
208 }
209
210 if (slide_current == NULL)
211 {
212 slide_current = reinterpret_cast<Slide *>(g_queue_peek_head(_bg_slideshow->slides));
213 time_to_next_change = slide_current->duration;
214 }
215
216 // time_to_next_change now holds the seconds until the next slide change
217 // the next slide change may or may not be a fixed slide.
218 _slideshow_handler = g_timeout_add ((guint)(time_to_next_change * 1000),
219 (GSourceFunc)OnSlideshowTransition,
220 (gpointer)this);
221
222 // find our current slide now
223 if (slide_current->file1 == NULL)
224 {
225 LOG_WARNING(logger) << "Could not load filename \"" << filename << "\"";
226 }
227 else
228 {
229 FileSize *fs = reinterpret_cast<FileSize *>(slide_current->file1->data);
230 filename = reinterpret_cast<gchar *>(fs->file);
231 }
232
233 _current_slide = slide_current;
189 }234 }
190
191 _current_slide = slide_current;
192 }235 }
236
237 LoadFileToHash(filename);
193 }238 }
194
195 LoadFileToHash(filename);
196 }239 }
197240
198 gboolean BGHash::OnSlideshowTransition (BGHash *self)241 gboolean BGHash::OnSlideshowTransition (BGHash *self)
@@ -235,7 +278,7 @@
235 const gchar *filename = NULL;278 const gchar *filename = NULL;
236 if (proposed_slide->file1 == NULL)279 if (proposed_slide->file1 == NULL)
237 {280 {
238 g_warning ("BGHash.cpp: could not load filename %s - slide has no filename", filename);281 LOG_WARNING(logger) << "Could not load filename \"" << filename << "\"";
239 }282 }
240 else283 else
241 {284 {
@@ -310,7 +353,7 @@
310 _current_color.red * 0.7f,353 _current_color.red * 0.7f,
311 _current_color.green * 0.7f,354 _current_color.green * 0.7f,
312 _current_color.blue * 0.7f,355 _current_color.blue * 0.7f,
313 _current_color.alpha)356 0.5)
314 );357 );
315 }358 }
316359
@@ -336,10 +379,17 @@
336379
337 void BGHash::LoadPixbufToHash(GdkPixbuf *pixbuf)380 void BGHash::LoadPixbufToHash(GdkPixbuf *pixbuf)
338 {381 {
382 nux::Color new_color;
339 if (pixbuf == NULL)383 if (pixbuf == NULL)
340 return;384 {
385 LOG_WARNING(logger) << "Passed in a bad pixbuf, defaulting colour";
386 new_color = unity::colors::Aubergine;
387 }
388 else
389 {
390 new_color = HashColor (pixbuf);
391 }
341392
342 nux::Color new_color = HashColor (pixbuf);
343 TransitionToNewColor (new_color);393 TransitionToNewColor (new_color);
344 }394 }
345395
@@ -350,8 +400,12 @@
350400
351 if (error)401 if (error)
352 {402 {
403 LOG_WARNING(logger) << "Could not load filename \"" << path << "\": " << error.Message();
353 _current_color = nux::Color(0.2, 0.2, 0.2, 0.9);404 _current_color = nux::Color(0.2, 0.2, 0.2, 0.9);
354 return;405
406 // try and get a colour from gnome-bg, for various reasons, gnome bg might not
407 // return a correct image which sucks =\ but this is a fallback
408 pixbuf = GetPixbufFromBG();
355 }409 }
356410
357 LoadPixbufToHash (pixbuf);411 LoadPixbufToHash (pixbuf);
@@ -507,8 +561,6 @@
507 // apply design to the colour561 // apply design to the colour
508 chosen_color.alpha = 0.5f;562 chosen_color.alpha = 0.5f;
509563
510
511
512 return chosen_color;564 return chosen_color;
513 }565 }
514566
515567
=== modified file 'plugins/unityshell/src/BGHash.h'
--- plugins/unityshell/src/BGHash.h 2011-08-11 16:47:44 +0000
+++ plugins/unityshell/src/BGHash.h 2011-08-18 11:16:32 +0000
@@ -25,11 +25,19 @@
25#include <unity-misc/gnome-bg-slideshow.h>25#include <unity-misc/gnome-bg-slideshow.h>
26#include <UnityCore/GLibSignal.h>26#include <UnityCore/GLibSignal.h>
2727
28namespace unity {
29namespace colors {
30 const nux::Color Aubergine(0x3E, 0x20, 0x60);
31};
32};
33
28namespace unity34namespace unity
29{35{
30 class BGHash36 class BGHash
31 {37 {
32 public:38 public:
39
40
33 BGHash ();41 BGHash ();
34 ~BGHash ();42 ~BGHash ();
3543
@@ -67,7 +75,7 @@
6775
68 guint64 _hires_time_start;76 guint64 _hires_time_start;
69 guint64 _hires_time_end;77 guint64 _hires_time_end;
70 glib::SignalManager signal_manager_; 78 glib::SignalManager signal_manager_;
71 uint _ubus_handle_request_colour;79 uint _ubus_handle_request_colour;
72 };80 };
73};81};
7482
=== modified file 'tests/TestBGHash.cpp'
--- tests/TestBGHash.cpp 2011-07-28 11:02:56 +0000
+++ tests/TestBGHash.cpp 2011-08-18 11:16:32 +0000
@@ -16,9 +16,10 @@
16 *16 *
17 * Authored by: Gordon Allott <gord.allott@canonical.com>17 * Authored by: Gordon Allott <gord.allott@canonical.com>
18 */18 */
19#include "Nux/Nux.h"19#include <Nux/Nux.h>
20#include "Nux/WindowThread.h"20#include <NuxCore/Logger.h>
21#include "NuxGraphics/GraphicsEngine.h"21#include <Nux/WindowThread.h>
22#include <NuxGraphics/GraphicsEngine.h>
22#include <gtk/gtk.h>23#include <gtk/gtk.h>
2324
24#include "BGHash.h"25#include "BGHash.h"
@@ -84,7 +85,7 @@
84int main(int argc, char **argv)85int main(int argc, char **argv)
85{86{
86 UBusServer *ubus;87 UBusServer *ubus;
87 unity::BGHash bg_hash;88
88 nux::SystemThread* st = NULL;89 nux::SystemThread* st = NULL;
89 nux::WindowThread* wt = NULL;90 nux::WindowThread* wt = NULL;
9091
@@ -97,6 +98,9 @@
97 gtk_init (&argc, &argv);98 gtk_init (&argc, &argv);
9899
99 nux::NuxInitialize(0);100 nux::NuxInitialize(0);
101 nux::logging::configure_logging(::getenv("UNITY_LOG_SEVERITY"));
102
103 unity::BGHash bg_hash;
100104
101 ubus = ubus_server_get_default ();105 ubus = ubus_server_get_default ();
102 ubus_server_register_interest (ubus, UBUS_BACKGROUND_COLOR_CHANGED,106 ubus_server_register_interest (ubus, UBUS_BACKGROUND_COLOR_CHANGED,