Commit 280c77f3 authored by Bram Schoenmakers's avatar Bram Schoenmakers

Allow UIs to override the window size

The console widget is slightly smaller than the terminal size, so the
column UI should help get_terminal_size a bit to determine the correct
size.
parent cf9ee528
......@@ -23,12 +23,6 @@ import re
from collections import namedtuple
from datetime import date
# shutil.get_terminal_size was added to the standard library in Python 3.3
try:
from shutil import get_terminal_size as _get_terminal_size # pylint: disable=no-name-in-module
except ImportError:
from backports.shutil_get_terminal_size import get_terminal_size as _get_terminal_size # pylint: disable=import-error
def date_string_to_date(p_date):
"""
......@@ -61,19 +55,42 @@ def escape_ansi(p_string):
escape_ansi.pattern = re.compile(r'\x1b[^m]*m')
def get_terminal_size():
def get_terminal_size(p_getter=None):
"""
Try to determine terminal size at run time. If that is not possible,
returns the default size of 80x24.
By default, the size is determined with provided get_terminal_size by
shutil. Sometimes an UI may want to specify the desired width, then it can
provide a getter that returns a named tuple (columns, lines) with the size.
"""
try:
sz = _get_terminal_size()
except ValueError:
"""
This can result from the 'underlying buffer being detached', which
occurs during running the unittest on Windows (but not on Linux?)
"""
terminal_size = namedtuple('Terminal_Size', 'columns lines')
sz = terminal_size((80, 24))
return sz
return get_terminal_size.getter()
except AttributeError:
if p_getter:
get_terminal_size.getter = p_getter
else:
def inner():
try:
# shutil.get_terminal_size was added to the standard
# library in Python 3.3
try:
from shutil import get_terminal_size as _get_terminal_size # pylint: disable=no-name-in-module
except ImportError:
from backports.shutil_get_terminal_size import get_terminal_size as _get_terminal_size # pylint: disable=import-error
sz = _get_terminal_size()
except ValueError:
"""
This can result from the 'underlying buffer being detached', which
occurs during running the unittest on Windows (but not on Linux?)
"""
terminal_size = namedtuple('Terminal_Size', 'columns lines')
sz = terminal_size((80, 24))
return sz
get_terminal_size.getter = inner
return get_terminal_size.getter()
......@@ -21,6 +21,8 @@ class ConsoleWidget(urwid.LineBox):
urwid.register_signal(ConsoleWidget, ['close'])
self.text = urwid.Text(p_text)
self.width = 0
super().__init__(self.text)
def keypress(self, p_size, p_key):
......@@ -29,6 +31,14 @@ class ConsoleWidget(urwid.LineBox):
# don't return the key, 'enter', 'escape' or 'q' are your only escape.
def render(self, p_size, focus):
"""
This override intercepts the width of the widget such that it can be
stored. The width is used for rendering `ls` output.
"""
self.width = p_size[0]
return super().render(p_size, focus)
def selectable(self):
return True
......@@ -37,3 +47,7 @@ class ConsoleWidget(urwid.LineBox):
def clear(self):
self.text.set_text("")
def console_width(self):
# return the last known width (last render)
return self.width
......@@ -14,6 +14,7 @@
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
from collections import namedtuple
import shlex
import urwid
......@@ -27,6 +28,7 @@ from topydo.ui.ColumnLayout import columns
from topydo.lib.Config import config
from topydo.lib.Sorter import Sorter
from topydo.lib.Filter import get_filter_list, RelevanceFilter, DependencyFilter
from topydo.lib.Utils import get_terminal_size
from topydo.lib.View import View
from topydo.lib import TodoFile
from topydo.lib import TodoList
......@@ -81,6 +83,7 @@ class UIApplication(CLIApplicationBase):
# console widget
self.console = ConsoleWidget()
get_terminal_size(self._console_width)
urwid.connect_signal(self.commandline, 'blur', self._blur_commandline)
urwid.connect_signal(self.commandline, 'execute_command',
......@@ -355,6 +358,13 @@ class UIApplication(CLIApplicationBase):
return user_input[0]
def _console_width(self):
terminal_size = namedtuple('Terminal_Size', 'columns lines')
width = self.console.console_width() - 2
sz = terminal_size(width, 1)
return sz
def run(self):
layout = columns()
if len(layout) > 0:
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment