comparison cagou/core/profile_manager.py @ 270:89ba66464329

profile manager: don't use anymore deprecated ListView + use dp() for sizes of buttons instead of relative size.
author Goffi <goffi@goffi.org>
date Wed, 20 Mar 2019 09:29:44 +0100
parents b270fcc87304
children 1b835bcfa663
comparison
equal deleted inserted replaced
269:a5dfc789eeaf 270:89ba66464329
21 from sat.core import log as logging 21 from sat.core import log as logging
22 log = logging.getLogger(__name__) 22 log = logging.getLogger(__name__)
23 from .constants import Const as C 23 from .constants import Const as C
24 from sat_frontends.quick_frontend.quick_profile_manager import QuickProfileManager 24 from sat_frontends.quick_frontend.quick_profile_manager import QuickProfileManager
25 from kivy.uix.boxlayout import BoxLayout 25 from kivy.uix.boxlayout import BoxLayout
26 from kivy.uix import listview 26 from kivy.uix.togglebutton import ToggleButton
27 from kivy.uix.button import Button
28 from kivy.uix.screenmanager import ScreenManager, Screen 27 from kivy.uix.screenmanager import ScreenManager, Screen
29 from kivy.adapters import listadapter
30 from kivy.metrics import sp 28 from kivy.metrics import sp
31 from kivy import properties 29 from kivy import properties
32 from cagou import G 30 from cagou import G
33 31
34 32
35 class ProfileItem(listview.ListItemButton): 33 class ProfileItem(ToggleButton):
36 pass 34 ps = properties.ObjectProperty()
37 35 index = properties.NumericProperty(0)
38
39 class ProfileListAdapter(listadapter.ListAdapter):
40
41 def __init__(self, pm, *args, **kwargs):
42 super(ProfileListAdapter, self).__init__(*args, **kwargs)
43 self.pm = pm
44
45 def closeUI(self, xmlui):
46 self.pm.screen_manager.transition.direction = 'right'
47 self.pm.screen_manager.current = 'profiles'
48
49 def showUI(self, xmlui):
50 xmlui.setCloseCb(self.closeUI)
51 if xmlui.type == 'popup':
52 xmlui.bind(on_touch_up=lambda obj, value: self.closeUI(xmlui))
53 self.pm.xmlui_screen.clear_widgets()
54 self.pm.xmlui_screen.add_widget(xmlui)
55 self.pm.screen_manager.transition.direction = 'left'
56 self.pm.screen_manager.current = 'xmlui'
57
58 def select_item_view(self, view):
59 def authenticate_cb(data, cb_id, profile):
60 if C.bool(data.pop('validated', C.BOOL_FALSE)):
61 super(ProfileListAdapter, self).select_item_view(view)
62 G.host.actionManager(data, callback=authenticate_cb, ui_show_cb=self.showUI, profile=profile)
63
64 G.host.launchAction(C.AUTHENTICATE_PROFILE_ID, callback=authenticate_cb, profile=view.text)
65
66
67 class ConnectButton(Button):
68
69 def __init__(self, profile_screen):
70 self.profile_screen = profile_screen
71 self.pm = profile_screen.pm
72 super(ConnectButton, self).__init__()
73 36
74 37
75 class NewProfileScreen(Screen): 38 class NewProfileScreen(Screen):
76 profile_name = properties.ObjectProperty(None) 39 profile_name = properties.ObjectProperty(None)
77 jid = properties.ObjectProperty(None) 40 jid = properties.ObjectProperty(None)
86 msg = [l for l in unicode(failure).split('\n') if l][-1] 49 msg = [l for l in unicode(failure).split('\n') if l][-1]
87 self.error_msg = unicode(msg) 50 self.error_msg = unicode(msg)
88 51
89 def onCreationSuccess(self, profile): 52 def onCreationSuccess(self, profile):
90 self.pm.profiles_screen.reload() 53 self.pm.profiles_screen.reload()
91 G.host.bridge.profileStartSession(self.password.text, profile, callback=lambda dummy: self._sessionStarted(profile), errback=self.onCreationFailure) 54 G.host.bridge.profileStartSession(
55 self.password.text, profile,
56 callback=lambda dummy: self._sessionStarted(profile),
57 errback=self.onCreationFailure)
92 58
93 def _sessionStarted(self, profile): 59 def _sessionStarted(self, profile):
94 jid = self.jid.text.strip() 60 jid = self.jid.text.strip()
95 G.host.bridge.setParam("JabberID", jid, "Connection", -1, profile) 61 G.host.bridge.setParam("JabberID", jid, "Connection", -1, profile)
96 G.host.bridge.setParam("Password", self.password.text, "Connection", -1, profile) 62 G.host.bridge.setParam("Password", self.password.text, "Connection", -1, profile)
99 65
100 def doCreate(self): 66 def doCreate(self):
101 name = self.profile_name.text.strip() 67 name = self.profile_name.text.strip()
102 # XXX: we use XMPP password for profile password to simplify 68 # XXX: we use XMPP password for profile password to simplify
103 # if user want to change profile password, he can do it in preferences 69 # if user want to change profile password, he can do it in preferences
104 G.host.bridge.profileCreate(name, self.password.text, u'', callback=lambda: self.onCreationSuccess(name), errback=self.onCreationFailure) 70 G.host.bridge.profileCreate(
71 name, self.password.text, u'',
72 callback=lambda: self.onCreationSuccess(name),
73 errback=self.onCreationFailure)
105 74
106 75
107 class DeleteProfilesScreen(Screen): 76 class DeleteProfilesScreen(Screen):
108 77
109 def __init__(self, pm): 78 def __init__(self, pm):
122 self.pm.screen_manager.transition.direction = 'right' 91 self.pm.screen_manager.transition.direction = 'right'
123 self.pm.screen_manager.current = 'profiles' 92 self.pm.screen_manager.current = 'profiles'
124 93
125 for profile in to_delete: 94 for profile in to_delete:
126 log.info(u"Deleteing profile [{}]".format(profile)) 95 log.info(u"Deleteing profile [{}]".format(profile))
127 G.host.bridge.asyncDeleteProfile(profile, callback=deleteInc, errback=deleteInc) 96 G.host.bridge.asyncDeleteProfile(
97 profile, callback=deleteInc, errback=deleteInc)
128 98
129 99
130 class ProfilesScreen(Screen): 100 class ProfilesScreen(Screen):
131 layout = properties.ObjectProperty(None) 101 layout = properties.ObjectProperty(None)
102 profiles = properties.ListProperty()
132 103
133 def __init__(self, pm): 104 def __init__(self, pm):
134 self.pm = pm 105 self.pm = pm
135 self.list_adapter = ProfileListAdapter(pm,
136 data=[],
137 cls=ProfileItem,
138 args_converter=self.converter,
139 selection_mode='multiple',
140 allow_empty_selection=True,
141 )
142 super(ProfilesScreen, self).__init__(name=u'profiles') 106 super(ProfilesScreen, self).__init__(name=u'profiles')
143 self.layout.add_widget(listview.ListView(adapter=self.list_adapter))
144 connect_btn = ConnectButton(self)
145 self.layout.add_widget(connect_btn)
146 self.reload() 107 self.reload()
147 108
148 def _profilesListGetCb(self, profiles): 109 def _profilesListGetCb(self, profiles):
149 profiles.sort() 110 profiles.sort()
150 self.list_adapter.data = profiles 111 self.profiles = profiles
112 for idx, profile in enumerate(profiles):
113 item = ProfileItem(ps=self, index=idx, text=profile, group='profiles')
114 self.layout.add_widget(item)
151 115
152 def converter(self, row_idx, obj): 116 def converter(self, row_idx, obj):
153 return {'text': obj, 117 return {'text': obj,
154 'size_hint_y': None, 118 'size_hint_y': None,
155 'height': sp(40)} 119 'height': sp(40)}
156 120
157 def reload(self): 121 def reload(self):
158 """Reload profiles list""" 122 """Reload profiles list"""
123 self.layout.clear_widgets()
159 G.host.bridge.profilesListGet(callback=self._profilesListGetCb) 124 G.host.bridge.profilesListGet(callback=self._profilesListGetCb)
160 125
161 126
162 class ProfileManager(QuickProfileManager, BoxLayout): 127 class ProfileManager(QuickProfileManager, BoxLayout):
128 selected = properties.ObjectProperty(None)
163 129
164 def __init__(self, autoconnect=None): 130 def __init__(self, autoconnect=None):
165 QuickProfileManager.__init__(self, G.host, autoconnect) 131 QuickProfileManager.__init__(self, G.host, autoconnect)
166 BoxLayout.__init__(self, orientation="vertical") 132 BoxLayout.__init__(self, orientation="vertical")
167 self.screen_manager = ScreenManager() 133 self.screen_manager = ScreenManager()
172 self.screen_manager.add_widget(self.profiles_screen) 138 self.screen_manager.add_widget(self.profiles_screen)
173 self.screen_manager.add_widget(self.xmlui_screen) 139 self.screen_manager.add_widget(self.xmlui_screen)
174 self.screen_manager.add_widget(self.new_profile_screen) 140 self.screen_manager.add_widget(self.new_profile_screen)
175 self.screen_manager.add_widget(self.delete_profiles_screen) 141 self.screen_manager.add_widget(self.delete_profiles_screen)
176 self.add_widget(self.screen_manager) 142 self.add_widget(self.screen_manager)
143 self.bind(selected=self.onProfileSelect)
144
145 def closeUI(self, xmlui):
146 self.screen_manager.transition.direction = 'right'
147 self.screen_manager.current = 'profiles'
148
149 def showUI(self, xmlui):
150 xmlui.setCloseCb(self.closeUI)
151 if xmlui.type == 'popup':
152 xmlui.bind(on_touch_up=lambda obj, value: self.closeUI(xmlui))
153 self.xmlui_screen.clear_widgets()
154 self.xmlui_screen.add_widget(xmlui)
155 self.screen_manager.transition.direction = 'left'
156 self.screen_manager.current = 'xmlui'
157
158 def onProfileSelect(self, __, selected):
159 if not selected:
160 return
161 def authenticate_cb(data, cb_id, profile):
162 if not C.bool(data.pop('validated', C.BOOL_FALSE)):
163 # profile didn't validate, we unselect it
164 selected.state = 'normal'
165 self.selected = ''
166 else:
167 # state may have been modified so we need to be sure it's down
168 selected.state = 'down'
169 self.selected = selected
170 G.host.actionManager(data, callback=authenticate_cb, ui_show_cb=self.showUI,
171 profile=profile)
172
173 G.host.launchAction(C.AUTHENTICATE_PROFILE_ID, callback=authenticate_cb,
174 profile=selected.text)
177 175
178 def getProfiles(self): 176 def getProfiles(self):
179 return [pi.text for pi in self.profiles_screen.list_adapter.selection] 177 # for now we restrict to a single profile in Cagou
178 # TODO: handle multi-profiles
179 return [self.selected.text] if self.selected else []