Mercurial > libervia-backend
annotate frontends/src/wix/contact_list.py @ 297:c5554e2939dd
plugin XEP 0277: author for in request + author, updated management for out request
- a workaround is now used to parse "nick" tag (Jappix behaviour)
- author and updated can now be used in data when sendind microblog. Is no author is given, user jid is used, if no updated is given, current timestamp is used
author | Goffi <goffi@goffi.org> |
---|---|
date | Fri, 18 Feb 2011 22:32:02 +0100 |
parents | b1794cbb88e5 |
children | 3a21d586dae4 |
rev | line source |
---|---|
227 | 1 #!/usr/bin/python |
2 # -*- coding: utf-8 -*- | |
3 | |
4 """ | |
5 wix: a SAT frontend | |
228 | 6 Copyright (C) 2009, 2010, 2011 Jérôme Poisson (goffi@goffi.org) |
227 | 7 |
8 This program is free software: you can redistribute it and/or modify | |
9 it under the terms of the GNU General Public License as published by | |
10 the Free Software Foundation, either version 3 of the License, or | |
11 (at your option) any later version. | |
12 | |
13 This program is distributed in the hope that it will be useful, | |
14 but WITHOUT ANY WARRANTY; without even the implied warranty of | |
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
16 GNU General Public License for more details. | |
17 | |
18 You should have received a copy of the GNU General Public License | |
19 along with this program. If not, see <http://www.gnu.org/licenses/>. | |
20 """ | |
21 | |
72 | 22 import wx |
227 | 23 from sat_frontends.quick_frontend.quick_contact_list import QuickContactList |
72 | 24 from logging import debug, info, error |
25 from cgi import escape | |
225
fd9b7834d98a
distutils installation script, draft
Goffi <goffi@goffi.org>
parents:
223
diff
changeset
|
26 from sat.tools.jid import JID |
72 | 27 |
28 | |
199 | 29 class Group(unicode): |
72 | 30 """Class used to recognize groups""" |
31 | |
199 | 32 class Contact(unicode): |
72 | 33 """Class used to recognize groups""" |
34 | |
35 class ContactList(wx.SimpleHtmlListBox, QuickContactList): | |
36 """Customized control to manage contacts.""" | |
37 | |
38 def __init__(self, parent, host, type="JID"): | |
39 """init the contact list | |
40 @param parent: WxWidgets parent of the widget | |
41 @param host: wix main app class | |
42 @param type: type of contact list: "JID" for the usual big jid contact list | |
43 "CUSTOM" for a customized contact list (self.__presentItem must then be overrided) | |
44 """ | |
45 wx.SimpleHtmlListBox.__init__(self, parent, -1) | |
46 QuickContactList.__init__(self, host.CM) | |
47 self.host = host | |
48 self.type = type | |
49 self.__typeSwitch() | |
50 self.groups = {} #list contacts in each groups, key = group | |
51 self.Bind(wx.EVT_LISTBOX, self.onSelected) | |
52 self.Bind(wx.EVT_LISTBOX_DCLICK, self.onActivated) | |
124 | 53 |
54 def __contains__(self, jid): | |
55 return bool(self.__find_idx(jid)) | |
72 | 56 |
57 def __typeSwitch(self): | |
58 if self.type == "JID": | |
59 self.__presentItem = self.__presentItemJID | |
60 elif type != "CUSTOM": | |
61 self.__presentItem = self.__presentItemDefault | |
62 | |
63 def __find_idx(self, entity): | |
64 """Find indexes of given contact (or groups) in contact list, manage jid | |
65 @return: list of indexes""" | |
66 result=[] | |
67 for i in range(self.GetCount()): | |
68 if (type(entity) == JID and type(self.GetClientData(i)) == JID and self.GetClientData(i).short == entity.short) or\ | |
69 self.GetClientData(i) == entity: | |
70 result.append(i) | |
71 return result | |
72 | |
73 def replace(self, contact, groups=None): | |
74 debug(_("update %s") % contact) | |
75 if not self.__find_idx(contact): | |
76 self.add(contact, groups) | |
77 else: | |
78 for i in self.__find_idx(contact): | |
79 self.SetString(i, self.__presentItem(contact)) | |
80 | |
81 def disconnect(self, contact): | |
82 self.remove(contact) #for now, we only show online contacts | |
83 | |
84 def __eraseGroup(self, group): | |
85 """Erase all contacts in group | |
86 @param group: group to erase | |
87 @return: True if something as been erased""" | |
88 erased = False | |
89 indexes = self.__find_idx(group) | |
90 for idx in indexes: | |
91 while idx<self.GetCount()-1 and type(self.GetClientData(idx+1)) != Group: | |
92 erased = True | |
93 self.Delete(idx+1) | |
94 return erased | |
95 | |
96 | |
97 def __presentGroup(self, group): | |
98 """Make a nice presentation for the contact groups""" | |
199 | 99 html = u"""-- [%s] --""" % group |
72 | 100 |
101 return html | |
102 | |
103 def __presentItemDefault(self, contact): | |
104 """Make a basic presentation of string contacts in the list.""" | |
105 return contact | |
106 | |
107 def __presentItemJID(self, jid): | |
108 """Make a nice presentation of the contact in the list for JID contacts.""" | |
109 name = self.CM.getAttr(jid,'name') | |
110 nick = self.CM.getAttr(jid,'nick') | |
111 show = filter(lambda x:x[0]==self.CM.getAttr(jid,'show'), const_STATUS)[0] | |
112 #show[0]==shortcut | |
113 #show[1]==human readable | |
114 #show[2]==color (or None) | |
115 show_html = "<font color='%s'>[%s]</font>" % (show[2], show[1]) if show[2] else "" | |
116 status = self.CM.getAttr(jid,'status') or '' | |
117 avatar = self.CM.getAttr(jid,'avatar') or IMAGE_DIR+'/empty_avatar.png' | |
118 | |
119 html = """ | |
120 <table border='0'> | |
121 <td> | |
122 <img height='64' width='64' src='%s' /> | |
123 </td> | |
124 <td> | |
125 <b>%s</b> %s<br /> | |
126 <i>%s</i> | |
127 </td> | |
128 </table> | |
129 """ % (avatar, | |
130 escape(nick or name or jid.node or jid.short), | |
131 show_html, | |
132 escape(status)) | |
133 | |
134 return html | |
135 | |
136 def clear_contacts(self): | |
137 """Clear all the contact list""" | |
138 self.Clear() | |
139 | |
140 def add(self, contact, groups = None): | |
141 """add a contact to the list""" | |
142 debug (_("adding %s"),contact) | |
143 if not groups: | |
144 idx = self.Insert(self.__presentItem(contact), 0, contact) | |
145 else: | |
146 for group in groups: | |
147 indexes = self.__find_idx(group) | |
148 gp_idx = 0 | |
149 if not indexes: #this is a new group, we have to create it | |
150 gp_idx = self.Append(self.__presentGroup(group), Group(group)) | |
151 else: | |
152 gp_idx = indexes[0] | |
153 | |
154 self.Insert(self.__presentItem(contact), gp_idx+1, contact) | |
155 | |
156 | |
157 | |
158 def remove(self, contact): | |
159 """remove a contact from the list""" | |
160 debug (_("removing %s"), contact) | |
161 list_idx = self.__find_idx(contact) | |
75 | 162 list_idx.reverse() #as we make some deletions, we have to reverse the order |
72 | 163 for i in list_idx: |
164 self.Delete(i) | |
165 | |
166 def onSelected(self, event): | |
167 """Called when a contact is selected.""" | |
168 data = self.getSelection() | |
169 if data == None: #we have a group | |
138
2f8c86488b05
wix: scrolling is not reseted anymore when clicking on a group on contact list
Goffi <goffi@goffi.org>
parents:
125
diff
changeset
|
170 first_visible = self.GetVisibleBegin() |
72 | 171 group = self.GetClientData(self.GetSelection()) |
172 erased = self.__eraseGroup(group) | |
173 if not erased: #the group was already erased, we can add again the contacts | |
174 contacts = self.CM.getContFromGroup(group) | |
175 contacts.sort() | |
176 id_insert = self.GetSelection()+1 | |
177 for contact in contacts: | |
178 self.Insert(self.__presentItem(contact), id_insert, contact) | |
179 self.SetSelection(wx.NOT_FOUND) | |
138
2f8c86488b05
wix: scrolling is not reseted anymore when clicking on a group on contact list
Goffi <goffi@goffi.org>
parents:
125
diff
changeset
|
180 self.ScrollToLine(first_visible) |
72 | 181 event.Skip(False) |
182 else: | |
183 event.Skip() | |
184 | |
185 def onActivated(self, event): | |
186 """Called when a contact is clicked or activated with keyboard.""" | |
187 data = self.getSelection() | |
188 self.onActivatedCB(data) | |
189 event.Skip() | |
190 | |
191 def getSelection(self): | |
192 """Return the selected contact, or an empty string if there is not""" | |
193 if self.GetSelection() == wx.NOT_FOUND: | |
194 return None | |
195 data = self.GetClientData(self.GetSelection()) | |
196 if type(data) == Group: | |
197 return None | |
198 return data | |
199 | |
200 def registerActivatedCB(self, cb): | |
201 """Register a callback with manage contact activation.""" | |
202 self.onActivatedCB=cb | |
203 |