Merge lp:~3v1n0/bamf/lib-factory-xids-matching into lp:bamf/0.4

Proposed by Marco Trevisan (Treviño)
Status: Merged
Approved by: Marco Trevisan (Treviño)
Approved revision: 480
Merged at revision: 462
Proposed branch: lp:~3v1n0/bamf/lib-factory-xids-matching
Merge into: lp:bamf/0.4
Diff against target: 892 lines (+410/-120)
9 files modified
lib/libbamf/Makefile.am (+1/-0)
lib/libbamf/bamf-application-private.h (+30/-0)
lib/libbamf/bamf-application.c (+71/-8)
lib/libbamf/bamf-factory.c (+157/-44)
lib/libbamf/bamf-factory.h (+17/-0)
lib/libbamf/bamf-matcher.c (+68/-38)
lib/libbamf/bamf-view-private.h (+2/-0)
lib/libbamf/bamf-view.c (+62/-29)
lib/libbamf/bamf-window.c (+2/-1)
To merge this branch: bzr merge lp:~3v1n0/bamf/lib-factory-xids-matching
Reviewer Review Type Date Requested Status
Michal Hruby (community) Approve
Review via email: mp+103591@code.launchpad.net

Commit message

BamfFactory: be more smart to re-associate a dbus path to a view using windows xid

Description of the change

BamfFactory has been improved adding the new bamf_factory_view_for_path_type that allows to get a view from a path with the defined type. This allows to avoid (when the type is known) to create a temporary view, only to query via dbus the type of the object.

Also now the factory now has been improved to re-associate the opened views to the new ones using the related windows xids. So basically when a new application has been opened, we initially try to re-associate it to the opened view with the same desktop file; if that check fails we fallback to the children windows xid comparison (if a view has at least a xid that matches the ones of the new application, then we consider them the same).

So, thanks to this both applications with .desktop files associated and applications with no desktop file can be re-used avoiding memory duplication and double launcher icon instances.

Tests covered by: lp:~3v1n0/unity/launcher-double-icons-tests

To post a comment you must log in.
Revision history for this message
Michal Hruby (mhr3) wrote :
Download full text (3.6 KiB)

It seems to be working fine, although it seems to be causing some assertions:

(bamfdaemon:26376): GLib-CRITICAL **: g_str_has_prefix: assertion `str != NULL' failed

Backtrace:

#0 g_log (log_domain=0x7ffff632370e "GLib", log_level=G_LOG_LEVEL_CRITICAL,
    format=0x7ffff632cb2a "%s: assertion `%s' failed")
    at /build/buildd/glib2.0-2.32.1/./glib/gmessages.c:788
#1 0x00007ffff63014f2 in g_str_has_prefix (str=0x0,
    prefix=0x43e931 "libreoffice")
    at /build/buildd/glib2.0-2.32.1/./glib/gstrfuncs.c:2771
#2 0x000000000042f265 in is_open_office_window (window=0x7ac1e0,
    self=<optimized out>)
    at /home/miso-work/unity/source/bamf/src/bamf-matcher.c:1378
#3 handle_window_opened (screen=<optimized out>, window=0x7ac1e0,
    self=0x7861b0) at /home/miso-work/unity/source/bamf/src/bamf-matcher.c:2081
#4 0x00007ffff67b6354 in g_cclosure_marshal_VOID__OBJECTv (closure=0x7b2630,
    return_value=<optimized out>, instance=0x777a80, args=<optimized out>,
    marshal_data=<optimized out>, n_params=<optimized out>,
    param_types=0x79bf50)
    at /build/buildd/glib2.0-2.32.1/./gobject/gmarshal.c:1312
#5 0x00007ffff67b2eca in _g_closure_invoke_va (closure=0x7b2630,
    return_value=0x0, instance=0x777a80, args=0x7fffffffd348, n_params=1,
    param_types=<optimized out>)
    at /build/buildd/glib2.0-2.32.1/./gobject/gclosure.c:840
#6 0x00007ffff67cb741 in g_signal_emit_valist (instance=0x777a80,
    signal_id=<optimized out>, detail=0, var_args=<optimized out>)
---Type <return> to continue, or q <return> to quit---
    at /build/buildd/glib2.0-2.32.1/./gobject/gsignal.c:3207
#7 0x00007ffff67cc242 in g_signal_emit (instance=<optimized out>,
    signal_id=<optimized out>, detail=<optimized out>)
    at /build/buildd/glib2.0-2.32.1/./gobject/gsignal.c:3352
#8 0x00007ffff67b6354 in g_cclosure_marshal_VOID__OBJECTv (closure=0x7b2590,
    return_value=<optimized out>, instance=0x79a390, args=<optimized out>,
    marshal_data=<optimized out>, n_params=<optimized out>,
    param_types=0x7b0f30)
    at /build/buildd/glib2.0-2.32.1/./gobject/gmarshal.c:1312
