mirror of
https://github.com/liberatedsystems/openCom-Companion.git
synced 2025-02-22 01:09:51 +01:00
Removed library
This commit is contained in:
parent
6b2cf01c69
commit
09db4a9328
@ -1,132 +0,0 @@
|
||||
# converts some HTML tags to BBCode
|
||||
# pass --debug to save the output to readme.finalpass
|
||||
# may be better off replacing this with html to markdown (and then to bbcode). Lepture recommeds a JS html to markdown converter: sundown
|
||||
from bs4 import BeautifulSoup, NavigableString
|
||||
import argparse
|
||||
|
||||
def handle_font_tag(tag, replacements):
|
||||
"""Handles the conversion of <font> tag with attributes like color and size."""
|
||||
attributes = []
|
||||
if 'color' in tag.attrs:
|
||||
attributes.append(f"COLOR={tag['color']}")
|
||||
if 'size' in tag.attrs:
|
||||
attributes.append(f"SIZE={tag['size']}")
|
||||
if 'face' in tag.attrs:
|
||||
attributes.append(f"FONT={tag['face']}")
|
||||
|
||||
inner_content = ''.join(recursive_html_to_bbcode(child, replacements) for child in tag.children)
|
||||
if attributes:
|
||||
# Nest all attributes. Example: [COLOR=red][SIZE=5]content[/SIZE][/COLOR]
|
||||
for attr in reversed(attributes):
|
||||
inner_content = f"[{attr}]{inner_content}[/{attr.split('=')[0]}]"
|
||||
return inner_content
|
||||
|
||||
def handle_style_tag(tag, replacements):
|
||||
"""Handles the conversion of tags with style attributes like color, size, and font."""
|
||||
attributes = []
|
||||
style = tag.attrs.get('style', '')
|
||||
|
||||
# Extracting CSS properties
|
||||
css_properties = {item.split(':')[0].strip(): item.split(':')[1].strip() for item in style.split(';') if ':' in item}
|
||||
|
||||
# Mapping CSS properties to BBCode
|
||||
if 'color' in css_properties:
|
||||
attributes.append(f"COLOR={css_properties['color']}")
|
||||
if 'font-size' in css_properties:
|
||||
attributes.append(f"SIZE={css_properties['font-size']}")
|
||||
if 'font-family' in css_properties:
|
||||
attributes.append(f"FONT={css_properties['font-family']}")
|
||||
if 'text-decoration' in css_properties and 'line-through' in css_properties['text-decoration']:
|
||||
attributes.append("S") # Assume strike-through
|
||||
if 'text-decoration' in css_properties and 'underline' in css_properties['text-decoration']:
|
||||
attributes.append("U")
|
||||
if 'font-weight' in css_properties:
|
||||
if css_properties['font-weight'].lower() == 'bold' or (css_properties['font-weight'].isdigit() and int(css_properties['font-weight']) >= 700):
|
||||
attributes.append("B") # Assume bold
|
||||
|
||||
inner_content = ''.join(recursive_html_to_bbcode(child, replacements) for child in tag.children)
|
||||
if attributes:
|
||||
# Nest all attributes
|
||||
for attr in reversed(attributes):
|
||||
if '=' in attr: # For attributes with values
|
||||
inner_content = f"[{attr}]{inner_content}[/{attr.split('=')[0]}]"
|
||||
else: # For simple BBCode tags like [B], [I], [U], [S]
|
||||
inner_content = f"[{attr}]{inner_content}[/{attr}]"
|
||||
return inner_content
|
||||
|
||||
def recursive_html_to_bbcode(element):
|
||||
"""Recursively convert HTML elements to BBCode."""
|
||||
bbcode = ''
|
||||
|
||||
if isinstance(element, NavigableString):
|
||||
bbcode += str(element)
|
||||
elif element.name == 'details':
|
||||
# Handle <details> tag
|
||||
summary = element.find('summary')
|
||||
spoiler_title = ''
|
||||
if summary:
|
||||
# Get the summary content and remove the summary element
|
||||
spoiler_title = '=' + ''.join([recursive_html_to_bbcode(child) for child in summary.contents])
|
||||
summary.decompose()
|
||||
|
||||
# Process remaining content
|
||||
content = ''.join([recursive_html_to_bbcode(child) for child in element.contents])
|
||||
bbcode += f'[SPOILER{spoiler_title}]{content}[/SPOILER]'
|
||||
elif element.name == 'summary':
|
||||
# Skip summary tag as it's handled in details
|
||||
return ''
|
||||
else:
|
||||
# Handle other tags or pass through
|
||||
content = ''.join([recursive_html_to_bbcode(child) for child in element.contents])
|
||||
bbcode += content
|
||||
|
||||
return bbcode
|
||||
|
||||
def html_to_bbcode(html):
|
||||
replacements = {
|
||||
'b': 'B',
|
||||
'strong': 'B',
|
||||
'i': 'I',
|
||||
'em': 'I',
|
||||
'u': 'U',
|
||||
's': 'S',
|
||||
'sub': 'SUB',
|
||||
'sup': 'SUP',
|
||||
'p': '', # Handled by default
|
||||
'ul': 'LIST',
|
||||
'ol': 'LIST=1',
|
||||
'li': '*', # Special handling in recursive function
|
||||
'font': '', # To be handled for attributes
|
||||
'blockquote': 'QUOTE',
|
||||
'pre': 'CODE',
|
||||
'code': 'ICODE',
|
||||
'a': 'URL', # Special handling for attributes
|
||||
'img': 'IMG' # Special handling for attributes
|
||||
}
|
||||
|
||||
soup = BeautifulSoup(html, 'html.parser')
|
||||
return recursive_html_to_bbcode(soup)
|
||||
|
||||
def process_html(input_html, debug=False, output_file=None):
|
||||
converted_bbcode = html_to_bbcode(input_html)
|
||||
|
||||
if debug:
|
||||
with open(output_file, 'w', encoding='utf-8') as file:
|
||||
file.write(converted_bbcode)
|
||||
else:
|
||||
return converted_bbcode
|
||||
|
||||
if __name__ == "__main__":
|
||||
parser = argparse.ArgumentParser(description="Convert HTML to BBCode with optional debugging output.")
|
||||
parser.add_argument('input_file', type=str, help='Input HTML file path')
|
||||
parser.add_argument('--debug', action='store_true', help='Save output to readme.finalpass for debugging')
|
||||
|
||||
args = parser.parse_args()
|
||||
input_file = args.input_file
|
||||
output_file = 'readme.finalpass' if args.debug else None
|
||||
|
||||
with open(input_file, 'r', encoding='utf-8') as file:
|
||||
html_content = file.read()
|
||||
|
||||
# Call the processing function
|
||||
process_html(html_content, debug=args.debug, output_file=output_file)
|
@ -1,67 +0,0 @@
|
||||
# uses a custom mistune renderer to convert Markdown to BBCode. The custom renderer is defined in the bbcode.py file.
|
||||
# pass --debug to save the output to readme.1stpass (main.py) and readme.finalpass (html2bbcode)
|
||||
# for further debugging, you can convert the markdown file to AST using md2ast.py. Remember to load the plugin(s) you want to test.
|
||||
|
||||
#standard library
|
||||
import argparse
|
||||
import sys
|
||||
import RNS
|
||||
|
||||
# mistune
|
||||
import mistune
|
||||
from mistune.plugins.formatting import strikethrough, mark, superscript, subscript, insert
|
||||
from mistune.plugins.table import table, table_in_list
|
||||
from mistune.plugins.footnotes import footnotes
|
||||
from mistune.plugins.task_lists import task_lists
|
||||
from mistune.plugins.def_list import def_list
|
||||
from mistune.plugins.abbr import abbr
|
||||
from mistune.plugins.spoiler import spoiler
|
||||
|
||||
if RNS.vendor.platformutils.is_android():
|
||||
from .plugins.merge_lists import merge_ordered_lists
|
||||
from .renderers.bbcode import BBCodeRenderer
|
||||
from .html2bbcode import process_html
|
||||
else:
|
||||
from sbapp.md2bbcode.plugins.merge_lists import merge_ordered_lists
|
||||
from sbapp.md2bbcode.renderers.bbcode import BBCodeRenderer
|
||||
from sbapp.md2bbcode.html2bbcode import process_html
|
||||
|
||||
def convert_markdown_to_bbcode(markdown_text, domain):
|
||||
# Create a Markdown parser instance using the custom BBCode renderer
|
||||
markdown_parser = mistune.create_markdown(renderer=BBCodeRenderer(domain=domain), plugins=[strikethrough, mark, superscript, subscript, insert, table, footnotes, task_lists, def_list, abbr, spoiler, table_in_list, merge_ordered_lists])
|
||||
|
||||
# Convert Markdown text to BBCode
|
||||
return markdown_parser(markdown_text)
|
||||
|
||||
def process_readme(markdown_text, domain=None, debug=False):
|
||||
# Convert Markdown to BBCode
|
||||
bbcode_text = convert_markdown_to_bbcode(markdown_text, domain)
|
||||
|
||||
# Convert BBCode formatted as HTML to final BBCode
|
||||
final_bbcode = process_html(bbcode_text, debug, 'readme.finalpass')
|
||||
|
||||
return final_bbcode
|
||||
|
||||
def main():
|
||||
parser = argparse.ArgumentParser(description='Convert Markdown file to BBCode with HTML processing.')
|
||||
parser.add_argument('input', help='Input Markdown file path')
|
||||
parser.add_argument('--domain', help='Domain to prepend to relative URLs')
|
||||
parser.add_argument('--debug', action='store_true', help='Output intermediate results to files for debugging')
|
||||
args = parser.parse_args()
|
||||
|
||||
if args.input == '-':
|
||||
# Read Markdown content from stdin
|
||||
markdown_text = sys.stdin.read()
|
||||
else:
|
||||
with open(args.input, 'r', encoding='utf-8') as md_file:
|
||||
markdown_text = md_file.read()
|
||||
|
||||
# Process the readme and get the final BBCode
|
||||
final_bbcode = process_readme(markdown_text, args.domain, args.debug)
|
||||
|
||||
# Optionally, print final BBCode to console
|
||||
if not args.debug:
|
||||
print(final_bbcode)
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
@ -1,47 +0,0 @@
|
||||
# this is for debugging the custom mistune renderer bbcode.py
|
||||
import argparse
|
||||
import mistune
|
||||
import json # Import the json module for serialization
|
||||
from mistune.plugins.formatting import strikethrough, mark, superscript, subscript, insert
|
||||
from mistune.plugins.table import table, table_in_list
|
||||
from mistune.plugins.footnotes import footnotes
|
||||
from mistune.plugins.task_lists import task_lists
|
||||
from mistune.plugins.def_list import def_list
|
||||
from mistune.plugins.abbr import abbr
|
||||
from mistune.plugins.spoiler import spoiler
|
||||
|
||||
#local
|
||||
from sbapp.md2bbcode.plugins.merge_lists import merge_ordered_lists
|
||||
|
||||
def convert_markdown_to_ast(input_filepath, output_filepath):
|
||||
# Initialize Markdown parser with no renderer to produce an AST
|
||||
markdown_parser = mistune.create_markdown(renderer=None, plugins=[strikethrough, mark, superscript, subscript, insert, table, footnotes, task_lists, def_list, abbr, spoiler, table_in_list, merge_ordered_lists])
|
||||
|
||||
# Read the input Markdown file
|
||||
with open(input_filepath, 'r', encoding='utf-8') as md_file:
|
||||
markdown_text = md_file.read()
|
||||
|
||||
# Convert Markdown text to AST
|
||||
ast_text = markdown_parser(markdown_text)
|
||||
|
||||
# Serialize the AST to a JSON string
|
||||
ast_json = json.dumps(ast_text, indent=4)
|
||||
|
||||
# Write the output AST to a new file in JSON format
|
||||
with open(output_filepath, 'w', encoding='utf-8') as ast_file:
|
||||
ast_file.write(ast_json)
|
||||
|
||||
def main():
|
||||
# Create argument parser
|
||||
parser = argparse.ArgumentParser(description='Convert Markdown file to AST file (JSON format).')
|
||||
# Add arguments
|
||||
parser.add_argument('input', help='Input Markdown file path')
|
||||
parser.add_argument('output', help='Output AST file path (JSON format)')
|
||||
# Parse arguments
|
||||
args = parser.parse_args()
|
||||
|
||||
# Convert the Markdown to AST using the provided paths
|
||||
convert_markdown_to_ast(args.input, args.output)
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
@ -1,83 +0,0 @@
|
||||
from typing import Dict, Any, List
|
||||
|
||||
def merge_ordered_lists(md):
|
||||
"""
|
||||
A plugin to merge consecutive "top-level" ordered lists into one,
|
||||
and also attach any intervening code blocks or blank lines to the
|
||||
last list item so that the final BBCode appears as a single list
|
||||
with multiple steps.
|
||||
|
||||
This relies on a few assumptions:
|
||||
1) The only tokens between two ordered lists that should be merged
|
||||
are code blocks or blank lines (not normal paragraphs).
|
||||
2) We want any code block(s) right after a list item to appear in
|
||||
that same bullet item.
|
||||
"""
|
||||
|
||||
def rewrite_tokens(md, state):
|
||||
tokens = state.tokens
|
||||
merged = []
|
||||
i = 0
|
||||
|
||||
while i < len(tokens):
|
||||
token = tokens[i]
|
||||
|
||||
# Check if this token is a top-level ordered list
|
||||
if (
|
||||
token["type"] == "list"
|
||||
and token.get("attrs", {}).get("ordered", False)
|
||||
and token.get("attrs", {}).get("depth", 0) == 0
|
||||
):
|
||||
# Start new merged list
|
||||
current_depth = token["attrs"]["depth"]
|
||||
list_items = list(token["children"]) # bullet items in the first list
|
||||
i += 1
|
||||
|
||||
# Continue until we run into something that's not:
|
||||
# another top-level ordered list,
|
||||
# or code blocks / blank lines (which we'll attach to the last bullet).
|
||||
while i < len(tokens):
|
||||
nxt = tokens[i]
|
||||
|
||||
# If there's another ordered list at the same depth, merge its bullet items
|
||||
if (
|
||||
nxt["type"] == "list"
|
||||
and nxt.get("attrs", {}).get("ordered", False)
|
||||
and nxt.get("attrs", {}).get("depth", 0) == current_depth
|
||||
):
|
||||
list_items.extend(nxt["children"])
|
||||
i += 1
|
||||
|
||||
# If there's a code block or blank line, attach it to the *last* bullet item.
|
||||
elif nxt["type"] in ["block_code", "blank_line"]:
|
||||
if list_items: # attach to last bullet item, if any
|
||||
list_items[-1]["children"].append(nxt)
|
||||
i += 1
|
||||
|
||||
else:
|
||||
# Not a same-depth list or code block—stop merging
|
||||
break
|
||||
|
||||
# Create single merged list token
|
||||
merged.append(
|
||||
{
|
||||
"type": "list",
|
||||
"children": list_items,
|
||||
"attrs": {
|
||||
"ordered": True,
|
||||
"depth": current_depth,
|
||||
},
|
||||
}
|
||||
)
|
||||
|
||||
else:
|
||||
# If not a top-level ordered list, just keep it as-is
|
||||
merged.append(token)
|
||||
i += 1
|
||||
|
||||
# Replace the old tokens with the merged version
|
||||
state.tokens = merged
|
||||
|
||||
# Attach to before_render_hooks so we can manipulate tokens before rendering
|
||||
md.before_render_hooks.append(rewrite_tokens)
|
||||
return md
|
@ -1,240 +0,0 @@
|
||||
from mistune.core import BaseRenderer
|
||||
from mistune.util import escape as escape_text, striptags, safe_entity
|
||||
from urllib.parse import urljoin, urlparse
|
||||
|
||||
|
||||
class BBCodeRenderer(BaseRenderer):
|
||||
"""A renderer for converting Markdown to BBCode."""
|
||||
_escape: bool
|
||||
NAME = 'bbcode'
|
||||
|
||||
def __init__(self, escape=False, domain=None):
|
||||
super(BBCodeRenderer, self).__init__()
|
||||
self._escape = escape
|
||||
self.domain = domain
|
||||
|
||||
def render_token(self, token, state):
|
||||
func = self._get_method(token['type'])
|
||||
attrs = token.get('attrs')
|
||||
|
||||
if 'raw' in token:
|
||||
text = token['raw']
|
||||
elif 'children' in token:
|
||||
text = self.render_tokens(token['children'], state)
|
||||
else:
|
||||
if attrs:
|
||||
return func(**attrs)
|
||||
else:
|
||||
return func()
|
||||
|
||||
if attrs:
|
||||
return func(text, **attrs)
|
||||
else:
|
||||
return func(text)
|
||||
|
||||
def safe_url(self, url: str) -> str:
|
||||
# Simple URL sanitization
|
||||
if url.startswith(('javascript:', 'vbscript:', 'data:')):
|
||||
return '#harmful-link'
|
||||
# Check if the URL is absolute by looking for a netloc part in the URL
|
||||
if not urlparse(url).netloc:
|
||||
url = urljoin(self.domain, url)
|
||||
return url
|
||||
|
||||
def text(self, text: str) -> str:
|
||||
if self._escape:
|
||||
return escape_text(text)
|
||||
return text
|
||||
|
||||
def emphasis(self, text: str) -> str:
|
||||
return '[i]' + text + '[/i]'
|
||||
|
||||
def strong(self, text: str) -> str:
|
||||
return '[b]' + text + '[/b]'
|
||||
|
||||
def link(self, text: str, url: str, title=None) -> str:
|
||||
return '[url=' + self.safe_url(url) + ']' + text + '[/url]'
|
||||
|
||||
def image(self, text: str, url: str, title=None) -> str:
|
||||
alt_text = f' alt="{text}"' if text else ''
|
||||
img_tag = f'[img{alt_text}]' + self.safe_url(url) + '[/img]'
|
||||
# Check if alt text starts with 'pixel' and treat it as pixel art
|
||||
if text and text.lower().startswith('pixel'):
|
||||
return f'[pixelate]{img_tag}[/pixelate]'
|
||||
return img_tag
|
||||
|
||||
def codespan(self, text: str) -> str:
|
||||
return '[icode]' + text + '[/icode]'
|
||||
|
||||
def linebreak(self) -> str:
|
||||
return '\n'
|
||||
|
||||
def softbreak(self) -> str:
|
||||
return '\n'
|
||||
|
||||
def inline_html(self, html: str) -> str:
|
||||
if self._escape:
|
||||
return escape_text(html)
|
||||
return html
|
||||
|
||||
def paragraph(self, text: str) -> str:
|
||||
return text + '\n\n'
|
||||
|
||||
def heading(self, text: str, level: int, **attrs) -> str:
|
||||
if 1 <= level <= 3:
|
||||
return f"[HEADING={level}]{text}[/HEADING]\n"
|
||||
else:
|
||||
# Handle cases where level is outside 1-3
|
||||
return f"[HEADING=3]{text}[/HEADING]\n"
|
||||
|
||||
def blank_line(self) -> str:
|
||||
return ''
|
||||
|
||||
def thematic_break(self) -> str:
|
||||
return '[hr][/hr]\n'
|
||||
|
||||
def block_text(self, text: str) -> str:
|
||||
return text
|
||||
|
||||
def block_code(self, code: str, **attrs) -> str:
|
||||
# Renders blocks of code using the language specified in Markdown
|
||||
special_cases = {
|
||||
'plaintext': None # Default [CODE]
|
||||
}
|
||||
|
||||
if 'info' in attrs:
|
||||
lang_info = safe_entity(attrs['info'].strip())
|
||||
lang = lang_info.split(None, 1)[0].lower()
|
||||
# Check if the language needs special handling
|
||||
bbcode_lang = special_cases.get(lang, lang) # Use the special case if it exists, otherwise use lang as is
|
||||
if bbcode_lang:
|
||||
return f"[CODE={bbcode_lang}]{escape_text(code)}[/CODE]\n"
|
||||
else:
|
||||
return f"[CODE]{escape_text(code)}[/CODE]\n"
|
||||
else:
|
||||
# No language specified, render with a generic [CODE] tag
|
||||
return f"[CODE]{escape_text(code)}[/CODE]\n"
|
||||
|
||||
def block_quote(self, text: str) -> str:
|
||||
return '[QUOTE]\n' + text + '[/QUOTE]\n'
|
||||
|
||||
def block_html(self, html: str) -> str:
|
||||
if self._escape:
|
||||
return '<p>' + escape_text(html.strip()) + '</p>\n'
|
||||
return html + '\n'
|
||||
|
||||
def block_error(self, text: str) -> str:
|
||||
return '[color=red][icode]' + text + '[/icode][/color]\n'
|
||||
|
||||
def list(self, text: str, ordered: bool, **attrs) -> str:
|
||||
depth = 0; sln = ""; tli = ""
|
||||
if "depth" in attrs: depth = attrs["depth"]
|
||||
if depth != 0: sln = "\n"
|
||||
if depth == 0: tli = "\n"
|
||||
def remove_empty_lines(text):
|
||||
lines = text.split('\n')
|
||||
non_empty_lines = [line for line in lines if line.strip() != '']
|
||||
nli = ""; dlm = "\n"+" "*depth
|
||||
if depth != 0: nli = dlm
|
||||
return nli+dlm.join(non_empty_lines)
|
||||
|
||||
text = remove_empty_lines(text)
|
||||
|
||||
return sln+text+"\n"+tli
|
||||
# return '[{}]'.format(tag) + text + '[/list]\n'
|
||||
|
||||
def list_item(self, text: str) -> str:
|
||||
return '• ' + text + '\n'
|
||||
|
||||
def strikethrough(self, text: str) -> str:
|
||||
return '[s]' + text + '[/s]'
|
||||
|
||||
def mark(self, text: str) -> str:
|
||||
# Simulate the mark effect with a background color in BBCode
|
||||
return '[mark]' + text + '[/mark]'
|
||||
|
||||
def insert(self, text: str) -> str:
|
||||
# Use underline to represent insertion
|
||||
return '[u]' + text + '[/u]'
|
||||
|
||||
def superscript(self, text: str) -> str:
|
||||
return '[sup]' + text + '[/sup]'
|
||||
|
||||
def subscript(self, text: str) -> str:
|
||||
return '[sub]' + text + '[/sub]'
|
||||
|
||||
def inline_spoiler(self, text: str) -> str:
|
||||
return '[ISPOILER]' + text + '[/ISPOILER]'
|
||||
|
||||
def block_spoiler(self, text: str) -> str:
|
||||
return '[SPOILER]\n' + text + '\n[/SPOILER]'
|
||||
|
||||
def footnote_ref(self, key: str, index: int):
|
||||
# Use superscript for the footnote reference
|
||||
return f'[sup][u][JUMPTO=fn-{index}]{index}[/JUMPTO][/u][/sup]'
|
||||
|
||||
def footnotes(self, text: str):
|
||||
# Optionally wrap all footnotes in a specific section if needed
|
||||
return '[b]Footnotes:[/b]\n' + text
|
||||
|
||||
def footnote_item(self, text: str, key: str, index: int):
|
||||
# Define the footnote with an anchor at the end of the document
|
||||
return f'[ANAME=fn-{index}]{index}[/ANAME]. {text}'
|
||||
|
||||
def table(self, children, **attrs):
|
||||
# Starting with a full-width table by default if not specified
|
||||
# width = attrs.get('width', '100%') # comment out until XF 2.3
|
||||
# return f'[TABLE width="{width}"]\n' + children + '[/TABLE]\n' # comment out until XF 2.3
|
||||
return '[TABLE]\n' + children + '[/TABLE]\n'
|
||||
|
||||
def table_head(self, children, **attrs):
|
||||
return '[TR]\n' + children + '[/TR]\n'
|
||||
|
||||
def table_body(self, children, **attrs):
|
||||
return children
|
||||
|
||||
def table_row(self, children, **attrs):
|
||||
return '[TR]\n' + children + '[/TR]\n'
|
||||
|
||||
def table_cell(self, text, align=None, head=False, **attrs):
|
||||
# BBCode does not support direct cell alignment,
|
||||
# use [LEFT], [CENTER], or [RIGHT] tags
|
||||
|
||||
# Use th for header cells and td for normal cells
|
||||
tag = 'TH' if head else 'TD'
|
||||
|
||||
# Initialize alignment tags
|
||||
alignment_start = ''
|
||||
alignment_end = ''
|
||||
|
||||
if align == 'center':
|
||||
alignment_start = '[CENTER]'
|
||||
alignment_end = '[/CENTER]'
|
||||
elif align == 'right':
|
||||
alignment_start = '[RIGHT]'
|
||||
alignment_end = '[/RIGHT]'
|
||||
elif align == 'left':
|
||||
alignment_start = '[LEFT]'
|
||||
alignment_end = '[/LEFT]'
|
||||
|
||||
return f'[{tag}]{alignment_start}{text}{alignment_end}[/{tag}]\n'
|
||||
|
||||
def task_list_item(self, text: str, checked: bool = False) -> str:
|
||||
# Using emojis to represent the checkbox
|
||||
checkbox_emoji = '' if checked else ''
|
||||
return checkbox_emoji + ' ' + text + '\n'
|
||||
|
||||
def def_list(self, text: str) -> str:
|
||||
# No specific BBCode tag for <dl>, so we just use the plain text grouping
|
||||
return '\n' + text + '\n'
|
||||
|
||||
def def_list_head(self, text: str) -> str:
|
||||
return '[b]' + text + '[/b]' + ' ' + ':' + '\n'
|
||||
|
||||
def def_list_item(self, text: str) -> str:
|
||||
return '[INDENT]' + text + '[/INDENT]\n'
|
||||
|
||||
def abbr(self, text: str, title: str) -> str:
|
||||
if title:
|
||||
return f'[abbr={title}]{text}[/abbr]'
|
||||
return text
|
Loading…
x
Reference in New Issue
Block a user