Clean code with black and create setup.py.
This commit is contained in:
parent
833d16752a
commit
6a65529e06
2
.gitignore
vendored
2
.gitignore
vendored
@ -1,2 +1,4 @@
|
||||
*~
|
||||
**/__pycache__
|
||||
**/.mypy_cache
|
||||
*.egg-info
|
||||
|
@ -17,26 +17,25 @@ class CompileResult(enum.Enum):
|
||||
|
||||
class documentclass(element):
|
||||
|
||||
classname = 'standalone'
|
||||
classname = "standalone"
|
||||
|
||||
templates = {
|
||||
'package': '\\usepackage{pkgoptions}{{{pkgname}}}',
|
||||
'options': '[{content}]',
|
||||
'def': '\\def\\{name}{nargs}{{{value}}}',
|
||||
'content': """\\documentclass{options}{{{classname}}}
|
||||
"package": "\\usepackage{pkgoptions}{{{pkgname}}}",
|
||||
"options": "[{content}]",
|
||||
"def": "\\def\\{name}{nargs}{{{value}}}",
|
||||
"content": """\\documentclass{options}{{{classname}}}
|
||||
{packages}
|
||||
{preamble}
|
||||
\\begin{{document}}
|
||||
{content}
|
||||
\\end{{document}}
|
||||
"""
|
||||
""",
|
||||
}
|
||||
|
||||
output_aux_folder = '.pyltk'
|
||||
auto_tex_folder_name = 'tex2pdf'
|
||||
output_aux_folder = ".pyltk"
|
||||
auto_tex_folder_name = "tex2pdf"
|
||||
|
||||
def __init__(self, classname, childrens=[], options=[],
|
||||
packages=[], preamble=[]):
|
||||
def __init__(self, classname, childrens=[], options=[], packages=[], preamble=[]):
|
||||
super().__init__(parent=None, childrens=childrens)
|
||||
self.options = options
|
||||
self.classname = classname
|
||||
@ -60,38 +59,44 @@ class documentclass(element):
|
||||
self.preamble.append(value)
|
||||
|
||||
def add_def(self, name, nargs, value):
|
||||
self.preamble.append(self.fmt().format('def', {
|
||||
'name': name,
|
||||
'nargs': '#{}'.format(nargs) if nargs > 0 else '',
|
||||
'value': value
|
||||
}))
|
||||
self.preamble.append(
|
||||
self.fmt().format(
|
||||
"def",
|
||||
{
|
||||
"name": name,
|
||||
"nargs": "#{}".format(nargs) if nargs > 0 else "",
|
||||
"value": value,
|
||||
},
|
||||
)
|
||||
)
|
||||
|
||||
def format_preamble(self, defs):
|
||||
return '\n'.join(str(p) for p in self.preamble)
|
||||
return "\n".join(str(p) for p in self.preamble)
|
||||
|
||||
def format_packages(self, pkgs):
|
||||
out = []
|
||||
for pkg in sorted(pkgs):
|
||||
options = ''
|
||||
options = ""
|
||||
if pkgs[pkg] is not True:
|
||||
options = self.format_options(pkgs[pkg])
|
||||
out.append(self.fmt().format('package', {
|
||||
'pkgname': pkg,
|
||||
'pkgoptions': options
|
||||
}))
|
||||
return '\n'.join(out)
|
||||
out.append(
|
||||
self.fmt().format("package", {"pkgname": pkg, "pkgoptions": options})
|
||||
)
|
||||
return "\n".join(out)
|
||||
|
||||
def content(self):
|
||||
return self.fmt().format('content', {
|
||||
'options': self.format_options(self.options),
|
||||
'packages': self.format_packages(self.packages),
|
||||
'preamble': self.format_preamble(self.preamble),
|
||||
'classname': self.classname,
|
||||
'content': super().content()
|
||||
})
|
||||
return self.fmt().format(
|
||||
"content",
|
||||
{
|
||||
"options": self.format_options(self.options),
|
||||
"packages": self.format_packages(self.packages),
|
||||
"preamble": self.format_preamble(self.preamble),
|
||||
"classname": self.classname,
|
||||
"content": super().content(),
|
||||
},
|
||||
)
|
||||
|
||||
def compile(self, outfile, infile='auto', outlog=None,
|
||||
compile_twice=False):
|
||||
def compile(self, outfile, infile="auto", outlog=None, compile_twice=False):
|
||||
""" Compile the given document into a PDF file.
|
||||
|
||||
If infile is not None, and infile already exists, the document
|
||||
@ -116,55 +121,62 @@ class documentclass(element):
|
||||
res = CompileResult.ERROR
|
||||
|
||||
output_aux_folder = os.path.join(outdir, self.output_aux_folder)
|
||||
auto_tex_folder = os.path.join(output_aux_folder,
|
||||
self.auto_tex_folder_name)
|
||||
auto_tex_folder = os.path.join(output_aux_folder, self.auto_tex_folder_name)
|
||||
|
||||
# Make aux directory
|
||||
os.makedirs(output_aux_folder, exist_ok=True)
|
||||
|
||||
# Remove extension if exists
|
||||
if outfile.endswith('.pdf'):
|
||||
if outfile.endswith(".pdf"):
|
||||
outfile = outfile[:-4]
|
||||
|
||||
to_delete = False
|
||||
|
||||
if infile == 'auto':
|
||||
if infile == "auto":
|
||||
os.makedirs(auto_tex_folder, exist_ok=True)
|
||||
infile = '{}/{}.tex'.format(auto_tex_folder, outfile)
|
||||
infile = "{}/{}.tex".format(auto_tex_folder, outfile)
|
||||
|
||||
if infile is None:
|
||||
to_delete = True
|
||||
infile = os.path.join(outdir, '.pyltk-{}.tex'.format(outfile))
|
||||
infile = os.path.join(outdir, ".pyltk-{}.tex".format(outfile))
|
||||
|
||||
to_create = True
|
||||
new_content = self.content()
|
||||
|
||||
# If the input file already exists...
|
||||
if os.path.exists(infile):
|
||||
with open(infile, 'r') as infd:
|
||||
with open(infile, "r") as infd:
|
||||
old_content = infd.read()
|
||||
|
||||
# Content has not changed
|
||||
if old_content == new_content \
|
||||
and os.path.exists(os.path.join(outdir, outfile) + '.pdf') \
|
||||
and os.path.getctime(infile) <= \
|
||||
os.path.getctime(os.path.join(outdir, outfile) + '.pdf'):
|
||||
if (
|
||||
old_content == new_content
|
||||
and os.path.exists(os.path.join(outdir, outfile) + ".pdf")
|
||||
and os.path.getctime(infile)
|
||||
<= os.path.getctime(os.path.join(outdir, outfile) + ".pdf")
|
||||
):
|
||||
to_create = False
|
||||
|
||||
if to_create:
|
||||
with open(infile, 'w') as infd:
|
||||
with open(infile, "w") as infd:
|
||||
infd.write(self.content())
|
||||
call = ['pdflatex', '-halt-on-error',
|
||||
'-output-directory', output_aux_folder,
|
||||
'-jobname', outfile, infile]
|
||||
call = [
|
||||
"pdflatex",
|
||||
"-halt-on-error",
|
||||
"-output-directory",
|
||||
output_aux_folder,
|
||||
"-jobname",
|
||||
outfile,
|
||||
infile,
|
||||
]
|
||||
res = subprocess.call(call, stdout=outlog)
|
||||
if compile_twice:
|
||||
res = subprocess.call(call, stdout=outlog)
|
||||
if res == 0:
|
||||
os.replace(
|
||||
os.path.join(
|
||||
output_aux_folder, outfile + '.pdf'),
|
||||
os.path.join(outdir, outfile + '.pdf'))
|
||||
os.path.join(output_aux_folder, outfile + ".pdf"),
|
||||
os.path.join(outdir, outfile + ".pdf"),
|
||||
)
|
||||
res = CompileResult.SUCCESS
|
||||
else:
|
||||
res = CompileResult.ERROR
|
||||
|
@ -18,7 +18,7 @@ class element:
|
||||
are no subclasses of `element`. """
|
||||
|
||||
# Joiner for childrens
|
||||
sep = '\n'
|
||||
sep = "\n"
|
||||
|
||||
# Automatically add label after element if present
|
||||
autolabel = True
|
||||
@ -26,8 +26,7 @@ class element:
|
||||
# Do not wrap non-element in wrapper_element
|
||||
raw = False
|
||||
|
||||
def __init__(self, parent=None, childrens=[], label=None,
|
||||
raw=False, **kargs):
|
||||
def __init__(self, parent=None, childrens=[], label=None, raw=False, **kargs):
|
||||
""" Create a new element with given parameters.
|
||||
|
||||
Parameters:
|
||||
@ -80,25 +79,25 @@ class element:
|
||||
if isinstance(value, dict):
|
||||
value = self.format_options_dict(value)
|
||||
elif isinstance(value, list) or isinstance(value, tuple):
|
||||
value = ','.join(value)
|
||||
value = ",".join(value)
|
||||
else:
|
||||
value = str(value).strip()
|
||||
if value[0] == '{' and value[1] == '}':
|
||||
if value[0] == "{" and value[1] == "}":
|
||||
value = value[1:-1]
|
||||
opts.append('{key}={{{value}}}'.format(key=k, value=value))
|
||||
return ', '.join(opts)
|
||||
opts.append("{key}={{{value}}}".format(key=k, value=value))
|
||||
return ", ".join(opts)
|
||||
|
||||
def format_options(self, options):
|
||||
if not options:
|
||||
return ''
|
||||
return self.fmt().format('options', {
|
||||
'content': self.format_options_dict(options)
|
||||
})
|
||||
return ""
|
||||
return self.fmt().format(
|
||||
"options", {"content": self.format_options_dict(options)}
|
||||
)
|
||||
|
||||
def format_label(self, label):
|
||||
if not label:
|
||||
return ''
|
||||
return '\\label{{{}}}'.format(label)
|
||||
return ""
|
||||
return "\\label{{{}}}".format(label)
|
||||
|
||||
def __str__(self):
|
||||
out = self.content().strip()
|
||||
@ -111,7 +110,7 @@ class wrapper_element(element):
|
||||
|
||||
""" Wrapper for standard python types working as latex elements. """
|
||||
|
||||
escape_list = ['_', '#', '%']
|
||||
escape_list = ["_", "#", "%"]
|
||||
|
||||
def __init__(self, data, parent=None, autoescape=True):
|
||||
super().__init__(parent=parent)
|
||||
@ -122,7 +121,7 @@ class wrapper_element(element):
|
||||
if not self.autoescape:
|
||||
return s
|
||||
for e in self.escape_list:
|
||||
s = s.replace(e, '\\' + e)
|
||||
s = s.replace(e, "\\" + e)
|
||||
return s
|
||||
|
||||
def content(self):
|
||||
|
@ -7,19 +7,25 @@ class figure(element):
|
||||
""" Class representing a latex figure. """
|
||||
|
||||
templates = {
|
||||
'caption': '\\caption{{{content}}}',
|
||||
'content': """\\begin{{figure}}[{options}]
|
||||
"caption": "\\caption{{{content}}}",
|
||||
"content": """\\begin{{figure}}[{options}]
|
||||
{centered}
|
||||
{inner}
|
||||
{caption}{label}
|
||||
\\end{{figure}}"""
|
||||
\\end{{figure}}""",
|
||||
}
|
||||
|
||||
autolabel = False
|
||||
|
||||
def __init__(self, childrens=None, parent=None,
|
||||
caption=None, options='!h',
|
||||
centered=True, label=None):
|
||||
def __init__(
|
||||
self,
|
||||
childrens=None,
|
||||
parent=None,
|
||||
caption=None,
|
||||
options="!h",
|
||||
centered=True,
|
||||
label=None,
|
||||
):
|
||||
""" Create a figure with given options.
|
||||
|
||||
Parameters:
|
||||
@ -29,18 +35,21 @@ class figure(element):
|
||||
super().__init__(parent, childrens, label=label)
|
||||
self.options = options
|
||||
self.caption = caption
|
||||
self.centered = ''
|
||||
self.centered = ""
|
||||
if centered:
|
||||
self.centered = '\\centering'
|
||||
self.centered = "\\centering"
|
||||
|
||||
def content(self):
|
||||
caption = ''
|
||||
caption = ""
|
||||
if self.caption:
|
||||
caption = self.fmt().format('caption', {'content': self.caption})
|
||||
return self.fmt().format('content', {
|
||||
'options': self.options,
|
||||
'centered': self.centered,
|
||||
'caption': caption,
|
||||
'label': self.format_label(self.label),
|
||||
'inner': super().content()
|
||||
})
|
||||
caption = self.fmt().format("caption", {"content": self.caption})
|
||||
return self.fmt().format(
|
||||
"content",
|
||||
{
|
||||
"options": self.options,
|
||||
"centered": self.centered,
|
||||
"caption": caption,
|
||||
"label": self.format_label(self.label),
|
||||
"inner": super().content(),
|
||||
},
|
||||
)
|
||||
|
@ -7,8 +7,8 @@ class includegraphics(element):
|
||||
""" Class representing a latex includegrahics. """
|
||||
|
||||
templates = {
|
||||
'options': '[{content}]',
|
||||
'element': '\\includegraphics{options}{{{filename}}}'
|
||||
"options": "[{content}]",
|
||||
"element": "\\includegraphics{options}{{{filename}}}",
|
||||
}
|
||||
|
||||
autolabel = False
|
||||
@ -18,7 +18,7 @@ class includegraphics(element):
|
||||
self.filename = filename
|
||||
|
||||
def content(self):
|
||||
return self.fmt().format('element', {
|
||||
'filename': self.filename,
|
||||
'options': self.format_options(self.options)
|
||||
})
|
||||
return self.fmt().format(
|
||||
"element",
|
||||
{"filename": self.filename, "options": self.format_options(self.options)},
|
||||
)
|
||||
|
@ -11,23 +11,19 @@ class inline_element(element):
|
||||
def __init__(self, content, parent=None):
|
||||
super().__init__(parent=parent)
|
||||
self.value = content
|
||||
self.templates = {
|
||||
'wrapper': self.wrapper
|
||||
}
|
||||
self.templates = {"wrapper": self.wrapper}
|
||||
|
||||
def content(self):
|
||||
return self.fmt().format('wrapper', {
|
||||
'value': self.value
|
||||
})
|
||||
return self.fmt().format("wrapper", {"value": self.value})
|
||||
|
||||
|
||||
class it(inline_element):
|
||||
wrapper = '\\textit{{{value}}}'
|
||||
wrapper = "\\textit{{{value}}}"
|
||||
|
||||
|
||||
class bf(inline_element):
|
||||
wrapper = '\\textbf{{{value}}}'
|
||||
wrapper = "\\textbf{{{value}}}"
|
||||
|
||||
|
||||
class mt(inline_element):
|
||||
wrapper = '${value}$'
|
||||
wrapper = "${value}$"
|
||||
|
@ -5,15 +5,11 @@ from .element import element
|
||||
|
||||
class input_element(element):
|
||||
|
||||
templates = {
|
||||
'element': '\\input{{{filename}}}'
|
||||
}
|
||||
templates = {"element": "\\input{{{filename}}}"}
|
||||
|
||||
def __init__(self, filename, parent=None):
|
||||
super().__init__(parent)
|
||||
self.filename = filename.replace('.tex', '')
|
||||
self.filename = filename.replace(".tex", "")
|
||||
|
||||
def content(self):
|
||||
return self.fmt().format('element', {
|
||||
'filename': self.filename
|
||||
})
|
||||
return self.fmt().format("element", {"filename": self.filename})
|
||||
|
@ -6,10 +6,7 @@ from .element import element
|
||||
|
||||
class generic_element(element):
|
||||
|
||||
templates = {
|
||||
'element': '\\{name}{options}{attributes}',
|
||||
'options': '[{content}]'
|
||||
}
|
||||
templates = {"element": "\\{name}{options}{attributes}", "options": "[{content}]"}
|
||||
|
||||
autolabel = False
|
||||
|
||||
@ -17,22 +14,23 @@ class generic_element(element):
|
||||
super().__init__(parent, **kargs)
|
||||
self.name = name
|
||||
if not args:
|
||||
self.attributes = '{}'
|
||||
self.attributes = "{}"
|
||||
else:
|
||||
self.attributes = ''
|
||||
self.attributes = ""
|
||||
for arg in args:
|
||||
self.attributes += '{{{}}}'.format(arg)
|
||||
self.attributes += "{{{}}}".format(arg)
|
||||
|
||||
def content(self):
|
||||
return self.fmt().format('element', {
|
||||
'name': self.name,
|
||||
'attributes': self.attributes,
|
||||
'options': self.format_options(self.options)
|
||||
})
|
||||
return self.fmt().format(
|
||||
"element",
|
||||
{
|
||||
"name": self.name,
|
||||
"attributes": self.attributes,
|
||||
"options": self.format_options(self.options),
|
||||
},
|
||||
)
|
||||
|
||||
|
||||
class factory:
|
||||
|
||||
def __getattr__(self, name):
|
||||
return lambda *args, **kargs: \
|
||||
generic_element(name, *args, **kargs)
|
||||
return lambda *args, **kargs: generic_element(name, *args, **kargs)
|
||||
|
@ -7,7 +7,7 @@ class makebox(element):
|
||||
""" Class representing an unindented makebox. """
|
||||
|
||||
templates = {
|
||||
'content': """{noindent}\\makebox[{width}]{{
|
||||
"content": """{noindent}\\makebox[{width}]{{
|
||||
{inner}
|
||||
}}"""
|
||||
}
|
||||
@ -25,17 +25,20 @@ class makebox(element):
|
||||
|
||||
self.width = width
|
||||
if self.width is None:
|
||||
self.width = '\\textwidth'
|
||||
elif type(self.width) != 'str':
|
||||
self.width = '{}\\textwidth'.format(self.width)
|
||||
self.width = "\\textwidth"
|
||||
elif type(self.width) != "str":
|
||||
self.width = "{}\\textwidth".format(self.width)
|
||||
|
||||
self.noindent = ''
|
||||
self.noindent = ""
|
||||
if self.noindent:
|
||||
self.noindent = '\\noindent'
|
||||
self.noindent = "\\noindent"
|
||||
|
||||
def content(self):
|
||||
return self.fmt().format('content', {
|
||||
'inner': super().content(),
|
||||
'width': self.width,
|
||||
'noindent': self.noindent
|
||||
})
|
||||
return self.fmt().format(
|
||||
"content",
|
||||
{
|
||||
"inner": super().content(),
|
||||
"width": self.width,
|
||||
"noindent": self.noindent,
|
||||
},
|
||||
)
|
||||
|
@ -7,12 +7,12 @@ class axis(element):
|
||||
""" Class representing an axis. """
|
||||
|
||||
templates = {
|
||||
'options': '[{content}]',
|
||||
'legends': '\\legend{{{content}}}',
|
||||
'content': """\\begin{{axis}}{options}
|
||||
"options": "[{content}]",
|
||||
"legends": "\\legend{{{content}}}",
|
||||
"content": """\\begin{{axis}}{options}
|
||||
{inner}
|
||||
{legend}
|
||||
\\end{{axis}}"""
|
||||
\\end{{axis}}""",
|
||||
}
|
||||
|
||||
def __init__(self, *args, parent=None, legend=None, label=None, **kwargs):
|
||||
@ -23,17 +23,24 @@ class axis(element):
|
||||
self.add(arg)
|
||||
|
||||
def content(self):
|
||||
leg = ''
|
||||
leg = ""
|
||||
if self.legend:
|
||||
if type(self.legend) is str:
|
||||
leg = self.legend
|
||||
else:
|
||||
leg = self.fmt().format('legends', {
|
||||
'content': ', '.join('{{{}}}'.format(p.legend)
|
||||
for p in self.childrens)
|
||||
})
|
||||
return self.fmt().format('content', {
|
||||
'options': self.format_options(self.options),
|
||||
'inner': super().content(),
|
||||
'legend': leg
|
||||
})
|
||||
leg = self.fmt().format(
|
||||
"legends",
|
||||
{
|
||||
"content": ", ".join(
|
||||
"{{{}}}".format(p.legend) for p in self.childrens
|
||||
)
|
||||
},
|
||||
)
|
||||
return self.fmt().format(
|
||||
"content",
|
||||
{
|
||||
"options": self.format_options(self.options),
|
||||
"inner": super().content(),
|
||||
"legend": leg,
|
||||
},
|
||||
)
|
||||
|
@ -4,13 +4,11 @@ from .generic_plot import generic_plot
|
||||
|
||||
|
||||
class coordinates_plot(generic_plot):
|
||||
|
||||
def __init__(self, *args, **kargs):
|
||||
super().__init__(*args, **kargs)
|
||||
|
||||
def format_data(self, data):
|
||||
pts = []
|
||||
for d in data:
|
||||
pts.append('({}, {})'.format(
|
||||
*self.format_values(d)))
|
||||
return 'coordinates {{{}}}'.format(''.join(pts))
|
||||
pts.append("({}, {})".format(*self.format_values(d)))
|
||||
return "coordinates {{{}}}".format("".join(pts))
|
||||
|
@ -4,10 +4,8 @@ from .generic_plot import generic_plot
|
||||
|
||||
|
||||
class errorbars_plot(generic_plot):
|
||||
|
||||
def __init__(self, legend, data, precision=5, label=None, options=[]):
|
||||
options = options + [
|
||||
'error bars/.cd', ('y dir', 'both'), ('y explicit')]
|
||||
options = options + ["error bars/.cd", ("y dir", "both"), ("y explicit")]
|
||||
super().__init__(legend, data, label=label, options=options)
|
||||
|
||||
def format_data(self, data):
|
||||
@ -19,7 +17,12 @@ class errorbars_plot(generic_plot):
|
||||
except TypeError:
|
||||
p = d[2]
|
||||
n = p
|
||||
rows.append('({x}, {y}) += (0, {p}) -= (0, {n})'.format(
|
||||
x=self.format_value(x), y=self.format_value(y),
|
||||
p=self.format_value(p), n=self.format_value(n)))
|
||||
return 'coordinates {{{}}}'.format('\n'.join(rows))
|
||||
rows.append(
|
||||
"({x}, {y}) += (0, {p}) -= (0, {n})".format(
|
||||
x=self.format_value(x),
|
||||
y=self.format_value(y),
|
||||
p=self.format_value(p),
|
||||
n=self.format_value(n),
|
||||
)
|
||||
)
|
||||
return "coordinates {{{}}}".format("\n".join(rows))
|
||||
|
@ -7,9 +7,9 @@ class generic_plot(element):
|
||||
""" Class representing a pgfplots plot. """
|
||||
|
||||
templates = {
|
||||
'options': '+[{content}]',
|
||||
'content': """\\addplot{options} {data};{legend}""",
|
||||
'legend': """\\addlegendentry{{{content}}}"""
|
||||
"options": "+[{content}]",
|
||||
"content": """\\addplot{options} {data};{legend}""",
|
||||
"legend": """\\addlegendentry{{{content}}}""",
|
||||
}
|
||||
|
||||
def __init__(self, legend, data, precision=6, label=None, options=[]):
|
||||
@ -21,32 +21,31 @@ class generic_plot(element):
|
||||
|
||||
def format_options(self, options):
|
||||
if not options:
|
||||
return ''
|
||||
return ""
|
||||
opts = []
|
||||
for opt in options:
|
||||
if type(opt) is not str:
|
||||
opt = '{}={}'.format(*opt)
|
||||
opt = "{}={}".format(*opt)
|
||||
opts.append(str(opt))
|
||||
return self.fmt().format('options', {
|
||||
'content': ', '.join(opts)
|
||||
})
|
||||
return self.fmt().format("options", {"content": ", ".join(opts)})
|
||||
|
||||
def format_value(self, value):
|
||||
return '{:.{prec}f}'.format(value, prec=self.precision)
|
||||
return "{:.{prec}f}".format(value, prec=self.precision)
|
||||
|
||||
def format_values(self, values):
|
||||
return [self.format_value(value) for value in values]
|
||||
|
||||
def format_legend(self, legend):
|
||||
if not legend:
|
||||
return ''
|
||||
return self.fmt().format('legend', {
|
||||
'content': legend
|
||||
})
|
||||
return ""
|
||||
return self.fmt().format("legend", {"content": legend})
|
||||
|
||||
def content(self):
|
||||
return self.fmt().format('content', {
|
||||
'data': self.format_data(self.data),
|
||||
'options': self.format_options(self.options),
|
||||
'legend': self.format_legend(self.legend)
|
||||
})
|
||||
return self.fmt().format(
|
||||
"content",
|
||||
{
|
||||
"data": self.format_data(self.data),
|
||||
"options": self.format_options(self.options),
|
||||
"legend": self.format_legend(self.legend),
|
||||
},
|
||||
)
|
||||
|
@ -7,12 +7,12 @@ class semilogyaxis(axis):
|
||||
""" Class representing an axis. """
|
||||
|
||||
templates = {
|
||||
'options': '[{content}]',
|
||||
'legends': '\\legend{{{content}}}',
|
||||
'content': """\\begin{{semilogyaxis}}{options}
|
||||
"options": "[{content}]",
|
||||
"legends": "\\legend{{{content}}}",
|
||||
"content": """\\begin{{semilogyaxis}}{options}
|
||||
{inner}
|
||||
{legend}
|
||||
\\end{{semilogyaxis}}"""
|
||||
\\end{{semilogyaxis}}""",
|
||||
}
|
||||
|
||||
def __init__(self, *args, **kargs):
|
||||
@ -23,12 +23,12 @@ class semilogxaxis(axis):
|
||||
""" Class representing an axis. """
|
||||
|
||||
templates = {
|
||||
'options': '[{content}]',
|
||||
'legends': '\\legend{{{content}}}',
|
||||
'content': """\\begin{{semilogxaxis}}{options}
|
||||
"options": "[{content}]",
|
||||
"legends": "\\legend{{{content}}}",
|
||||
"content": """\\begin{{semilogxaxis}}{options}
|
||||
{inner}
|
||||
{legend}
|
||||
\\end{{semilogxaxis}}"""
|
||||
\\end{{semilogxaxis}}""",
|
||||
}
|
||||
|
||||
def __init__(self, *args, **kargs):
|
||||
|
@ -7,13 +7,12 @@ class resizebox(element):
|
||||
""" Class representing a latex resizebox. """
|
||||
|
||||
templates = {
|
||||
'content': """\\resizebox{{{width}}}{{{height}}}{{
|
||||
"content": """\\resizebox{{{width}}}{{{height}}}{{
|
||||
{inner}
|
||||
}}"""
|
||||
}
|
||||
|
||||
def __init__(self, content=None, parent=None,
|
||||
width="\\linewidth", height="!"):
|
||||
def __init__(self, content=None, parent=None, width="\\linewidth", height="!"):
|
||||
""" Create a resizebox with given width and height.
|
||||
|
||||
Parameters:
|
||||
@ -28,12 +27,11 @@ class resizebox(element):
|
||||
super().__init__(parent, content)
|
||||
self.width = width
|
||||
if type(width) is not str:
|
||||
self.width = '{}\\linewidth'.format(width)
|
||||
self.width = "{}\\linewidth".format(width)
|
||||
self.height = height
|
||||
|
||||
def content(self):
|
||||
return self.fmt().format('content', {
|
||||
'width': self.width,
|
||||
'height': self.height,
|
||||
'inner': super().content()
|
||||
})
|
||||
return self.fmt().format(
|
||||
"content",
|
||||
{"width": self.width, "height": self.height, "inner": super().content()},
|
||||
)
|
||||
|
@ -4,7 +4,6 @@ from .element import element
|
||||
|
||||
|
||||
class strelement(element):
|
||||
|
||||
def __init__(self, content, parent=None):
|
||||
self.inner = content
|
||||
|
||||
|
@ -7,7 +7,7 @@ class subfloat(element):
|
||||
""" Class representing a latex subfloat. """
|
||||
|
||||
templates = {
|
||||
'content': """\\subfloat[{caption}{label}]{{
|
||||
"content": """\\subfloat[{caption}{label}]{{
|
||||
{inner}
|
||||
}}"""
|
||||
}
|
||||
@ -19,8 +19,11 @@ class subfloat(element):
|
||||
self.caption = caption
|
||||
|
||||
def content(self):
|
||||
return self.fmt().format('content', {
|
||||
'caption': self.caption,
|
||||
'label': self.format_label(self.label),
|
||||
'inner': super().content()
|
||||
})
|
||||
return self.fmt().format(
|
||||
"content",
|
||||
{
|
||||
"caption": self.caption,
|
||||
"label": self.format_label(self.label),
|
||||
"inner": super().content(),
|
||||
},
|
||||
)
|
||||
|
@ -8,19 +8,25 @@ class table(element):
|
||||
""" Class representing a latex figure. """
|
||||
|
||||
templates = {
|
||||
'caption': '\\caption{{{content}}}',
|
||||
'content': """\\begin{{table}}[{options}]
|
||||
"caption": "\\caption{{{content}}}",
|
||||
"content": """\\begin{{table}}[{options}]
|
||||
{centered}
|
||||
{inner}
|
||||
{caption}{label}
|
||||
\\end{{table}}"""
|
||||
\\end{{table}}""",
|
||||
}
|
||||
|
||||
autolabel = False
|
||||
|
||||
def __init__(self, childrens=None, parent=None,
|
||||
caption=None, options='!ht',
|
||||
centered=True, label=None):
|
||||
def __init__(
|
||||
self,
|
||||
childrens=None,
|
||||
parent=None,
|
||||
caption=None,
|
||||
options="!ht",
|
||||
centered=True,
|
||||
label=None,
|
||||
):
|
||||
""" Create a table with given options.
|
||||
|
||||
Parameters:
|
||||
@ -30,25 +36,27 @@ class table(element):
|
||||
super().__init__(parent, childrens, label=label)
|
||||
self.options = options
|
||||
self.caption = caption
|
||||
self.centered = ''
|
||||
self.centered = ""
|
||||
if centered:
|
||||
self.centered = '\\centering'
|
||||
self.centered = "\\centering"
|
||||
|
||||
def content(self):
|
||||
caption = ''
|
||||
caption = ""
|
||||
if self.caption:
|
||||
caption = self.fmt().format('caption', {'content': self.caption})
|
||||
return self.fmt().format('content', {
|
||||
'options': self.options,
|
||||
'centered': self.centered,
|
||||
'caption': caption,
|
||||
'label': self.format_label(self.label),
|
||||
'inner': super().content()
|
||||
})
|
||||
caption = self.fmt().format("caption", {"content": self.caption})
|
||||
return self.fmt().format(
|
||||
"content",
|
||||
{
|
||||
"options": self.options,
|
||||
"centered": self.centered,
|
||||
"caption": caption,
|
||||
"label": self.format_label(self.label),
|
||||
"inner": super().content(),
|
||||
},
|
||||
)
|
||||
|
||||
|
||||
class tabledf(table):
|
||||
|
||||
def __init__(self, df, header=None, multilevels=False, fmt=None, **kargs):
|
||||
super().__init__(**kargs)
|
||||
self.add(tabulardf(df, header, multilevels, fmt))
|
||||
|
@ -14,8 +14,9 @@ class row_element(element):
|
||||
|
||||
""" Class representing a row of a tabular element. """
|
||||
|
||||
def __init__(self, columns, parent, label=None,
|
||||
wrapper=False, endline=False, fmt=None):
|
||||
def __init__(
|
||||
self, columns, parent, label=None, wrapper=False, endline=False, fmt=None
|
||||
):
|
||||
super().__init__(parent, columns, label=label, raw=(fmt is not None))
|
||||
self.wrapper = wrapper
|
||||
self.endline = endline
|
||||
@ -31,20 +32,19 @@ class row_element(element):
|
||||
cw = 1 / len(self.childrens)
|
||||
wp = lambda c: self.wrapper(c, width=cw)
|
||||
row = map(wp, row)
|
||||
out = ' & '.join(map(str, row))
|
||||
out = " & ".join(map(str, row))
|
||||
if self.endline:
|
||||
out += '\\\\'
|
||||
out += "\\\\"
|
||||
return out
|
||||
|
||||
|
||||
class hline_element(row_element):
|
||||
|
||||
def __init__(self, command='hline', parent=None):
|
||||
def __init__(self, command="hline", parent=None):
|
||||
super().__init__([], parent)
|
||||
self.command = command
|
||||
|
||||
def content(self):
|
||||
return '\\' + self.command
|
||||
return "\\" + self.command
|
||||
|
||||
|
||||
# instance of hline element
|
||||
@ -55,13 +55,20 @@ class tabular(element):
|
||||
""" Class representing a latex tabular. """
|
||||
|
||||
templates = {
|
||||
'content': """\\begin{{{name}}}{{{columns}}}
|
||||
"content": """\\begin{{{name}}}{{{columns}}}
|
||||
{inner}
|
||||
\\end{{{name}}}"""
|
||||
}
|
||||
|
||||
def __init__(self, parent=None, rows=[], columns=None,
|
||||
autowrap=False, label=None, name='tabular'):
|
||||
def __init__(
|
||||
self,
|
||||
parent=None,
|
||||
rows=[],
|
||||
columns=None,
|
||||
autowrap=False,
|
||||
label=None,
|
||||
name="tabular",
|
||||
):
|
||||
""" Create a tabular with given rows and column specification.
|
||||
|
||||
Parameters:
|
||||
@ -103,21 +110,18 @@ class tabular(element):
|
||||
self.addrow(row, **kargs)
|
||||
|
||||
def content(self):
|
||||
return self.fmt().format('content', {
|
||||
'name': self.name,
|
||||
'columns': self.columns,
|
||||
'inner': super().content()
|
||||
})
|
||||
return self.fmt().format(
|
||||
"content",
|
||||
{"name": self.name, "columns": self.columns, "inner": super().content()},
|
||||
)
|
||||
|
||||
|
||||
class multicolumn(element):
|
||||
""" Class representing a multicolumn element. """
|
||||
|
||||
templates = {
|
||||
'content': """\\multicolumn{{{ncolumns}}}{{{align}}}{{{content}}}"""
|
||||
}
|
||||
templates = {"content": """\\multicolumn{{{ncolumns}}}{{{align}}}{{{content}}}"""}
|
||||
|
||||
def __init__(self, ncolumns, content='', alignment='c', **kargs):
|
||||
def __init__(self, ncolumns, content="", alignment="c", **kargs):
|
||||
super().__init__(**kargs)
|
||||
self.ncolumns = ncolumns
|
||||
self.inner = content
|
||||
@ -126,15 +130,13 @@ class multicolumn(element):
|
||||
def content(self):
|
||||
if self.ncolumns == 1:
|
||||
return self.inner
|
||||
return self.fmt().format('content', {
|
||||
'ncolumns': self.ncolumns,
|
||||
'content': self.inner,
|
||||
'align': self.alignment
|
||||
})
|
||||
return self.fmt().format(
|
||||
"content",
|
||||
{"ncolumns": self.ncolumns, "content": self.inner, "align": self.alignment},
|
||||
)
|
||||
|
||||
|
||||
class tabulardf(tabular):
|
||||
|
||||
def __init__(self, df, header=None, multilevels=False, fmt=None, **kargs):
|
||||
if header is None:
|
||||
multilevels, header = self.create_header(df)
|
||||
@ -145,7 +147,7 @@ class tabulardf(tabular):
|
||||
ncols = len(header)
|
||||
header = [header]
|
||||
|
||||
kargs.setdefault('columns', 'r' * ncols)
|
||||
kargs.setdefault("columns", "r" * ncols)
|
||||
super().__init__(**kargs)
|
||||
self.addrows(header)
|
||||
self.addhline()
|
||||
|
@ -7,17 +7,17 @@ class tikzpicture(element):
|
||||
""" Class representing a latex tikzfigure. """
|
||||
|
||||
templates = {
|
||||
'options': '[{content}]',
|
||||
'content': """\\begin{{tikzpicture}}{options}
|
||||
"options": "[{content}]",
|
||||
"content": """\\begin{{tikzpicture}}{options}
|
||||
{inner}
|
||||
\\end{{tikzpicture}}"""
|
||||
\\end{{tikzpicture}}""",
|
||||
}
|
||||
|
||||
def __init__(self, childrens=None, parent=None, label=None, **kargs):
|
||||
super().__init__(parent, childrens, label=label, **kargs)
|
||||
|
||||
def content(self):
|
||||
return self.fmt().format('content', {
|
||||
'inner': super().content(),
|
||||
'options': self.format_options(self.options)
|
||||
})
|
||||
return self.fmt().format(
|
||||
"content",
|
||||
{"inner": super().content(), "options": self.format_options(self.options)},
|
||||
)
|
||||
|
20
setup.cfg
Normal file
20
setup.cfg
Normal file
@ -0,0 +1,20 @@
|
||||
[flake8]
|
||||
# Use black line length:
|
||||
max-line-length = 88
|
||||
extend-ignore =
|
||||
# See https://github.com/PyCQA/pycodestyle/issues/373
|
||||
E203,
|
||||
|
||||
[mypy]
|
||||
warn_return_any = True
|
||||
warn_unused_configs = True
|
||||
namespace_packages = True
|
||||
|
||||
[tox:tox]
|
||||
envlist = py36,py37,py38,py36-lint
|
||||
|
||||
[testenv]
|
||||
deps =
|
||||
pytest
|
||||
commands =
|
||||
pytest tests
|
37
setup.py
Normal file
37
setup.py
Normal file
@ -0,0 +1,37 @@
|
||||
# -*- encoding: utf-8 -*-
|
||||
|
||||
from setuptools import setup, find_packages
|
||||
|
||||
dev_requires = [
|
||||
"black",
|
||||
"flake8",
|
||||
"flake8-black",
|
||||
"mypy",
|
||||
"pytest",
|
||||
]
|
||||
|
||||
setup(
|
||||
# Name of the package:
|
||||
name="pyltk",
|
||||
# Version of the package:
|
||||
version="0.0.1",
|
||||
# Find the package automatically (include everything):
|
||||
packages=find_packages(),
|
||||
# Author information:
|
||||
author="Mikaël Capelle",
|
||||
author_email="capelle.mikael@gmail.com",
|
||||
# Description of the package:
|
||||
description="Python library to generate and build LaTeX files",
|
||||
include_package_data=True,
|
||||
classifiers=[
|
||||
"Programming Language :: Python",
|
||||
"Programming Language :: Python :: 3",
|
||||
"Programming Language :: Python :: 3.6",
|
||||
"Programming Language :: Python :: 3.7",
|
||||
],
|
||||
# License:
|
||||
license="MIT",
|
||||
# Requirements:
|
||||
install_requires=[],
|
||||
extras_require={"dev": dev_requires},
|
||||
)
|
Loading…
Reference in New Issue
Block a user