Package flumotion :: Package admin :: Package gtk :: Module message
[hide private]

Source Code for Module flumotion.admin.gtk.message

  1  # -*- Mode: Python -*- 
  2  # vi:si:et:sw=4:sts=4:ts=4 
  3  # 
  4  # Flumotion - a streaming media server 
  5  # Copyright (C) 2004,2005,2006,2007 Fluendo, S.L. (www.fluendo.com). 
  6  # All rights reserved. 
  7   
  8  # This file may be distributed and/or modified under the terms of 
  9  # the GNU General Public License version 2 as published by 
 10  # the Free Software Foundation. 
 11  # This file is distributed without any warranty; without even the implied 
 12  # warranty of merchantability or fitness for a particular purpose. 
 13  # See "LICENSE.GPL" in the source distribution for more information. 
 14   
 15  # Licensees having purchased or holding a valid Flumotion Advanced 
 16  # Streaming Server license may use this file in accordance with the 
 17  # Flumotion Advanced Streaming Server Commercial License Agreement. 
 18  # See "LICENSE.Flumotion" in the source distribution for more information. 
 19   
 20  # Headers in this file shall remain intact. 
 21   
 22  from flumotion.common import messages 
 23  from flumotion.configure import configure 
 24   
 25  from gettext import gettext as _ 
 26   
 27  import os 
 28  import time 
 29  import gtk 
 30   
 31  _stock_icons = {messages.ERROR: gtk.STOCK_DIALOG_ERROR, 
 32                  messages.WARNING: gtk.STOCK_DIALOG_WARNING, 
 33                  messages.INFO: gtk.STOCK_DIALOG_INFO} 
 34   
 35  _headings = {messages.ERROR: _('Error'), 
 36               messages.WARNING: _('Warning'), 
 37               messages.INFO: _('Note')} 
 38   
39 -class MessageButton(gtk.ToggleButton):
40 """ 41 I am a button at the top right of the message view, representing a message. 42 """
43 - def __init__(self, message):
44 gtk.ToggleButton.__init__(self) 45 46 self.message = message 47 48 i = gtk.Image() 49 i.set_from_stock(_stock_icons.get(message.level, 50 gtk.STOCK_MISSING_IMAGE), 51 gtk.ICON_SIZE_BUTTON) 52 i.show() 53 self.add(i) 54 self.set_focus_on_click(False) 55 self.set_relief(gtk.RELIEF_NONE)
56
57 - def __repr__(self):
58 return '<MessageButton for %s at %d>' % (self.message, id(self))
59 60 # instantiated through create_function in glade files
61 -class MessagesView(gtk.VBox):
62 """ 63 I am a widget that can show messages. 64 """ 65 # I am a vbox with first row the label and icons, 66 # second row a separator 67 # and third row a text view
68 - def __init__(self):
69 gtk.VBox.__init__(self) 70 71 h1 = gtk.HBox() 72 self.pack_start(h1, False, False, 0) 73 self.label = gtk.Label() 74 self.label.show() 75 h1.pack_start(self.label, False, False, 6) 76 77 # button box holding the message icons at the top right 78 h2 = gtk.HBox() 79 h1.pack_end(h2, False, False, 0) 80 s = gtk.HSeparator() 81 self.pack_start(s, False, False, 6) 82 sw = gtk.ScrolledWindow() 83 sw.set_policy(gtk.POLICY_NEVER, gtk.POLICY_AUTOMATIC) 84 sw.set_shadow_type(gtk.SHADOW_NONE) 85 self.pack_start(sw, True, True, 0) 86 87 # text view shows the messages, plus debug information 88 # FIXME: needs to be hyperlinkable in the future 89 tv = gtk.TextView() 90 tv.set_wrap_mode(gtk.WRAP_WORD) 91 tv.set_left_margin(6) 92 tv.set_right_margin(6) 93 tv.set_accepts_tab(False) 94 tv.set_cursor_visible(False) 95 tv.set_editable(False) 96 #tv.set_sensitive(False) 97 sw.add(tv) 98 99 self.active_button = None 100 self.buttonbox = h2 101 self.textview = tv 102 103 self.show_all() 104 self.clear() 105 106 self._translator = messages.Translator() 107 localedir = os.path.join(configure.localedatadir, 'locale') 108 # FIXME: add locales as messages from domains come in 109 self._translator.addLocaleDir('flumotion', localedir)
110
111 - def clear(self):
112 """ 113 Remove all messages and hide myself. 114 """ 115 for i in self.buttonbox.get_children(): 116 self.clear_message(i.message.id) 117 self.hide()
118
119 - def add_message(self, m):
120 """ 121 Add a message to me. 122 @type m: L{flumotion.common.messages.Message} 123 """ 124 def on_toggled(b): 125 # on toggling the button, show the message 126 if not b.get_active(): 127 if self.active_button == b: 128 b.set_active(True) 129 return 130 old_active = self.active_button 131 self.active_button = b 132 if old_active and old_active != b: 133 old_active.set_active(False) 134 buf = gtk.TextBuffer() 135 # FIXME: it would be good to have a "Debug" button when 136 # applicable, instead of always showing the text 137 text = self._translator.translate(m) 138 # F0.4: timestamp was added in 0.4.2 139 if hasattr(m, 'timestamp'): 140 text += _("\nPosted on %s.\n") % time.strftime( 141 "%c", time.localtime(m.timestamp)) 142 if m.debug: 143 text += "\n\n" + _("Debug information:\n") + m.debug 144 buf.set_text(text) 145 self.textview.set_buffer(buf) 146 self.label.set_markup('<b>%s</b>' % 147 _headings.get(m.level, _('Message')))
148 149 # FIXME:this clears all messages with the same id as the new one. 150 # effectively replacing. Is this what we want ? 151 self.clear_message(m.id) 152 153 # add a message button to show this message 154 b = MessageButton(m) 155 b.sigid = b.connect('toggled', on_toggled) 156 b.show() 157 self.buttonbox.pack_start(b, False, False, 0) 158 159 # Sort all messages first by (reverse of) level, then priority 160 kids = [(-w.message.level, w.message.priority, w) for w in self.buttonbox.get_children()] 161 kids.sort() 162 kids.reverse() 163 kids = [(i, kids[i][2]) for i in range(len(kids))] 164 for x in kids: 165 self.buttonbox.reorder_child(x[1], x[0]) 166 167 if not self.active_button: 168 b.set_active(True) 169 elif b == kids[0][1]: # the first button, e.g. highest priority 170 b.set_active(True) 171 self.show()
172
173 - def clear_message(self, id):
174 """ 175 Clear all messages with the given id. 176 Will bring the remaining most important message to the front, 177 or hide the view completely if no messages are left. 178 """ 179 for b in self.buttonbox.get_children(): 180 if b.message.id == id: 181 self.buttonbox.remove(b) 182 b.disconnect(b.sigid) 183 b.sigid = 0 184 if not self.buttonbox.get_children(): 185 self.active_button = None 186 self.hide() 187 elif self.active_button == b: 188 self.active_button = self.buttonbox.get_children()[0] 189 self.active_button.set_active(True) 190 return
191