comparison browser_side/richtext.py @ 324:8131d0ccf21b

browser_side: prepare user input for microblog titles
author souliane <souliane@mailoo.org>
date Sat, 04 Jan 2014 02:38:23 +0100
parents 0b7934e75e76
children 6126bd24e7dd
comparison
equal deleted inserted replaced
323:0b7934e75e76 324:8131d0ccf21b
21 21
22 from pyjamas.ui.TextArea import TextArea 22 from pyjamas.ui.TextArea import TextArea
23 from pyjamas.ui.Button import Button 23 from pyjamas.ui.Button import Button
24 from pyjamas.ui.DialogBox import DialogBox 24 from pyjamas.ui.DialogBox import DialogBox
25 from pyjamas.ui.Label import Label 25 from pyjamas.ui.Label import Label
26 from pyjamas.ui.HTML import HTML
26 from pyjamas.ui.FlexTable import FlexTable 27 from pyjamas.ui.FlexTable import FlexTable
27 from pyjamas.ui.HorizontalPanel import HorizontalPanel 28 from pyjamas.ui.HorizontalPanel import HorizontalPanel
28 29
29 from dialog import ConfirmDialog, InfoDialog 30 from dialog import ConfirmDialog, InfoDialog
31 from base_panels import ToggleStackPanel
30 from list_manager import ListManager 32 from list_manager import ListManager
31 33
32 from sat_frontends.tools import composition 34 from sat_frontends.tools import composition
33 35 from sat.core.i18n import _
34 36
35 # used for onCloseCallback 37 # used for onCloseCallback
36 CANCEL, SYNC_NOT_SAVE, SAVE = xrange(0, 3) 38 CANCEL, SYNC_NOT_SAVE, SAVE = xrange(0, 3)
37 39
38 40
51 self._debug = False 53 self._debug = False
52 54
53 # This must be done before FlexTable.__init__ because it is used by setVisible 55 # This must be done before FlexTable.__init__ because it is used by setVisible
54 self.host = host 56 self.host = host
55 57
58 self.no_title = 'no_title' in options
59 #self.no_title = True # XXX: remove this line when titles are managed
56 self.no_close = 'no_close' in options 60 self.no_close = 'no_close' in options
57 self.update_msg = 'update_msg' in options 61 self.update_msg = 'update_msg' in options
58 self.no_recipient = 'no_recipient' in options 62 self.no_recipient = 'no_recipient' in options
59 self.no_command = 'no_command' in options 63 self.no_command = 'no_command' in options
60 self.no_sync_unibox = self.no_command or 'no_sync_unibox' in options 64 self.no_sync_unibox = self.no_command or 'no_sync_unibox' in options
61 self.no_main_style = 'no_style' in options or 'no_main_style' in options 65 self.no_main_style = 'no_style' in options or 'no_main_style' in options
62 self.no_toolbar_style = 'no_style' in options or 'no_toolbar_style' in options 66 self.no_title_style = 'no_style' in options or 'no_title_style' in options
63 self.no_textarea_style = 'no_style' in options or 'no_textarea_style' in options 67 self.no_textarea_style = 'no_style' in options or 'no_textarea_style' in options
64 68
65 offset1 = 0 if self.no_recipient else len(composition.RECIPIENT_TYPES) 69 offset1 = 0 if self.no_recipient else (len(composition.RECIPIENT_TYPES) + 1)
66 offset2 = len(composition.RICH_FORMATS) if self._debug else 1 70 offset2 = 0 if self.no_title else 1
67 offset3 = 0 if self.no_command else 1 71 offset3 = len(composition.RICH_FORMATS) if self._debug else 1
68 FlexTable.__init__(self, offset1 + offset2 + 1 + offset3, 2) 72 offset4 = 0 if self.no_command else 1
73 FlexTable.__init__(self, offset1 + offset2 + offset3 + 1 + offset4, 2)
69 if not self.no_main_style: 74 if not self.no_main_style:
70 self.addStyleName('richTextEditor') 75 self.addStyleName('richTextEditor')
71 76
72 self._parent = parent 77 self._parent = parent
73 self._on_close_callback = onCloseCallback 78 self._on_close_callback = onCloseCallback
74 self.original_text = '' 79 self.original_text = ''
75 80
81 current_offset = offset1
76 if not self.no_recipient: 82 if not self.no_recipient:
77 # recipient types sub-panels are automatically added by the manager 83 # recipient types sub-panels are automatically added by the manager
78 self.recipient = RecipientManager(self) 84 self.recipient = RecipientManager(self)
79 self.recipient.createWidgets(title_format="%s: ") 85 self.recipient.createWidgets(title_format="%s: ")
86 self.getFlexCellFormatter().setColSpan(current_offset - 1, 0, 2)
87 spacer = HTML('')
88 spacer.setStyleName('recipientSpacer')
89 self.setWidget(current_offset - 1, 0, spacer)
90
91 current_offset += offset2
92 if not self.no_title:
93 self.title_panel = TitlePanel()
94 self.title_panel.addStyleName("richTextTitle")
95 self.getFlexCellFormatter().setColSpan(current_offset - 1, 0, 2)
96 self.setWidget(current_offset - 1, 0, self.title_panel)
80 97
81 # Rich text tool bar is automatically added by setVisible 98 # Rich text tool bar is automatically added by setVisible
82 99 self.offset_toolbar = offset1 + offset2
100
101 current_offset += offset3 + 1
83 self.textarea = TextArea() 102 self.textarea = TextArea()
84 if not self.no_textarea_style: 103 if not self.no_textarea_style:
85 self.textarea.addStyleName('richTextArea') 104 self.textarea.addStyleName('richTextArea')
86 105 self.getFlexCellFormatter().setColSpan(current_offset - 1, 0, 2)
87 self.getFlexCellFormatter().setColSpan(offset1 + offset2, 0, 2) 106 self.setWidget(current_offset - 1, 0, self.textarea)
88 self.setWidget(offset1 + offset2, 0, self.textarea) 107
89 108 current_offset += offset4
90 if not self.no_command: 109 if not self.no_command:
91 self.command = HorizontalPanel() 110 self.command = HorizontalPanel()
92 self.command.addStyleName("marginAuto") 111 self.command.addStyleName("marginAuto")
93 self.command.add(Button("Cancel", listener=self.cancelWithoutSaving)) 112 self.command.add(Button("Cancel", listener=self.cancelWithoutSaving))
94 if not self.no_sync_unibox: 113 if not self.no_sync_unibox:
95 self.command.add(Button("Back to quick box", listener=self.closeAndSave)) 114 self.command.add(Button("Back to quick box", listener=self.closeAndSave))
96 self.command.add(Button("Update" if self.update_msg else "Send message", 115 self.command.add(Button("Update" if self.update_msg else "Send message",
97 listener=self.__close if (self.update_msg or self.no_recipient) else self.sendMessage)) 116 listener=self.__close if (self.update_msg or self.no_recipient) else self.sendMessage))
98 self.getFlexCellFormatter().setColSpan(offset1 + offset2 + 1, 0, 2) 117 self.getFlexCellFormatter().setColSpan(current_offset - 1, 0, 2)
99 self.setWidget(offset1 + offset2 + 1, 0, self.command) 118 self.setWidget(current_offset - 1, 0, self.command)
100 119
101 @classmethod 120 @classmethod
102 def getOrCreate(cls, host, parent=None, onCloseCallback=None): 121 def getOrCreate(cls, host, parent=None, onCloseCallback=None):
103 """Get or create the richtext editor associated to that host. 122 """Get or create the richtext editor associated to that host.
104 Add it to parent if parent is not None, otherwise display it 123 Add it to parent if parent is not None, otherwise display it
158 if _format is None or _format not in composition.RICH_FORMATS.keys(): 177 if _format is None or _format not in composition.RICH_FORMATS.keys():
159 _format = composition.RICH_FORMATS.keys()[0] 178 _format = composition.RICH_FORMATS.keys()[0]
160 if hasattr(self, "_format") and self._format == _format: 179 if hasattr(self, "_format") and self._format == _format:
161 return 180 return
162 self._format = _format 181 self._format = _format
163 offset1 = 0 if self.no_recipient else len(composition.RECIPIENT_TYPES)
164 count = 0 182 count = 0
165 for _format in composition.RICH_FORMATS.keys() if self._debug else [self._format]: 183 for _format in composition.RICH_FORMATS.keys() if self._debug else [self._format]:
166 toolbar = HorizontalPanel() 184 toolbar = HorizontalPanel()
167 if not self.no_toolbar_style: 185 toolbar.addStyleName('richTextToolbar')
168 toolbar.addStyleName('richTextToolbar')
169 for key in composition.RICH_FORMATS[_format].keys(): 186 for key in composition.RICH_FORMATS[_format].keys():
170 self.addToolbarButton(toolbar, _format, key) 187 self.addToolbarButton(toolbar, _format, key)
171 label = Label("Format: %s" % _format) 188 label = Label("Format: %s" % _format)
172 label.addStyleName("richTextFormatLabel") 189 label.addStyleName("richTextFormatLabel")
173 toolbar.add(label) 190 toolbar.add(label)
174 self.getFlexCellFormatter().setColSpan(offset1 + count, 0, 2) 191 self.getFlexCellFormatter().setColSpan(self.offset_toolbar + count, 0, 2)
175 self.setWidget(offset1 + count, 0, toolbar) 192 self.setWidget(self.offset_toolbar + count, 0, toolbar)
176 count += 1 193 count += 1
177 194
178 @property 195 @property
179 def format(self): 196 def format(self):
180 """Get the current text format""" 197 """Get the current text format"""
302 319
303 320
304 class RecipientManager(ListManager): 321 class RecipientManager(ListManager):
305 """A manager for sub-panels to set the recipients for each recipient type.""" 322 """A manager for sub-panels to set the recipients for each recipient type."""
306 323
307 def __init__(self, parent): 324 def __init__(self, parent, y_offset=0):
308 # TODO: be sure we also display empty groups and disconnected contacts + their groups 325 # TODO: be sure we also display empty groups and disconnected contacts + their groups
309 # store the full list of potential recipients (groups and contacts) 326 # store the full list of potential recipients (groups and contacts)
310 list_ = [] 327 list_ = []
311 list_.append("@@") 328 list_.append("@@")
312 list_.extend("@%s" % group for group in parent.host.contact_panel.getGroups()) 329 list_.extend("@%s" % group for group in parent.host.contact_panel.getGroups())
313 list_.extend(contact for contact in parent.host.contact_panel.getContacts()) 330 list_.extend(contact for contact in parent.host.contact_panel.getContacts())
314 ListManager.__init__(self, parent, composition.RECIPIENT_TYPES, list_) 331 ListManager.__init__(self, parent, composition.RECIPIENT_TYPES, list_, {'y': y_offset})
315 332
316 self.registerPopupMenuPanel(entries=composition.RECIPIENT_TYPES, 333 self.registerPopupMenuPanel(entries=composition.RECIPIENT_TYPES,
317 hide=lambda sender, key: self.__children[key]["panel"].isVisible(), 334 hide=lambda sender, key: self.__children[key]["panel"].isVisible(),
318 callback=self.setContactPanelVisible) 335 callback=self.setContactPanelVisible)
336
337
338 class TitlePanel(ToggleStackPanel):
339 """A toggle panel to set the message title"""
340 def __init__(self):
341 ToggleStackPanel.__init__(self, Width="100%")
342 self.text_area = TextArea()
343 self.add(self.text_area, _("Title"))
344 self.addStackChangeListener(self)
345
346 def onStackChanged(self, sender, index, visible=None):
347 if visible is None:
348 visible = sender.getWidget(index).getVisible()
349 text = self.text_area.getText()
350 suffix = "" if (visible or not text) else (": %s" % text)
351 sender.setStackText(index, _("Title") + suffix)