Improve drastically the performance of the MucListTab
- avoid doing stringprep on every item, avoid at least one full copy - add the number of items to the infowin
This commit is contained in:
parent
7c7f9b2f47
commit
7b446d9b4d
2 changed files with 48 additions and 19 deletions
|
@ -10,13 +10,18 @@ import logging
|
|||
log = logging.getLogger(__name__)
|
||||
|
||||
import curses
|
||||
import collections
|
||||
from datetime import datetime
|
||||
|
||||
from . import Tab
|
||||
from sleekxmpp.plugins.xep_0030.stanza.items import DiscoItem
|
||||
|
||||
import windows
|
||||
from common import safeJID
|
||||
from decorators import refresh_wrapper
|
||||
|
||||
from . import Tab
|
||||
|
||||
|
||||
class MucListTab(Tab):
|
||||
"""
|
||||
A tab listing rooms from a specific server, displaying various information,
|
||||
|
@ -29,8 +34,11 @@ class MucListTab(Tab):
|
|||
Tab.__init__(self)
|
||||
self.state = 'normal'
|
||||
self.name = server
|
||||
columns = ('node-part', 'name', 'users')
|
||||
self.list_header = windows.ColumnHeaderWin(columns)
|
||||
columns = collections.OrderedDict()
|
||||
columns['node-part'] = 0
|
||||
columns['name'] = 2
|
||||
columns['users'] = 3
|
||||
self.list_header = windows.ColumnHeaderWin(list(columns))
|
||||
self.listview = windows.ListWin(columns)
|
||||
self.info_header = windows.MucListInfoWin(_('Chatroom list on server %s (Loading)') % self.name)
|
||||
self.default_help_message = windows.HelpText("“j”: join room.")
|
||||
|
@ -55,7 +63,7 @@ class MucListTab(Tab):
|
|||
if self.need_resize:
|
||||
self.resize()
|
||||
log.debug(' TAB Refresh: %s', self.__class__.__name__)
|
||||
self.info_header.refresh()
|
||||
self.info_header.refresh(window=self.listview)
|
||||
self.info_win.refresh()
|
||||
self.refresh_tab_win()
|
||||
self.list_header.refresh()
|
||||
|
@ -110,18 +118,22 @@ class MucListTab(Tab):
|
|||
if iq['type'] == 'error':
|
||||
self.set_error(iq['error']['type'], iq['error']['code'], iq['error']['text'])
|
||||
return
|
||||
items = [{'node-part': safeJID(item[0]).user if safeJID(item[0]).server == self.name else safeJID(item[0]).bare,
|
||||
'jid': item[0],
|
||||
'name': item[2] or '', 'users': ''} for item in iq['disco_items'].get_items()]
|
||||
self.listview.add_lines(items)
|
||||
def get_items():
|
||||
substanza = iq['disco_items']
|
||||
for item in substanza['substanzas']:
|
||||
if isinstance(item, DiscoItem):
|
||||
yield (item['jid'], item['node'], item['name'])
|
||||
items = [ (item[0].split('@')[0],
|
||||
item[0],
|
||||
item[2] or '', '') for item in get_items()]
|
||||
self.listview.set_lines(items)
|
||||
self.info_header.message = _('Chatroom list on server %s') % self.name
|
||||
if self.core.current_tab() is self:
|
||||
self.listview.refresh()
|
||||
self.info_header.refresh()
|
||||
self.refresh()
|
||||
else:
|
||||
self.state = 'highlight'
|
||||
self.refresh_tab_win()
|
||||
curses.doupdate()
|
||||
self.core.doupdate()
|
||||
|
||||
def sort_by(self):
|
||||
if self.list_header.get_order():
|
||||
|
@ -136,7 +148,7 @@ class MucListTab(Tab):
|
|||
asc=True)
|
||||
self.list_header.set_order(True)
|
||||
self.list_header.refresh()
|
||||
curses.doupdate()
|
||||
self.core.doupdate()
|
||||
|
||||
def join_selected(self):
|
||||
row = self.listview.get_selected_row()
|
||||
|
|
|
@ -491,7 +491,7 @@ class MucListInfoWin(InfoWin):
|
|||
InfoWin.__init__(self)
|
||||
self.message = message
|
||||
|
||||
def refresh(self, name=None):
|
||||
def refresh(self, name=None, window=None):
|
||||
log.debug('Refresh: %s',self.__class__.__name__)
|
||||
with g_lock:
|
||||
self._win.erase()
|
||||
|
@ -499,6 +499,8 @@ class MucListInfoWin(InfoWin):
|
|||
self.addstr(name, to_curses_attr(get_theme().COLOR_INFORMATION_BAR))
|
||||
else:
|
||||
self.addstr(self.message, to_curses_attr(get_theme().COLOR_INFORMATION_BAR))
|
||||
if window:
|
||||
self.print_scroll_position(window)
|
||||
self.finish_line(get_theme().COLOR_INFORMATION_BAR)
|
||||
self._refresh()
|
||||
|
||||
|
@ -2248,13 +2250,20 @@ class ListWin(Win):
|
|||
"""
|
||||
def __init__(self, columns, with_headers=True):
|
||||
Win.__init__(self)
|
||||
self._columns = columns # a tuple with the name of the columns
|
||||
self._columns = columns # a dict {'column_name': tuple_index}
|
||||
self._columns_sizes = {} # a dict {'column_name': size}
|
||||
self.sorted_by = (None, None) # for example: ('name', '↑')
|
||||
self.lines = [] # a list of dicts
|
||||
self._selected_row = 0
|
||||
self._starting_pos = 0 # The column number from which we start the refresh
|
||||
|
||||
@property
|
||||
def pos(self):
|
||||
if len(self.lines) > self.height:
|
||||
return len(self.lines)
|
||||
else:
|
||||
return 0
|
||||
|
||||
def empty(self):
|
||||
"""
|
||||
emtpy the list and reset some important values as well
|
||||
|
@ -2288,7 +2297,15 @@ class ListWin(Win):
|
|||
"""
|
||||
if not lines:
|
||||
return
|
||||
self.lines += lines
|
||||
self.lines.extend(lines)
|
||||
|
||||
def set_lines(self, lines):
|
||||
"""
|
||||
Set the lines to another list
|
||||
"""
|
||||
if not lines:
|
||||
return
|
||||
self.lines = lines
|
||||
|
||||
def get_selected_row(self):
|
||||
"""
|
||||
|
@ -2305,12 +2322,12 @@ class ListWin(Win):
|
|||
lines = self.lines[self._starting_pos:self._starting_pos+self.height]
|
||||
for y, line in enumerate(lines):
|
||||
x = 0
|
||||
for col in self._columns:
|
||||
for col in self._columns.items():
|
||||
try:
|
||||
txt = line[col] or ''
|
||||
except (KeyError):
|
||||
txt = line[col[1]] or ''
|
||||
except KeyError:
|
||||
txt = ''
|
||||
size = self._columns_sizes[col]
|
||||
size = self._columns_sizes[col[0]]
|
||||
txt += ' ' * (size-len(txt))
|
||||
if not txt:
|
||||
continue
|
||||
|
|
Loading…
Reference in a new issue