diff frontends/src/quick_frontend/quick_app.py @ 1331:7fa07c7b0761 frontends_multi_profiles

quick_frontend (quick_app): addListener takes a profiles_filter argument to check the profile before calling a listener (profile must be passed right after the event type in callListeners)
author souliane <souliane@mailoo.org>
date Sun, 22 Feb 2015 20:39:33 +0100
parents f8bd40509a2d
children 0f92b6a150ff
line wrap: on
line diff
--- a/frontends/src/quick_frontend/quick_app.py	Sun Feb 22 11:43:11 2015 +0100
+++ b/frontends/src/quick_frontend/quick_app.py	Sun Feb 22 20:39:33 2015 +0100
@@ -17,17 +17,19 @@
 # You should have received a copy of the GNU Affero General Public License
 # along with this program.  If not, see <http://www.gnu.org/licenses/>.
 
-from sat.core.i18n import _
-import sys
 from sat.core.log import getLogger
 log = getLogger(__name__)
+
+from sat.core.i18n import _
 from sat.core import exceptions
+
 from sat_frontends.tools import jid
 from sat_frontends.quick_frontend.quick_widgets import QuickWidgetsManager
 from sat_frontends.quick_frontend import quick_chat
-
 from sat_frontends.quick_frontend.constants import Const as C
 
+import sys
+from collections import OrderedDict
 
 try:
     # FIXME: to be removed when an acceptable solution is here
@@ -294,17 +296,21 @@
             handler(*args, **kwargs)
         self.bridge.register(functionName, signalReceived, iface)
 
-    def addListener(self, type_, callback):
+    def addListener(self, type_, callback, profiles_filter=None):
         """Add a listener for an event
 
         /!\ don't forget to remove listener when not used anymore (e.g. if you delete a widget)
         @param type_: type of event, can be:
             - avatar: called when avatar data is updated
-                      args: (entity, avatar file, profile)
+                      args: (entity, avatar file)
+            - presence: called when a presence is received
+                         args: (entity, show, priority, statuses)
         @param callback: method to call on event
+        @param profiles_filter (set[unicode]): if set and not empty, the
+            listener will be callable only by one of the given profiles.
         """
         assert type_ in C.LISTENERS
-        self._listeners.setdefault(type_, []).append(callback)
+        self._listeners.setdefault(type_, OrderedDict())[callback] = profiles_filter
 
     def removeListener(self, type_, callback):
         """Remove a callback from listeners
@@ -313,12 +319,15 @@
         @param callback: callback to remove
         """
         assert type_ in C.LISTENERS
-        self._listeners[type_].remove(callback)
+        self._listeners[type_].pop(callback)
 
-    def callListeners(self, type_, *args):
-        """Call all methods which listen of type_ event
+    def callListeners(self, type_, profile, *args):
+        """Call the methods which listen type_ event. If a profiles filter has
+        been register with a listener and profile argument is not None, the
+        listener will be called only if profile is in the profiles filter list.
 
         @param type_: same as for [addListener]
+        @param profile (unicode): %(doc_profile)s
         @param *args: arguments sent to callback
         """
         assert type_ in C.LISTENERS
@@ -327,8 +336,9 @@
         except KeyError:
             pass
         else:
-            for listener in listeners:
-                listener(*args)
+            for listener, profiles_filter in listeners.iteritems():
+                if profile is None or not profiles_filter or profile in profiles_filter:
+                    listener(*args)
 
     def check_profile(self, profile):
         """Tell if the profile is currently followed by the application"""
@@ -463,7 +473,7 @@
         #     self.showAlert(_("Watched jid [%s] is connected !") % entity.bare)
 
         self.contact_lists[profile].updatePresence(entity, show, priority, statuses)
-        self.callListeners('presence', entity, show, priority, statuses, profile)
+        self.callListeners('presence', profile, entity, show, priority, statuses)
 
     def roomJoinedHandler(self, room_jid_s, room_nicks, user_nick, profile):
         """Called when a MUC room is joined"""
@@ -656,7 +666,7 @@
             if entity in self.contact_lists[profile]:
                 def gotFilename(filename):
                     self.contact_lists[profile].setCache(entity, 'avatar', filename)
-                    self.callListeners('avatar', entity, filename, profile)
+                    self.callListeners('avatar', profile, entity, filename)
                 self.bridge.getAvatarFile(value, callback=gotFilename)
 
     def askConfirmationHandler(self, confirm_id, confirm_type, data, profile):