From 871e2bc9602e7feee9cdab5ec93e26863f512073 Mon Sep 17 00:00:00 2001 From: Ivan Habunek Date: Tue, 27 Aug 2019 14:34:51 +0200 Subject: [PATCH] Render polls --- toot/tui/entities.py | 8 ++------ toot/tui/timeline.py | 34 +++++++++++++++++++++++++++++++--- toot/tui/utils.py | 7 +++++++ 3 files changed, 40 insertions(+), 9 deletions(-) diff --git a/toot/tui/entities.py b/toot/tui/entities.py index d916eed..da2d84f 100644 --- a/toot/tui/entities.py +++ b/toot/tui/entities.py @@ -1,6 +1,7 @@ -from datetime import datetime from collections import namedtuple +from .utils import parse_datetime + Author = namedtuple("Author", ["account", "display_name"]) @@ -13,11 +14,6 @@ def get_author(data, instance): return Author(acct, status['account']['display_name']) -def parse_datetime(value): - """Returns an aware datetime in local timezone""" - return datetime.strptime(value, "%Y-%m-%dT%H:%M:%S.%f%z").astimezone() - - class Status: """ A wrapper around the Status entity data fetched from Mastodon. diff --git a/toot/tui/timeline.py b/toot/tui/timeline.py index 85e6d87..4e820eb 100644 --- a/toot/tui/timeline.py +++ b/toot/tui/timeline.py @@ -4,7 +4,7 @@ import webbrowser from toot.utils import format_content -from .utils import highlight_hashtags +from .utils import highlight_hashtags, parse_datetime from .widgets import SelectableText, SelectableColumns logger = logging.getLogger("toot") @@ -160,9 +160,15 @@ class StatusDetails(urwid.Pile): for line in format_content(status.data["content"]): yield ("pack", urwid.Text(highlight_hashtags(line))) - if status.data["card"]: + poll = status.data.get("poll") + if poll: yield ("pack", urwid.Divider()) - yield ("pack", self.build_card(status.data["card"])) + yield ("pack", self.build_poll(poll)) + + card = status.data.get("card") + if card: + yield ("pack", urwid.Divider()) + yield ("pack", self.build_card(card)) # Push things to bottom yield ("weight", 1, urwid.SolidFill(" ")) @@ -190,6 +196,28 @@ class StatusDetails(urwid.Pile): card = urwid.Padding(card, left=1, right=1) return urwid.LineBox(card) + def poll_generator(self, poll): + for option in poll["options"]: + perc = (round(100 * option["votes_count"] / poll["votes_count"]) + if poll["votes_count"] else 0) + yield urwid.Text(option["title"]) + yield urwid.ProgressBar("", "blue_selected", perc) + + if poll["expired"]: + status = "Closed" + else: + expires_at = parse_datetime(poll["expires_at"]).strftime("%Y-%m-%d %H:%M") + status = "Closes on {}".format(expires_at) + + status = "Poll · {} votes · {}".format(poll["votes_count"], status) + yield urwid.Text(("gray", status)) + + def build_poll(self, poll): + contents = list(self.poll_generator(poll)) + poll = urwid.Pile(contents) + poll = urwid.Padding(poll, left=1, right=1) + return urwid.LineBox(poll) + class StatusListItem(SelectableColumns): def __init__(self, status): diff --git a/toot/tui/utils.py b/toot/tui/utils.py index 0f302c5..604230a 100644 --- a/toot/tui/utils.py +++ b/toot/tui/utils.py @@ -1,5 +1,7 @@ import re +from datetime import datetime + HASHTAG_PATTERN = re.compile(r'(?