#9 0x00007ffff67b2eca in _g_closure_invoke_va (closure=0x7b2590,
    return_value=0x0, instance=0x79a390, args=0x7fffffffd718, n_params=1,
    param_types=<optimized out>)
    at /build/buildd/glib2.0-2.32.1/./gobject/gclosure.c:840
#10 0x00007ffff67cb741 in g_signal_emit_valist (instance=0x79a390,
    signal_id=<optimized out>, detail=0, var_args=<optimized out>)
    at /build/buildd/glib2.0-2.32.1/./gobject/gsignal.c:3207
#11 0x00007ffff67cc242 in g_signal_emit (instance=<optimized out>,
    signal_id=<optimized out>, detail=<optimized out>)
    at /build/buildd/glib2.0-2.32.1/./gobject/gsignal.c:3352
#12 0x00007ffff787e339 in ?? () from /usr/lib/libwnck-3.so.0
#13 0x00007ffff787ea24 in ?? () from /usr/lib/libwnck-3.so.0
#14 0x00007ffff62e4c9a in g_main_dispatch (context=0x666a80)
    at /build/buildd/glib2.0-2.32.1/./glib/gmain.c:2515
#15 g_main_context_dispatch (context=0x666a80)
    at /build/buildd/glib2.0-2.32.1/./glib/gmain.c:3052
#16 0x00007ffff62e5060 in g_main_context_iterate (dispatch=1,
    block=<optimized out>, context=0x666a80, self=<optimized out>)
    at ...

Read more...

Revision history for this message
Michal Hruby (mhr3) wrote :

And unity also just complained about:

ERROR 2012-04-26 10:42:25 unity <unknown>:0 on_view_proxy_destroyed: assertion `BAMF_IS_VIEW (view)' failed

Revision history for this message
Michal Hruby (mhr3) wrote :

And one more thing - wouldn't it be better to use an enum in the bamf_factory_view_for_path_type() method?

479. By Marco Trevisan (Treviño)

libbamf, bamfview: disconect to the destroyed signal when needed

480. By Marco Trevisan (Treviño)

BamfFactory: use BamfFactoryViewType instead of strings comparisons when possible.

This cleans the code and is for sure more safe.

Revision history for this message
Marco Trevisan (Treviño) (3v1n0) wrote :

Ok, updated ;)

Revision history for this message
Michal Hruby (mhr3) wrote :

Looking good to me, do we want to have this in SRU1?

review: Approve
Revision history for this message
Marco Trevisan (Treviño) (3v1n0) wrote :

Well... I'd like to.

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'lib/libbamf/Makefile.am'
2--- lib/libbamf/Makefile.am 2012-01-20 15:33:59 +0000
3+++ lib/libbamf/Makefile.am 2012-04-26 17:14:21 +0000
4@@ -40,6 +40,7 @@
5
6 libbamf_la_SOURCES = \
7 bamf-factory.h \
8+ bamf-application-private.h \
9 bamf-view-private.h \
10 $(sources_h) \
11 $(libbamf_sources) \
12
13=== added file 'lib/libbamf/bamf-application-private.h'
14--- lib/libbamf/bamf-application-private.h 1970-01-01 00:00:00 +0000
15+++ lib/libbamf/bamf-application-private.h 2012-04-26 17:14:21 +0000
16@@ -0,0 +1,30 @@
17+/*
18+ * bamf-application-private.h
19+ * This file is part of BAMF
20+ *
21+ * Copyright (C) 2012 - Marco Trevisan (Treviño)
22+ *
23+ * BAMF is free software; you can redistribute it and/or modify
24+ * it under the terms of the GNU General Public License as published by
25+ * the Free Software Foundation; either version 2 of the License, or
26+ * (at your option) any later version.
27+ *
28+ * BAMF is distributed in the hope that it will be useful,
29+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
30+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
31+ * GNU General Public License for more details.
32+ *
33+ * You should have received a copy of the GNU General Public License
34+ * along with BAMF; if not, write to the Free Software
35+ * Foundation, Inc., 51 Franklin St, Fifth Floor,
36+ * Boston, MA 02110-1301 USA
37+ */
38+
39+#ifndef _BAMF_APPLICATION_PRIVATE_H_
40+#define _BAMF_APPLICATION_PRIVATE_H_
41+
42+#include <libbamf/bamf-application.h>
43+
44+GList *bamf_application_get_cached_xids (BamfApplication *app);
45+
46+#endif
47
48=== modified file 'lib/libbamf/bamf-application.c'
49--- lib/libbamf/bamf-application.c 2012-04-10 08:57:06 +0000
50+++ lib/libbamf/bamf-application.c 2012-04-26 17:14:21 +0000
51@@ -37,6 +37,7 @@
52 #include "bamf-application.h"
53 #include "bamf-window.h"
54 #include "bamf-factory.h"
55+#include "bamf-application-private.h"
56 #include "bamf-view-private.h"
57
58 #include <gio/gdesktopappinfo.h>
59@@ -66,6 +67,7 @@
60 DBusGProxy *proxy;
61 gchar *application_type;
62 gchar *desktop_file;
63+ GList *cached_xids;
64 int show_stubs;
65 };
66
67@@ -98,6 +100,12 @@
68 return NULL;
69 }
70
71+ if (file && file[0] == '\0')
72+ {
73+ g_free (file);
74+ file = NULL;
75+ }
76+
77 priv->desktop_file = file;
78 return file;
79 }
80@@ -185,6 +193,7 @@
81 }
82 }
83
84+ g_list_free (children);
85 return windows;
86 }
87
88@@ -238,20 +247,48 @@
89 bamf_application_on_window_added (DBusGProxy *proxy, char *path, BamfApplication *self)
90 {
91 BamfView *view;
92-
93- view = bamf_factory_view_for_path (bamf_factory_get_default (), path);
94-
95- g_signal_emit (G_OBJECT (self), application_signals[WINDOW_ADDED], 0, view);
96+ BamfFactory *factory;
97+
98+ factory = bamf_factory_get_default ();
99+ view = bamf_factory_view_for_path_type (factory, path, BAMF_FACTORY_WINDOW);
100+
101+ if (BAMF_IS_WINDOW (view))
102+ {
103+ guint32 xid = bamf_window_get_xid (BAMF_WINDOW (view));
104+
105+ if (!g_list_find (self->priv->cached_xids, GUINT_TO_POINTER (xid)))
106+ {
107+ self->priv->cached_xids = g_list_prepend (self->priv->cached_xids, GUINT_TO_POINTER (xid));
108+ }
109+
110+ g_signal_emit (G_OBJECT (self), application_signals[WINDOW_ADDED], 0, view);
111+ }
112 }
113
114 static void
115 bamf_application_on_window_removed (DBusGProxy *proxy, char *path, BamfApplication *self)
116 {
117 BamfView *view;
118-
119- view = bamf_factory_view_for_path (bamf_factory_get_default (), path);
120-
121- g_signal_emit (G_OBJECT (self), application_signals[WINDOW_REMOVED], 0, view);
122+ BamfFactory *factory;
123+
124+ factory = bamf_factory_get_default ();
125+ view = bamf_factory_view_for_path_type (factory, path, BAMF_FACTORY_WINDOW);
126+
127+ if (BAMF_IS_WINDOW (view))
128+ {
129+ guint32 xid = bamf_window_get_xid (BAMF_WINDOW (view));
130+ self->priv->cached_xids = g_list_remove (self->priv->cached_xids, GUINT_TO_POINTER (xid));
131+
132+ g_signal_emit (G_OBJECT (self), application_signals[WINDOW_REMOVED], 0, view);
133+ }
134+}
135+
136+GList *
137+bamf_application_get_cached_xids (BamfApplication *self)
138+{
139+ g_return_val_if_fail (BAMF_IS_APPLICATION (self), NULL);
140+
141+ return self->priv->cached_xids;
142 }
143
144 static void
145@@ -291,6 +328,12 @@
146 priv->proxy = NULL;
147 }
148
149+ if (priv->cached_xids)
150+ {
151+ g_list_free (priv->cached_xids);
152+ priv->cached_xids = NULL;
153+ }
154+
155 if (G_OBJECT_CLASS (bamf_application_parent_class)->dispose)
156 G_OBJECT_CLASS (bamf_application_parent_class)->dispose (object);
157 }
158@@ -335,6 +378,26 @@
159 (GCallback) bamf_application_on_window_removed,
160 self,
161 NULL);
162+
163+ GList *children, *l;
164+ children = bamf_view_get_children (view);
165+
166+ if (priv->cached_xids)
167+ {
168+ g_list_free (priv->cached_xids);
169+ priv->cached_xids = NULL;
170+ }
171+
172+ for (l = children; l; l = l->next)
173+ {
174+ if (!BAMF_IS_WINDOW (l->data))
175+ continue;
176+
177+ guint32 xid = bamf_window_get_xid (BAMF_WINDOW (l->data));
178+ priv->cached_xids = g_list_prepend (priv->cached_xids, GUINT_TO_POINTER (xid));
179+ }
180+
181+ g_list_free (children);
182 }
183
184 static void
185
186=== modified file 'lib/libbamf/bamf-factory.c'
187--- lib/libbamf/bamf-factory.c 2012-04-18 12:28:41 +0000
188+++ lib/libbamf/bamf-factory.c 2012-04-26 17:14:21 +0000
189@@ -39,6 +39,7 @@
190 #include "bamf-view-private.h"
191 #include "bamf-window.h"
192 #include "bamf-application.h"
193+#include "bamf-application-private.h"
194 #include "bamf-indicator.h"
195
196 #include <dbus/dbus.h>
197@@ -159,68 +160,181 @@
198 return result;
199 }
200
201-BamfView *
202-bamf_factory_view_for_path (BamfFactory * factory,
203- const char * path)
204+static
205+BamfFactoryViewType compute_factory_type_by_str (const char *type)
206+{
207+ BamfFactoryViewType factory_type = BAMF_FACTORY_NONE;
208+
209+ if (type && type[0] != '\0')
210+ {
211+ if (g_strcmp0 (type, "window") == 0)
212+ {
213+ factory_type = BAMF_FACTORY_WINDOW;
214+ }
215+ else if (g_strcmp0 (type, "application") == 0)
216+ {
217+ factory_type = BAMF_FACTORY_APPLICATION;
218+ }
219+ else if (g_strcmp0 (type, "indicator") == 0)
220+ {
221+ factory_type = BAMF_FACTORY_INDICATOR;
222+ }
223+ else if (g_strcmp0 (type, "view") == 0)
224+ {
225+ factory_type = BAMF_FACTORY_VIEW;
226+ }
227+ }
228+
229+ return factory_type;
230+}
231+
232+BamfView *
233+bamf_factory_view_for_path (BamfFactory * factory, const char * path)
234+{
235+ return bamf_factory_view_for_path_type (factory, path, BAMF_FACTORY_NONE);
236+}
237+
238+BamfView *
239+bamf_factory_view_for_path_type_str (BamfFactory * factory, const char * path,
240+ const char * type)
241+{
242+ g_return_val_if_fail (BAMF_IS_FACTORY (factory), NULL);
243+ BamfFactoryViewType factory_type = compute_factory_type_by_str (type);
244+
245+ return bamf_factory_view_for_path_type (factory, path, factory_type);
246+}
247+
248+BamfView *
249+bamf_factory_view_for_path_type (BamfFactory * factory, const char * path,
250+ BamfFactoryViewType type)
251 {
252 GHashTable *views;
253 BamfView *view;
254 GList *l;
255- gchar *type;
256 gboolean created = FALSE;
257
258 g_return_val_if_fail (BAMF_IS_FACTORY (factory), NULL);
259
260- if (!path || strlen (path) == 0)
261+ if (!path || path[0] == '\0')
262 return NULL;
263
264 views = factory->priv->views;
265-
266 view = g_hash_table_lookup (views, path);
267
268 if (BAMF_IS_VIEW (view))
269 return view;
270-
271- view = g_object_new (BAMF_TYPE_VIEW, NULL);
272- bamf_view_set_path (view, path);
273- type = g_strdup (bamf_view_get_view_type (view));
274- g_object_unref (view);
275-
276- view = NULL;
277- if (g_strcmp0 (type, "application") == 0)
278- view = BAMF_VIEW (bamf_application_new (path));
279- else if (g_strcmp0 (type, "window") == 0)
280- view = BAMF_VIEW (bamf_window_new (path));
281- else if (g_strcmp0 (type, "indicator") == 0)
282- view = BAMF_VIEW (bamf_indicator_new (path));
283-
284+
285+ if (type == BAMF_FACTORY_NONE)
286+ {
287+ view = g_object_new (BAMF_TYPE_VIEW, NULL);
288+ bamf_view_set_path (view, path);
289+ type = compute_factory_type_by_str (bamf_view_get_view_type (view));
290+ g_object_unref (view);
291+ view = NULL;
292+ }
293+
294+ switch (type)
295+ {
296+ case BAMF_FACTORY_VIEW:
297+ view = g_object_new (BAMF_TYPE_VIEW, NULL);
298+ break;
299+ case BAMF_FACTORY_WINDOW:
300+ view = BAMF_VIEW (bamf_window_new (path));
301+ break;
302+ case BAMF_FACTORY_APPLICATION:
303+ view = BAMF_VIEW (bamf_application_new (path));
304+ break;
305+ case BAMF_FACTORY_INDICATOR:
306+ view = BAMF_VIEW (bamf_indicator_new (path));
307+ break;
308+ case BAMF_FACTORY_NONE:
309+ view = NULL;
310+ }
311+
312 created = TRUE;
313-
314+ BamfView *matched_view = NULL;
315+
316 if (BAMF_IS_APPLICATION (view))
317 {
318 /* handle case where a favorite exists and this matches it */
319 const char *local_desktop_file = bamf_application_get_desktop_file (BAMF_APPLICATION (view));
320- for (l = factory->priv->local_views; l; l = l->next)
321- {
322- /* remote ready views are already matched */
323- if (bamf_view_remote_ready (BAMF_VIEW (l->data)) || !BAMF_IS_APPLICATION (l->data))
324- continue;
325-
326- const char *list_desktop_file = bamf_application_get_desktop_file (BAMF_APPLICATION (l->data));
327-
328- if (g_strcmp0 (local_desktop_file, list_desktop_file) == 0)
329- {
330- created = FALSE;
331- g_object_unref (view);
332-
333- view = BAMF_VIEW (l->data);
334- bamf_view_set_path (view, path);
335- g_object_ref_sink (view);
336- break;
337- }
338- }
339- }
340-
341+ GList *local_children = bamf_view_get_children (view);
342+
343+ for (l = factory->priv->local_views; l; l = l->next)
344+ {
345+ if (!BAMF_IS_APPLICATION (l->data))
346+ continue;
347+
348+ BamfView *list_view = BAMF_VIEW (l->data);
349+ BamfApplication *list_app = BAMF_APPLICATION (l->data);
350+
351+ const char *list_desktop_file = bamf_application_get_desktop_file (list_app);
352+
353+ /* We try to match applications by desktop files */
354+ if (local_desktop_file && g_strcmp0 (local_desktop_file, list_desktop_file) == 0)
355+ {
356+ matched_view = list_view;
357+ break;
358+ }
359+
360+ /* If the primary search doesn't give out any result, we fallback
361+ * to children window comparison */
362+ if (!matched_view)
363+ {
364+ GList *list_children, *ll;
365+ list_children = bamf_application_get_cached_xids (list_app);
366+
367+ for (ll = local_children; ll; ll = ll->next)
368+ {
369+ if (!BAMF_IS_WINDOW (ll->data))
370+ continue;
371+
372+ guint32 local_xid = bamf_window_get_xid (BAMF_WINDOW (ll->data));
373+
374+ if (g_list_find (list_children, GUINT_TO_POINTER (local_xid)))
375+ {
376+ matched_view = list_view;
377+ break;
378+ }
379+ }
380+ }
381+ }
382+
383+ g_list_free (local_children);
384+ }
385+ else if (BAMF_IS_WINDOW (view))
386+ {
387+ guint32 local_xid = bamf_window_get_xid (BAMF_WINDOW (view));
388+
389+ for (l = factory->priv->local_views; l; l = l->next)
390+ {
391+ if (!BAMF_IS_WINDOW (l->data))
392+ continue;
393+
394+ BamfView *list_view = BAMF_VIEW (l->data);
395+ BamfWindow *list_win = BAMF_WINDOW (l->data);
396+
397+ guint32 list_xid = bamf_window_get_xid (list_win);
398+
399+ /* We try to match windows by xid */
400+ if (local_xid != 0 && local_xid == list_xid)
401+ {
402+ matched_view = list_view;
403+ break;
404+ }
405+ }
406+ }
407+
408+ if (matched_view)
409+ {
410+ created = FALSE;
411+ g_object_unref (view);
412+
413+ view = matched_view;
414+ bamf_view_set_path (view, path);
415+ g_object_ref_sink (view);
416+ }
417+
418 if (view)
419 {
420 bamf_factory_register_view (factory, view, path);
421@@ -231,8 +345,7 @@
422 g_object_ref_sink (view);
423 }
424 }
425-
426- g_free (type);
427+
428 return view;
429 }
430
431
432=== modified file 'lib/libbamf/bamf-factory.h'
433--- lib/libbamf/bamf-factory.h 2010-10-26 03:48:12 +0000
434+++ lib/libbamf/bamf-factory.h 2012-04-26 17:14:21 +0000
435@@ -54,6 +54,15 @@
436 typedef struct _BamfFactoryClass BamfFactoryClass;
437 typedef struct _BamfFactoryPrivate BamfFactoryPrivate;
438
439+typedef enum
440+{
441+ BAMF_FACTORY_VIEW,
442+ BAMF_FACTORY_WINDOW,
443+ BAMF_FACTORY_APPLICATION,
444+ BAMF_FACTORY_INDICATOR,
445+ BAMF_FACTORY_NONE
446+} BamfFactoryViewType;
447+
448 struct _BamfFactory
449 {
450 GObject parent;
451@@ -71,6 +80,14 @@
452 BamfView * bamf_factory_view_for_path (BamfFactory * factory,
453 const char * path);
454
455+BamfView * bamf_factory_view_for_path_type (BamfFactory * factory,
456+ const char * path,
457+ BamfFactoryViewType type);
458+
459+BamfView * bamf_factory_view_for_path_type_str (BamfFactory * factory,
460+ const char * path,
461+ const char * type);
462+
463 BamfApplication * bamf_factory_app_for_file (BamfFactory * factory,
464 const char * path,
465 gboolean create);
466
467=== modified file 'lib/libbamf/bamf-matcher.c'
468--- lib/libbamf/bamf-matcher.c 2012-04-24 14:14:44 +0000
469+++ lib/libbamf/bamf-matcher.c 2012-04-26 17:14:21 +0000
470@@ -144,8 +144,12 @@
471 BamfMatcher *matcher)
472 {
473 BamfView *view;
474-
475- view = bamf_factory_view_for_path (bamf_factory_get_default (), path);
476+ BamfFactory *factory = bamf_factory_get_default ();
477+
478+ view = bamf_factory_view_for_path_type_str (factory, path, type);
479+
480+ if (!BAMF_IS_VIEW (view))
481+ return;
482
483 g_signal_emit (matcher, matcher_signals[VIEW_OPENED], 0, view);
484 }
485@@ -157,8 +161,9 @@
486 BamfMatcher *matcher)
487 {
488 BamfView *view;
489+ BamfFactory *factory = bamf_factory_get_default ();
490
491- view = bamf_factory_view_for_path (bamf_factory_get_default (), path);
492+ view = bamf_factory_view_for_path_type_str (factory, path, type);
493
494 if (!BAMF_IS_VIEW (view))
495 return;
496@@ -172,14 +177,12 @@
497 char *new_path,
498 BamfMatcher *matcher)
499 {
500- BamfView *old_view = NULL;
501- BamfView *new_view = NULL;
502-
503- if (old_path && strlen (old_path) > 0)
504- old_view = bamf_factory_view_for_path (bamf_factory_get_default (), old_path);
505-
506- if (new_path && strlen (new_path) > 0)
507- new_view = bamf_factory_view_for_path (bamf_factory_get_default (), new_path);
508+ BamfView *old_view;
509+ BamfView *new_view;
510+
511+ BamfFactory *factory = bamf_factory_get_default ();
512+ old_view = bamf_factory_view_for_path_type (factory, old_path, BAMF_FACTORY_APPLICATION);
513+ new_view = bamf_factory_view_for_path_type (factory, new_path, BAMF_FACTORY_APPLICATION);
514
515 g_signal_emit (matcher, matcher_signals[ACTIVE_APPLICATION_CHANGED], 0, old_view, new_view);
516 }
517@@ -190,14 +193,12 @@
518 char *new_path,
519 BamfMatcher *matcher)
520 {
521- BamfView *old_view = NULL;
522- BamfView *new_view = NULL;
523-
524- if (old_path && strlen (old_path) > 0)
525- old_view = bamf_factory_view_for_path (bamf_factory_get_default (), old_path);
526-
527- if (new_path && strlen (new_path) > 0)
528- new_view = bamf_factory_view_for_path (bamf_factory_get_default (), new_path);
529+ BamfView *old_view;
530+ BamfView *new_view;
531+
532+ BamfFactory *factory = bamf_factory_get_default ();
533+ old_view = bamf_factory_view_for_path_type (factory, old_path, BAMF_FACTORY_WINDOW);
534+ new_view = bamf_factory_view_for_path_type (factory, new_path, BAMF_FACTORY_WINDOW);
535
536 g_signal_emit (matcher, matcher_signals[ACTIVE_WINDOW_CHANGED], 0, old_view, new_view);
537 }
538@@ -373,10 +374,17 @@
539 return NULL;
540 }
541
542+ if (app && app[0] == '\0')
543+ {
544+ g_free (app);
545+ return NULL;
546+ }
547+
548 if (!app)
549 return NULL;
550
551- view = bamf_factory_view_for_path (bamf_factory_get_default (), app);
552+ BamfFactory *factory = bamf_factory_get_default ();
553+ view = bamf_factory_view_for_path_type (factory, app, BAMF_FACTORY_APPLICATION);
554 g_free (app);
555
556 if (!BAMF_IS_APPLICATION (view))
557@@ -390,7 +398,7 @@
558 {
559 BamfMatcherPrivate *priv;
560 BamfView *view;
561- char *app = NULL;
562+ char *win = NULL;
563 GError *error = NULL;
564
565 g_return_val_if_fail (BAMF_IS_MATCHER (matcher), NULL);
566@@ -400,7 +408,7 @@
567 "ActiveWindow",
568 &error,
569 G_TYPE_INVALID,
570- G_TYPE_STRING, &app,
571+ G_TYPE_STRING, &win,
572 G_TYPE_INVALID))
573 {
574 g_warning ("Failed to fetch path: %s", error->message);
575@@ -408,11 +416,18 @@
576 return NULL;
577 }
578
579- if (!app)
580+ if (win && win[0] == '\0')
581+ {
582+ g_free (win);
583+ return NULL;
584+ }
585+
586+ if (!win)
587 return NULL;
588
589- view = bamf_factory_view_for_path (bamf_factory_get_default (), app);
590- g_free (app);
591+ BamfFactory *factory = bamf_factory_get_default ();
592+ view = bamf_factory_view_for_path_type (factory, win, BAMF_FACTORY_WINDOW);
593+ g_free (win);
594
595 if (!BAMF_IS_WINDOW (view))
596 return NULL;
597@@ -455,10 +470,17 @@
598 return NULL;
599 }
600
601+ if (app && app[0] == '\0')
602+ {
603+ g_free (app);
604+ return NULL;
605+ }
606+
607 if (!app)
608 return NULL;
609
610- view = bamf_factory_view_for_path (bamf_factory_get_default (), app);
611+ BamfFactory *factory = bamf_factory_get_default ();
612+ view = bamf_factory_view_for_path_type (factory, app, BAMF_FACTORY_APPLICATION);
613
614 g_free (app);
615
616@@ -522,14 +544,16 @@
617 return NULL;
618 }
619
620- g_return_val_if_fail (array, NULL);
621+ if (!array)
622+ return NULL;
623
624+ BamfFactory *factory = bamf_factory_get_default ();
625 len = g_strv_length (array);
626 for (i = len-1; i >= 0; i--)
627 {
628- view = bamf_factory_view_for_path (bamf_factory_get_default (), array[i]);
629+ view = bamf_factory_view_for_path_type (factory, array[i], BAMF_FACTORY_APPLICATION);
630
631- if (view)
632+ if (BAMF_IS_APPLICATION (view))
633 result = g_list_prepend (result, view);
634 }
635
636@@ -563,14 +587,16 @@
637 return NULL;
638 }
639
640- g_return_val_if_fail (array, NULL);
641+ if (!array)
642+ return NULL;
643
644+ BamfFactory *factory = bamf_factory_get_default ();
645 len = g_strv_length (array);
646 for (i = len-1; i >= 0; i--)
647 {
648- view = bamf_factory_view_for_path (bamf_factory_get_default (), array[i]);
649+ view = bamf_factory_view_for_path_type (factory, array[i], BAMF_FACTORY_WINDOW);
650
651- if (view)
652+ if (BAMF_IS_WINDOW (view))
653 result = g_list_prepend (result, view);
654 }
655
656@@ -606,14 +632,16 @@
657 return NULL;
658 }
659
660- g_return_val_if_fail (array, NULL);
661+ if (!array)
662+ return NULL;
663
664+ BamfFactory *factory = bamf_factory_get_default ();
665 len = g_strv_length (array);
666 for (i = len-1; i >= 0; i--)
667 {
668- view = bamf_factory_view_for_path (bamf_factory_get_default (), array[i]);
669+ view = bamf_factory_view_for_path_type (factory, array[i], BAMF_FACTORY_WINDOW);
670
671- if (view)
672+ if (BAMF_IS_WINDOW (view))
673 result = g_list_prepend (result, view);
674 }
675
676@@ -664,14 +692,16 @@
677 return NULL;
678 }
679
680- g_return_val_if_fail (array, NULL);
681+ if (!array)
682+ return NULL;
683
684+ BamfFactory *factory = bamf_factory_get_default ();
685 len = g_strv_length (array);
686 for (i = len-1; i >= 0; i--)
687 {
688- view = bamf_factory_view_for_path (bamf_factory_get_default (), array[i]);
689+ view = bamf_factory_view_for_path_type (factory, array[i], BAMF_FACTORY_APPLICATION);
690
691- if (view)
692+ if (BAMF_IS_APPLICATION (view))
693 result = g_list_prepend (result, view);
694 }
695
696
697=== modified file 'lib/libbamf/bamf-view-private.h'
698--- lib/libbamf/bamf-view-private.h 2010-11-01 05:07:11 +0000
699+++ lib/libbamf/bamf-view-private.h 2012-04-26 17:14:21 +0000
700@@ -31,6 +31,8 @@
701
702 gboolean bamf_view_remote_ready (BamfView *view);
703
704+void bamf_view_reset_flags (BamfView *view);
705+
706 void bamf_view_set_name (BamfView *view, const char *name);
707
708 void bamf_view_set_icon (BamfView *view, const char *icon);
709
710=== modified file 'lib/libbamf/bamf-view.c'
711--- lib/libbamf/bamf-view.c 2012-04-22 15:10:47 +0000
712+++ lib/libbamf/bamf-view.c 2012-04-26 17:14:21 +0000
713@@ -111,7 +111,7 @@
714 if (value)
715 priv->set_flags |= flag;
716 else
717- priv->set_flags = priv->set_flags & ~flag;
718+ priv->set_flags &= ~flag;
719
720 priv->checked_flags |= flag;
721 }
722@@ -386,7 +386,7 @@
723 return BAMF_VIEW_GET_CLASS (self)->get_name (self);
724
725 if (!bamf_view_remote_ready (self))
726- return g_strdup(priv->local_name);
727+ return g_strdup (priv->local_name);
728
729 if (!dbus_g_proxy_call (priv->proxy,
730 "Name",
731@@ -439,7 +439,7 @@
732 G_TYPE_STRING, &type,
733 G_TYPE_INVALID))
734 {
735- g_warning ("Failed to fetch view type at %s: %s", dbus_g_proxy_get_path (priv->proxy), error->message);
736+ g_warning ("Failed to fetch view type at %s: %s", dbus_g_proxy_get_path (priv->proxy), error ? error->message : "");
737 g_error_free (error);
738 return NULL;
739 }
740@@ -543,6 +543,16 @@
741 }
742
743 static void
744+on_view_proxy_destroyed (GObject *proxy, gpointer user_data)
745+{
746+ BamfView *view = user_data;
747+ g_return_if_fail (BAMF_IS_VIEW (view));
748+
749+ view->priv->checked_flags = 0x0;
750+ view->priv->proxy = NULL;
751+}
752+
753+static void
754 bamf_view_on_closed (DBusGProxy *proxy, BamfView *self)
755 {
756 BamfViewPrivate *priv;
757@@ -593,6 +603,8 @@
758 "UserVisibleChanged",
759 (GCallback) bamf_view_on_user_visible_changed,
760 self);
761+
762+ g_signal_handlers_disconnect_by_func (priv->proxy, on_view_proxy_destroyed, self);
763 g_object_unref (priv->proxy);
764 priv->proxy = NULL;
765 }
766@@ -737,6 +749,7 @@
767 (GCallback) bamf_view_on_name_changed,
768 view);
769
770+ g_signal_handlers_disconnect_by_func (priv->proxy, on_view_proxy_destroyed, view);
771 g_object_unref (priv->proxy);
772 priv->proxy = NULL;
773 }
774@@ -753,6 +766,40 @@
775 }
776
777 void
778+bamf_view_reset_flags (BamfView *view)
779+{
780+ BamfViewPrivate *priv;
781+ g_return_if_fail (BAMF_IS_VIEW (view));
782+
783+ priv = view->priv;
784+ priv->checked_flags = 0x0;
785+
786+ if (bamf_view_user_visible (view))
787+ {
788+ g_signal_emit (G_OBJECT(view), view_signals[VISIBLE_CHANGED], 0, TRUE);
789+ g_object_notify (G_OBJECT (view), "user-visible");
790+ }
791+
792+ if (bamf_view_is_active (view))
793+ {
794+ g_signal_emit (G_OBJECT(view), view_signals[ACTIVE_CHANGED], 0, TRUE);
795+ g_object_notify (G_OBJECT (view), "active");
796+ }
797+
798+ if (bamf_view_is_running (view))
799+ {
800+ g_signal_emit (G_OBJECT(view), view_signals[RUNNING_CHANGED], 0, TRUE);
801+ g_object_notify (G_OBJECT (view), "running");
802+ }
803+
804+ if (bamf_view_is_urgent (view))
805+ {
806+ g_signal_emit (G_OBJECT(view), view_signals[URGENT_CHANGED], 0, TRUE);
807+ g_object_notify (G_OBJECT (view), "urgent");
808+ }
809+}
810+
811+void
812 bamf_view_set_path (BamfView *view, const char *path)
813 {
814 BamfViewPrivate *priv;
815@@ -766,18 +813,27 @@
816 {
817 g_free (priv->path);
818 }
819-
820+
821+ if (priv->proxy)
822+ {
823+ g_signal_handlers_disconnect_by_func (priv->proxy, on_view_proxy_destroyed, view);
824+ g_object_unref (priv->proxy);
825+ }
826+
827 priv->path = g_strdup (path);
828 priv->proxy = dbus_g_proxy_new_for_name (priv->connection,
829 "org.ayatana.bamf",
830 priv->path,
831 "org.ayatana.bamf.view");
832+
833 if (priv->proxy == NULL)
834 {
835 g_critical ("Unable to get org.ayatana.bamf.view view");
836 return;
837 }
838
839+ g_signal_connect (priv->proxy, "destroy", G_CALLBACK (on_view_proxy_destroyed), view);
840+
841 dbus_g_proxy_add_signal (priv->proxy,
842 "ActiveChanged",
843 G_TYPE_BOOLEAN,
844@@ -868,32 +924,9 @@
845
846 if (bamf_view_is_sticky (view))
847 {
848- priv->checked_flags = 0x0;
849-
850- if (bamf_view_user_visible (view))
851- {
852- g_signal_emit (G_OBJECT(view), view_signals[VISIBLE_CHANGED], 0, TRUE);
853- g_object_notify (G_OBJECT (view), "user-visible");
854- }
855-
856- if (bamf_view_is_active (view))
857- {
858- g_signal_emit (G_OBJECT(view), view_signals[ACTIVE_CHANGED], 0, TRUE);
859- g_object_notify (G_OBJECT (view), "active");
860- }
861-
862- if (bamf_view_is_running (view))
863- {
864- g_signal_emit (G_OBJECT(view), view_signals[RUNNING_CHANGED], 0, TRUE);
865- g_object_notify (G_OBJECT (view), "running");
866- }
867-
868- if (bamf_view_is_urgent (view))
869- {
870- g_signal_emit (G_OBJECT(view), view_signals[URGENT_CHANGED], 0, TRUE);
871- g_object_notify (G_OBJECT (view), "urgent");
872- }
873+ bamf_view_reset_flags (view);
874 }
875+
876 if (BAMF_VIEW_GET_CLASS (view)->set_path)
877 BAMF_VIEW_GET_CLASS (view)->set_path (view, path);
878 }
879
880=== modified file 'lib/libbamf/bamf-window.c'
881--- lib/libbamf/bamf-window.c 2012-02-27 18:34:30 +0000
882+++ lib/libbamf/bamf-window.c 2012-04-26 17:14:21 +0000
883@@ -103,7 +103,8 @@
884 if (!path)
885 return NULL;
886
887- transient = bamf_factory_view_for_path (bamf_factory_get_default (), path);
888+ BamfFactory *factory = bamf_factory_get_default ();
889+ transient = bamf_factory_view_for_path_type (factory, path, BAMF_FACTORY_WINDOW);
890 g_free (path);
891
892 if (!BAMF_IS_WINDOW (transient))

Subscribers

People subscribed via source and target branches