clean up newlines in babycode.py
This commit is contained in:
@@ -8,12 +8,15 @@ import re
|
|||||||
|
|
||||||
BABYCODE_VERSION = 8
|
BABYCODE_VERSION = 8
|
||||||
|
|
||||||
|
|
||||||
class BabycodeError(Exception):
|
class BabycodeError(Exception):
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class BabycodeRenderError(BabycodeError):
|
class BabycodeRenderError(BabycodeError):
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class UnknownASTElementError(BabycodeRenderError):
|
class UnknownASTElementError(BabycodeRenderError):
|
||||||
def __init__(self, element_type, element=None):
|
def __init__(self, element_type, element=None):
|
||||||
self.element_type = element_type
|
self.element_type = element_type
|
||||||
@@ -24,6 +27,7 @@ class UnknownASTElementError(BabycodeRenderError):
|
|||||||
message += f' (element: {element})'
|
message += f' (element: {element})'
|
||||||
super().__init__(message)
|
super().__init__(message)
|
||||||
|
|
||||||
|
|
||||||
class BabycodeRenderResult:
|
class BabycodeRenderResult:
|
||||||
def __init__(self, result, mentions=[]):
|
def __init__(self, result, mentions=[]):
|
||||||
self.result = result
|
self.result = result
|
||||||
@@ -232,9 +236,11 @@ NAMED_COLORS = [
|
|||||||
'violet', 'wheat', 'white', 'whitesmoke', 'yellow', 'yellowgreen',
|
'violet', 'wheat', 'white', 'whitesmoke', 'yellow', 'yellowgreen',
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
def make_emoji(name, code):
|
def make_emoji(name, code):
|
||||||
return f' <img class=emoji src="/static/emoji/{name}.png" alt="{name}" title=":{code}:">'
|
return f' <img class=emoji src="/static/emoji/{name}.png" alt="{name}" title=":{code}:">'
|
||||||
|
|
||||||
|
|
||||||
EMOJI = {
|
EMOJI = {
|
||||||
'angry': make_emoji('angry', 'angry'),
|
'angry': make_emoji('angry', 'angry'),
|
||||||
|
|
||||||
@@ -281,6 +287,7 @@ EMOJI = {
|
|||||||
'wink': make_emoji('wink', 'wink'),
|
'wink': make_emoji('wink', 'wink'),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
RSS_EMOJI = {
|
RSS_EMOJI = {
|
||||||
**EMOJI,
|
**EMOJI,
|
||||||
|
|
||||||
@@ -329,8 +336,10 @@ RSS_EMOJI = {
|
|||||||
'wink': '😉',
|
'wink': '😉',
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
TEXT_ONLY = ["code"]
|
TEXT_ONLY = ["code"]
|
||||||
|
|
||||||
|
|
||||||
def tag_code(children, attr):
|
def tag_code(children, attr):
|
||||||
is_inline = children.find('\n') == -1
|
is_inline = children.find('\n') == -1
|
||||||
if is_inline:
|
if is_inline:
|
||||||
@@ -348,11 +357,13 @@ def tag_code(children, attr):
|
|||||||
except PygmentsClassNotFound:
|
except PygmentsClassNotFound:
|
||||||
return unhighlighted
|
return unhighlighted
|
||||||
|
|
||||||
|
|
||||||
def tag_list(children):
|
def tag_list(children):
|
||||||
list_body = re.sub(r" +\n", "<br>", children.strip())
|
list_body = re.sub(r" +\n", "<br>", children.strip())
|
||||||
list_body = re.sub(r"\n\n+", "\1", list_body)
|
list_body = re.sub(r"\n\n+", "\1", list_body)
|
||||||
return " ".join([f"<li>{x}</li>" for x in list_body.split("\1") if x])
|
return " ".join([f"<li>{x}</li>" for x in list_body.split("\1") if x])
|
||||||
|
|
||||||
|
|
||||||
def tag_color(children, attr):
|
def tag_color(children, attr):
|
||||||
if not attr:
|
if not attr:
|
||||||
return f"[color]{children}[/color]"
|
return f"[color]{children}[/color]"
|
||||||
@@ -370,16 +381,19 @@ def tag_color(children, attr):
|
|||||||
# return just the way it was if we can't parse it
|
# return just the way it was if we can't parse it
|
||||||
return f"[color={attr}]{children}[/color]"
|
return f"[color={attr}]{children}[/color]"
|
||||||
|
|
||||||
|
|
||||||
def tag_spoiler(children, attr):
|
def tag_spoiler(children, attr):
|
||||||
spoiler_name = attr if attr else "Spoiler"
|
spoiler_name = attr if attr else "Spoiler"
|
||||||
content = f"<div class='accordion-content post-accordion-content hidden'>{children}</div>"
|
content = f"<div class='accordion-content post-accordion-content hidden'>{children}</div>"
|
||||||
container = f"""<div class='accordion hidden' data-receive='toggleAccordion'><div class='accordion-header'><button type='button' class='accordion-toggle' data-send='toggleAccordion'>+</button><span>{spoiler_name}</span></div>{content}</div>"""
|
container = f"""<div class='accordion hidden' data-receive='toggleAccordion'><div class='accordion-header'><button type='button' class='accordion-toggle' data-send='toggleAccordion'>+</button><span>{spoiler_name}</span></div>{content}</div>"""
|
||||||
return container
|
return container
|
||||||
|
|
||||||
|
|
||||||
def tag_image(children, attr):
|
def tag_image(children, attr):
|
||||||
img = f"<img class=\"post-image\" src=\"{attr}\" alt=\"{children}\">"
|
img = f"<img class=\"post-image\" src=\"{attr}\" alt=\"{children}\">"
|
||||||
return f"<div class=post-img-container>{img}</div>"
|
return f"<div class=post-img-container>{img}</div>"
|
||||||
|
|
||||||
|
|
||||||
TAGS = {
|
TAGS = {
|
||||||
"b": lambda children, attr: f"<strong>{children}</strong>",
|
"b": lambda children, attr: f"<strong>{children}</strong>",
|
||||||
"i": lambda children, attr: f"<em>{children}</em>",
|
"i": lambda children, attr: f"<em>{children}</em>",
|
||||||
@@ -403,6 +417,7 @@ TAGS = {
|
|||||||
"spoiler": tag_spoiler,
|
"spoiler": tag_spoiler,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
def tag_code_rss(children, attr):
|
def tag_code_rss(children, attr):
|
||||||
is_inline = children.find('\n') == -1
|
is_inline = children.find('\n') == -1
|
||||||
if is_inline:
|
if is_inline:
|
||||||
@@ -419,6 +434,7 @@ def tag_url_rss(children, attr):
|
|||||||
|
|
||||||
return f"<a href={attr}>{children}</a>"
|
return f"<a href={attr}>{children}</a>"
|
||||||
|
|
||||||
|
|
||||||
def tag_image_rss(children, attr):
|
def tag_image_rss(children, attr):
|
||||||
if attr.startswith('/'):
|
if attr.startswith('/'):
|
||||||
from flask import current_app
|
from flask import current_app
|
||||||
@@ -427,6 +443,7 @@ def tag_image_rss(children, attr):
|
|||||||
|
|
||||||
return f'<img src="{attr}" alt={children} />'
|
return f'<img src="{attr}" alt={children} />'
|
||||||
|
|
||||||
|
|
||||||
RSS_TAGS = {
|
RSS_TAGS = {
|
||||||
**TAGS,
|
**TAGS,
|
||||||
'img': tag_image_rss,
|
'img': tag_image_rss,
|
||||||
@@ -438,6 +455,7 @@ RSS_TAGS = {
|
|||||||
'small': lambda children, attr: f'<small>{children}</small>'
|
'small': lambda children, attr: f'<small>{children}</small>'
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
VOID_TAGS = {
|
VOID_TAGS = {
|
||||||
'lb': lambda attr: '[',
|
'lb': lambda attr: '[',
|
||||||
'rb': lambda attr: ']',
|
'rb': lambda attr: ']',
|
||||||
@@ -445,6 +463,7 @@ VOID_TAGS = {
|
|||||||
'd': lambda attr: '-',
|
'd': lambda attr: '-',
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
# [img] is considered block for the purposes of collapsing whitespace,
|
# [img] is considered block for the purposes of collapsing whitespace,
|
||||||
# despite being potentially inline (since the resulting <img> tag is inline, but creates a block container around itself and sibling images).
|
# despite being potentially inline (since the resulting <img> tag is inline, but creates a block container around itself and sibling images).
|
||||||
# [code] has a special case in is_inline().
|
# [code] has a special case in is_inline().
|
||||||
@@ -452,6 +471,7 @@ INLINE_TAGS = {
|
|||||||
'b', 'i', 's', 'u', 'color', 'big', 'small', 'url', 'lb', 'rb', 'at', 'd'
|
'b', 'i', 's', 'u', 'color', 'big', 'small', 'url', 'lb', 'rb', 'at', 'd'
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
def is_tag(e, tag=None):
|
def is_tag(e, tag=None):
|
||||||
if e is None:
|
if e is None:
|
||||||
return False
|
return False
|
||||||
@@ -465,9 +485,11 @@ def is_tag(e, tag=None):
|
|||||||
|
|
||||||
return e['name'] == tag
|
return e['name'] == tag
|
||||||
|
|
||||||
|
|
||||||
def is_text(e):
|
def is_text(e):
|
||||||
return isinstance(e, str)
|
return isinstance(e, str)
|
||||||
|
|
||||||
|
|
||||||
def is_inline(e):
|
def is_inline(e):
|
||||||
if e is None:
|
if e is None:
|
||||||
return False # i think
|
return False # i think
|
||||||
@@ -483,24 +505,6 @@ def is_inline(e):
|
|||||||
|
|
||||||
return e['type'] != 'rule'
|
return e['type'] != 'rule'
|
||||||
|
|
||||||
def make_mention(e, mentions):
|
|
||||||
from ..models import Users
|
|
||||||
from flask import url_for, current_app
|
|
||||||
with current_app.test_request_context('/'):
|
|
||||||
target_user = Users.find({'username': e['name'].lower()})
|
|
||||||
if not target_user:
|
|
||||||
return f"@{e['name']}"
|
|
||||||
|
|
||||||
mention_data = {
|
|
||||||
'mention_text': f"@{e['name']}",
|
|
||||||
'mentioned_user_id': int(target_user.id),
|
|
||||||
"start": e['start'],
|
|
||||||
"end": e['end'],
|
|
||||||
}
|
|
||||||
if mention_data not in mentions:
|
|
||||||
mentions.append(mention_data)
|
|
||||||
|
|
||||||
return f"<a class='mention{' display' if target_user.has_display_name() else ''}' href='{url_for('users.page', username=target_user.username)}' title='@{target_user.username}' data-init='highlightMentions' data-username='{target_user.username}'>{'@' if not target_user.has_display_name() else ''}{target_user.get_readable_name()}</a>"
|
|
||||||
|
|
||||||
def should_collapse(text, surrounding):
|
def should_collapse(text, surrounding):
|
||||||
if not isinstance(text, str):
|
if not isinstance(text, str):
|
||||||
|
|||||||
Reference in New Issue
Block a user