Development: urwid-class_hierarchy.patch
| File urwid-class_hierarchy.patch, 7.1 kB (added by anonymous, 2 years ago) |
|---|
-
urwid/widget.py
old new 27 27 try: sum # old python? 28 28 except: sum = lambda l: reduce(lambda a,b: a+b, l, 0) 29 29 30 class FlowWidget(object): 30 class autosuper(type): 31 """adding .__super""" 32 def __init__(cls, name, bases, dict): 33 super(autosuper, cls).__init__(name, bases, dict) 34 if hasattr(cls, "_%s__super" % name): 35 raise AttributeError, "Class has same name as one of its super classes" 36 setattr(cls, "_%s__super" % name, super(cls)) 37 38 class Widget(object): 39 40 __metaclass__ = autosuper 41 _selectable = False 42 43 def __init__(self): 44 self.__callbacks = {} 45 46 def register_callback(self, name, callback, user_data=None, pos =-1): 47 # XXX check name 48 self.__callbacks.setdefault(name, []).insert( 49 pos, (callback, user_data)) 50 51 def deregister_callback(self, name, callback): 52 l = self.__callbacks.get(name, []) 53 for nr, (cb, user_data) in enumerate(l): 54 if cb == callback: 55 del l[nr] 56 return 57 raise ValueError, "Callback not registered" 58 59 def _callback(self, name, *args): 60 for callback, user_data in self.__callbacks.get(name, []): 61 if user_data is not None: 62 args.append(user_data) 63 if callback(*args): 64 return True 65 return False 66 67 def selectable(self): 68 return self._selectable 69 70 class FlowWidget(Widget): 31 71 """ 32 72 base class of widgets 33 73 """ 34 def selectable(self):35 """Return False. Not selectable by default."""36 return False37 38 74 def rows(self, (maxcol,), focus=False): 39 75 """ 40 76 All flow widgets must implement this function. … … 48 84 raise NotImplementedError() 49 85 50 86 51 class BoxWidget( object):87 class BoxWidget(Widget): 52 88 """ 53 89 base class of width and height constrained widgets such as 54 90 the top level widget attached to the display object 55 91 """ 56 def selectable(self): 57 """Return True. Selectable by default.""" 58 return True 59 92 _selectable = True 93 60 94 def render(self, size, focus=False): 61 95 """ 62 96 All widgets must implement this function. … … 74 108 raise ValueError("FixedWidget takes only () for size." \ 75 109 "passed: %s" % `size`) 76 110 77 class FixedWidget(object): 78 def selectable(self): 79 """Return False. Not selectable by default.""" 80 return False 81 111 class FixedWidget(Widget): 82 112 def render(self, size, focus=False): 83 113 """ 84 114 All widgets must implement this function. … … 101 131 top -- number of blank lines above 102 132 bottom -- number of blank lines below 103 133 """ 134 self.__super.__init__() 104 135 self.div_char = div_char 105 136 self.top = top 106 137 self.bottom = bottom … … 133 164 """ 134 165 fill_char -- character to fill area with 135 166 """ 167 self.__super.__init__() 136 168 self.fill_char = fill_char 137 169 138 170 def render(self,(maxcol,maxrow), focus=False ): … … 167 199 wrap -- wrap mode for text layout 168 200 layout -- layout object to use, defaults to StandardTextLayout 169 201 """ 202 self.__super.__init__() 170 203 self._cache_maxcol = None 171 204 self.set_text(markup) 172 205 self.set_layout(align, wrap, layout) … … 329 362 layout -- layout object 330 363 """ 331 364 332 Text.__init__(self,"", align, wrap, layout)365 self.__super.__init__("", align, wrap, layout) 333 366 assert type(edit_text)==type("") or type(edit_text)==type(u"") 334 367 self.multiline = multiline 335 368 self.allow_tab = allow_tab … … 588 621 """ 589 622 if default is not None: val = str(default) 590 623 else: val = "" 591 Edit.__init__(self,caption,val)624 self.__super.__init__(caption,val) 592 625 593 626 def keypress(self,(maxcol,),key): 594 627 """Handle editing keystrokes. Return others.""" … … 649 682 user_data -- additional param for on_press callback, 650 683 ommited if None for compatibility reasons 651 684 """ 685 self.__super.__init__() 652 686 self.label = Text("") 653 687 self.has_mixed = has_mixed 654 688 self.state = None … … 751 785 This function will append the new radio button to group. 752 786 "first True" will set to True if group is empty. 753 787 """ 788 self.__super.__init__() 754 789 755 790 if state=="first True": 756 791 state = not group … … 850 885 user_data -- additional param for on_press callback, 851 886 ommited if None for compatibility reasons 852 887 """ 888 self.__super.__init__() 853 889 854 890 self.set_label( label ) 855 891 self.on_press = on_press … … 920 956 align -- horizontal alignment of cells, see "align" parameter 921 957 of Padding widget for available options 922 958 """ 959 self.__super.__init__() 923 960 self.cells = cells 924 961 self.cell_width = cell_width 925 962 self.h_sep = h_sep … … 1097 1134 class PaddingError(Exception): 1098 1135 pass 1099 1136 1100 class Padding( object):1137 class Padding(FlowWidget, BoxWidget): 1101 1138 def __init__(self, w, align, width, min_width=None): 1102 1139 """ 1103 1140 w -- a box, flow or fixed widget to pad on the left and/or right … … 1124 1161 be clipped to fit within the space given. For example, 1125 1162 if align is 'left' then w may be clipped on the right. 1126 1163 """ 1164 self.__super.__init__() 1127 1165 1128 1166 at,aa,wt,wa=decompose_align_width(align, width, PaddingError) 1129 1167 … … 1267 1305 reducing the valign amount when necessary. If height still 1268 1306 cannot be satisfied it will also be reduced. 1269 1307 """ 1308 self.__super.__init__() 1270 1309 vt,va,ht,ha=decompose_valign_height(valign,height,FillerError) 1271 1310 1272 1311 self.body = body … … 1428 1467 when determining the size and position of top_w. bottom_w is 1429 1468 always rendered the full size available "below" top_w. 1430 1469 """ 1470 self.__super.__init__() 1431 1471 1432 1472 at,aa,wt,wa=decompose_align_width(align, width, OverlayError) 1433 1473 vt,va,ht,ha=decompose_valign_height(valign,height,OverlayError) … … 1709 1749 footer -- a flow widget for below the body (or None) 1710 1750 focus_part -- 'header', 'footer' or 'body' 1711 1751 """ 1752 self.__super.__init__() 1712 1753 self.header = header 1713 1754 self.body = body 1714 1755 self.footer = footer … … 1927 1968 class PileError(Exception): 1928 1969 pass 1929 1970 1930 class Pile( object): # either FlowWidget or BoxWidget1971 class Pile(FlowWidget, BoxWidget): # either FlowWidget or BoxWidget 1931 1972 def __init__(self, widget_list, focus_item=0): 1932 1973 """ 1933 1974 widget_list -- list of widgets … … 1946 1987 If the pile is treated as a box widget there must be at least 1947 1988 one 'weight' tuple in widget_list. 1948 1989 """ 1990 self.__super.__init__() 1949 1991 self.widget_list = widget_list 1950 1992 self.item_types = [] 1951 1993 for i in range(len(widget_list)): … … 2258 2300 pass 2259 2301 2260 2302 2261 class Columns( object): # either FlowWidget or BoxWidget2303 class Columns(FlowWidget, BoxWidget): # either FlowWidget or BoxWidget 2262 2304 def __init__(self, widget_list, dividechars=0, focus_column=0, 2263 2305 min_width=1, box_columns=None): 2264 2306 """ … … 2280 2322 box widget because in that case all columns are treated as box 2281 2323 widgets. 2282 2324 """ 2325 self.__super.__init__() 2283 2326 self.widget_list = widget_list 2284 2327 self.column_types = [] 2285 2328 for i in range(len(widget_list)): … … 2584 2627 2585 2628 2586 2629 2587 class BoxAdapter( object):2630 class BoxAdapter(FlowWidget): 2588 2631 """ 2589 2632 Adapter for using a box widget where a flow widget would usually go 2590 2633 """ … … 2596 2639 box_widget -- box widget 2597 2640 height -- number of rows for box widget 2598 2641 """ 2642 self.__super.__init__() 2599 2643 2600 2644 self.height = height 2601 2645 self.box_widget = box_widget
