From 921d2b099a4757b0704dced331449a3c4527f78d Mon Sep 17 00:00:00 2001 From: "matthias@quintern.xyz" Date: Mon, 17 Feb 2025 02:16:22 +0100 Subject: [PATCH] refactor with own translation package --- scripts/formulary.py | 81 +++++ scripts/util/gen_tex_colorscheme.py | 10 + src/ch/el.tex | 316 +++++++++------- src/ch/misc.tex | 26 +- src/comp/ad.tex | 2 +- src/comp/qmb.tex | 2 +- src/constants.tex | 7 + src/main.tex | 69 +--- src/math/linalg.tex | 3 +- src/pkg/mqconstant.sty | 62 ++++ src/pkg/mqformula.sty | 250 +++++++++++++ src/pkg/mqfqname.sty | 209 +++++++++++ src/pkg/mqlua.sty | 88 +++++ .../mqperiodictable.sty} | 6 +- src/pkg/mqquantity.sty | 43 +++ src/pkg/mqtranslation.sty | 177 +++++++++ src/quantities.tex | 16 +- src/quantum_computing.tex | 10 +- src/test.tex | 25 +- src/util/colorscheme.tex | 60 +-- src/util/environments.tex | 344 ------------------ src/util/translation.tex | 102 ------ 22 files changed, 1233 insertions(+), 675 deletions(-) create mode 100644 scripts/formulary.py create mode 100644 scripts/util/gen_tex_colorscheme.py create mode 100644 src/pkg/mqconstant.sty create mode 100644 src/pkg/mqformula.sty create mode 100644 src/pkg/mqfqname.sty create mode 100644 src/pkg/mqlua.sty rename src/{util/periodic_table.tex => pkg/mqperiodictable.sty} (98%) create mode 100644 src/pkg/mqquantity.sty create mode 100644 src/pkg/mqtranslation.sty delete mode 100644 src/util/translation.tex diff --git a/scripts/formulary.py b/scripts/formulary.py new file mode 100644 index 0000000..86cea3b --- /dev/null +++ b/scripts/formulary.py @@ -0,0 +1,81 @@ +#!/usr/bin env python3 +import os +import matplotlib.pyplot as plt +import numpy as np +import math +import scipy as scp + +import matplotlib as mpl +mpl.rcParams["font.family"] = "serif" +mpl.rcParams["mathtext.fontset"] = "stix" +mpl.rcParams["text.usetex"] = True +mpl.rcParams['text.latex.preamble'] = r'\usepackage{amsmath}\usepackage{siunitx}' + + +if __name__ == "__main__": # make relative imports work as described here: https://peps.python.org/pep-0366/#proposed-change + if __package__ is None: + __package__ = "formulary" + import sys + filepath = os.path.realpath(os.path.abspath(__file__)) + sys.path.insert(0, os.path.dirname(os.path.dirname(filepath))) + +from util.mpl_colorscheme import set_mpl_colorscheme +import util.colorschemes as cs +from util.gen_tex_colorscheme import generate_latex_colorscheme +# SET THE COLORSCHEME +# hard white and black +# cs.p_gruvbox["fg0"] = "#000000" +# cs.p_gruvbox["bg0"] = "#ffffff" +# COLORSCHEME = cs.gruvbox_light() +# COLORSCHEME = cs.gruvbox_dark() +# cs.p_tum["fg0"] = cs.p_tum["alt-blue"] +COLORSCHEME = cs.tum() +# COLORSCHEME = cs.legacy() + +tex_src_path = "../src/" +img_out_dir = os.path.join(tex_src_path, "img") +filetype = ".pdf" +skipasserts = False + +full = 8 +size_half_half = (full/2, full/2) +size_third_half = (full/3, full/2) +size_half_third = (full/2, full/3) + +def assert_directory(): + if not skipasserts: + assert os.path.abspath(".").endswith("scripts"), "Please run from the `scripts` directory" + +def texvar(var, val, math=True): + s = "$" if math else "" + s += f"\\{var} = {val}" + if math: s += "$" + return s + +def export(fig, name, tight_layout=True): + assert_directory() + filename = os.path.join(img_out_dir, name + filetype) + if tight_layout: + fig.tight_layout() + fig.savefig(filename, bbox_inches="tight", pad_inches=0.0) + +@np.vectorize +def smooth_step(x: float, left_edge: float, right_edge: float): + x = (x - left_edge) / (right_edge - left_edge) + if x <= 0: return 0. + elif x >= 1: return 1. + else: return 3*(x*2) - 2*(x**3) + + +# run even when imported +set_mpl_colorscheme(COLORSCHEME) + +if __name__ == "__main__": + assert_directory() + s = \ + """% This file was generated by scripts/formulary.py\n% Do not edit it directly, changes will be overwritten\n""" + generate_latex_colorscheme(COLORSCHEME) + filename = os.path.join(tex_src_path, "util/colorscheme.tex") + print(f"Writing tex colorscheme to {filename}") + with open(filename, "w") as file: + file.write(s) + diff --git a/scripts/util/gen_tex_colorscheme.py b/scripts/util/gen_tex_colorscheme.py new file mode 100644 index 0000000..c4a095c --- /dev/null +++ b/scripts/util/gen_tex_colorscheme.py @@ -0,0 +1,10 @@ +def color_latex_def(name, color): + # name = name.replace("-", "_") + color = color.strip("#") + return "\\definecolor{" + name + "}{HTML}{" + color + "}" + +def generate_latex_colorscheme(palette): + s = "" + for n, c in palette.items(): + s += color_latex_def(n, c) + "\n" + return s diff --git a/src/ch/el.tex b/src/ch/el.tex index eb988a8..a3e56df 100644 --- a/src/ch/el.tex +++ b/src/ch/el.tex @@ -47,45 +47,51 @@ \eng[electrolytic]{electrolytic} \ger[electrolytic]{electrolytisch} + \Eng[working_electrode]{Working electrode} + \Eng[counter_electrode]{Counter electrode} + \Eng[reference_electrode]{Reference electrode} + \Ger[working_electrode]{Working electrode} + \Ger[counter_electrode]{Gegenelektrode} + \Ger[reference_electrode]{Referenzelektrode} + \Eng[potentiostat]{Potentiostat} + \Ger[potentiostat]{Potentiostat} + \begin{formula}{schematic} \desc{Schematic}{}{} \desc[german]{Aufbau}{}{} - \begin{tikzpicture} - \pgfmathsetmacro{\width}{3} - \pgfmathsetmacro{\height}{4} - \pgfmathsetmacro{\elWidth}{\width/9} + \begin{tikzpicture}[scale=1.0,transform shape] + \pgfmathsetmacro{\W}{6} + \pgfmathsetmacro{\H}{3} + \pgfmathsetmacro{\elW}{\W/20} - \draw[thick] (0,0) rectangle (\width,\height); - \fill[bg-blue] (-2,-2) rectangle (2,0.5); + \pgfmathsetmacro{\CEx}{1/6*\W} + \pgfmathsetmacro{\WEx}{3/6*\W} + \pgfmathsetmacro{\REx}{5/6*\W} + \fill[bg-blue] (0,0) rectangle (\W, \H/2); + \draw[ultra thick] (0,0) rectangle (\W,\H); % Electrodes - \draw[thick, red] (-1,2) -- (-1,-1.2); % Reference electrode - \draw[thick, green] (0,2) -- (0,-1); % Counter electrode - \draw[thick, gray] (1,2) -- (1,-1.5); % Working electrode - - % Labels - \node[left] at (-1,0) {Reference electrode}; - \node[left] at (0,-0.5) {Counter electrode}; - \node[right] at (1,-1) {Working electrode}; - \node[left] at (-2,-1.5) {Electrolyte}; - - % Potentiostat - \draw[thick] (-2.5,3) rectangle (2.5,4); - \node at (0,3.5) {Potentiostat}; + \draw[thick, fill=bg-gray] (\CEx-\elW,\H/5) rectangle (\CEx+\elW,\H); + \draw[thick, fill=bg-purple] (\WEx-\elW,\H/5) rectangle (\WEx+\elW,\H); + \draw[thick, fill=bg-yellow] (\REx-\elW,\H/5) rectangle (\REx+\elW,\H); + \node at (\CEx,3*\H/5) {C}; + \node at (\WEx,3*\H/5) {W}; + \node at (\REx,3*\H/5) {R}; + % potentiostat + \pgfmathsetmacro{\potH}{\H+0.5+2} + \pgfmathsetmacro{\potM}{\H+0.5+1} + \draw[thick] (0,\H+0.5) rectangle (\W,\potH); % Wires - \draw[thick] (-1,2) -- (-1,3); - \draw[thick] (0,2) -- (0,3); - \draw[thick] (1,2) -- (1,3); + \draw (\CEx,\H) -- (\CEx,\potM) to[voltmeter,-o] (\WEx,\potM) to[european voltage source] (\WEx+1/6*\W,\potM) to[ammeter] (\REx,\potM); + \draw (\WEx,\H) -- (\WEx,\H+1.5); + \draw (\REx,\H) -- (\REx,\H+1.5); - % Ammeter and Voltmeter - \draw[thick] (-1,2) to[ammeter] (-1,3); - \draw[thick] (0,2) -- (0,3); - \draw[thick] (1,2) to[voltmeter] (1,3); - - % Connecting to potentiostat - \draw[thick] (-1,3.8) -- (-1,4); - \draw[thick] (1,3.8) -- (1,4); + % labels + \node[anchor=west, align=left] at (\W+0.2, 1*\H/4) {{\color{bg-gray} \blacksquare} \GT{counter_electrode}}; + \node[anchor=west, align=left] at (\W+0.2, 2*\H/4) {{\color{bg-purple}\blacksquare} \GT{working_electrode}}; + \node[anchor=west, align=left] at (\W+0.2, 3*\H/4) {{\color{bg-yellow}\blacksquare} \GT{reference_electrode}}; + \node[anchor=west, align=left] at (\W+0.2, \potM) {\GT{potentiostat}}; \end{tikzpicture} \end{formula} @@ -298,61 +304,89 @@ \eq{\eta_\text{act} = E_\text{electrode} - E_\text{ref}} \end{formula} - \begin{formula}{concentration_overpotential} - \desc{Concentration overpotential}{Due to concentration gradient near the electrode, the ions need to \hyperref[f:ch:el:ion_cond:diffusion]{diffuse} to the electrode before reacting}{\ConstRef{universal_gas}, \QtyRef{temperature}, $\c_{0/\txS}$ ion concentration in the electrolyte / at the double layer, $z$ \qtyRef{charge_number}, \ConstRef{faraday}} - \desc[german]{Konzentrationsüberspannung}{Durch einen Konzentrationsgradienten an der Elektrode müssen Ionen erst zur Elektrode \hyperref[f:ch:el:ion_cond:diffusion]{diffundieren}, bevor sie reagieren können}{} - \eq{ - \eta_\text{conc,anodic} &= -\frac{RT}{\alpha \,zF} \ln \left(\frac{c_\text{red}^0}{c_\text{red}^\txS}\right) \\ - \eta_\text{conc,cathodic} &= -\frac{RT}{(1-\alpha) zF} \ln \left(\frac{c_\text{ox}^0}{c_\text{ox}^\txS}\right) - } - \end{formula} - - \begin{formula}{diffusion_overpotential} - \desc{Diffusion overpotential}{}{} - \desc[german]{Diffusionsüberspannung}{}{} - \eq{\eta_\text{diff} = \frac{RT}{nF} \ln \left( \cfrac{\cfrac{c^\txs_\text{ox}}{c^0_\text{ox}}}{\cfrac{c^\txs_\text{red}}{c^0_\text{red}}} \right)} - \end{formula} - - \begin{formula}{diffusion_layer} - \desc{Cell layers}{}{} - \desc[german]{Zellschichten}{}{} - \begin{tikzpicture} - \tikzset{ - label/.style={color=fg1,anchor=center,rotate=90}, + \Subsubsection[ + \eng{Mass transport} + \ger{Massentransport} + ]{mass} + \begin{formula}{concentration_overpotential} + \desc{Concentration overpotential}{Due to concentration gradient near the electrode, the ions need to \hyperref[f:ch:el:ion_cond:diffusion]{diffuse} to the electrode before reacting}{\ConstRef{universal_gas}, \QtyRef{temperature}, $\c_{0/\txS}$ ion concentration in the electrolyte / at the double layer, $z$ \qtyRef{charge_number}, \ConstRef{faraday}} + \desc[german]{Konzentrationsüberspannung}{Durch einen Konzentrationsgradienten an der Elektrode müssen Ionen erst zur Elektrode \hyperref[f:ch:el:ion_cond:diffusion]{diffundieren}, bevor sie reagieren können}{} + \eq{ + \eta_\text{conc,anodic} &= -\frac{RT}{\alpha \,zF} \ln \left(\frac{c_\text{red}^0}{c_\text{red}^\txS}\right) \\ + \eta_\text{conc,cathodic} &= -\frac{RT}{(1-\alpha) zF} \ln \left(\frac{c_\text{ox}^0}{c_\text{ox}^\txS}\right) } - \pgfmathsetmacro{\tkW}{8} % Total width - \pgfmathsetmacro{\tkH}{5} % Total height - \pgfmathsetmacro{\edW}{1} % electrode width - \pgfmathsetmacro{\hhW}{1} % helmholtz width - \pgfmathsetmacro{\ndW}{2} % nernst diffusion with - \pgfmathsetmacro{\eyW}{\tkW-\edW-\hhW-\ndW} % electrolyte width - \pgfmathsetmacro{\edX}{0} % electrode width - \pgfmathsetmacro{\hhX}{\edW} % helmholtz width - \pgfmathsetmacro{\ndX}{\edW+\hhW} % nernst diffusion with - \pgfmathsetmacro{\eyX}{\tkW-\eyW} % electrolyte width + \end{formula} - \draw[->] (0,0) -- (\tkW+0.2,0) node[anchor=north] {$x$}; - \draw[->] (0,0) -- (0,\tkH+0.2) node[anchor=east] {$c$}; - \path[fill=bg-orange] (\edX,0) rectangle (\edX+\edW,\tkH); \node[label] at (\edX+\edW/2,\tkH/2) {\GT{electrode}}; - \path[fill=bg-green!90!bg0] (\hhX,0) rectangle (\hhX+\hhW,\tkH); \node[label] at (\hhX+\hhW/2,\tkH/2) {\GT{helmholtz_layer}}; - \path[fill=bg-green!60!bg0] (\ndX,0) rectangle (\ndX+\ndW,\tkH); \node[label] at (\ndX+\ndW/2,\tkH/2) {\GT{nernst_layer}}; - \path[fill=bg-green!20!bg0] (\eyX,0) rectangle (\eyX+\eyW,\tkH); \node[label] at (\eyX+\eyW/2,\tkH/2) {\GT{elektrolyte}}; - \draw (\hhX,2) -- (\ndX,3) -- (\tkW,3); - \tkYTick{2}{$c^\txS$}; - \tkYTick{3}{$c^0$}; - \end{tikzpicture} - \end{formula} - \Eng[c_surface]{surface \qtyRef{concentration}} - \Eng[c_bulk]{bulk \qtyRef{concentration}} - \Ger[c_surface]{Oberflächen-\qtyRef{concentration}} - \Ger[c_bulk]{Bulk-\qtyRef{concentration}} + \begin{formula}{diffusion_overpotential} + \desc{Diffusion overpotential}{Due to mass transport limitations}{$j_\infty$ \secEqRef{limiting_current}, $j_\text{meas}$ measured \qtyRef{current_density}, \ConstRef{universal_gas}, \QtyRef{temperature}, $n$ \qtyRef{charge_number}, \ConstRef{faraday}} + \desc[german]{Diffusionsüberspannung}{Durch Limit des Massentransports}{} + % \eq{\eta_\text{diff} = \frac{RT}{nF} \ln \left( \frac{\cfrac{c^\txs_\text{ox}}{c^0_\text{ox}}}{\cfrac{c^\txs_\text{red}}{c^0_\text{red}}} \right)} + \eq{\eta_\text{diff} = \frac{RT}{nF} \Ln{\frac{j_\infty}{j_\infty - j_\text{meas}}}} + \end{formula} + + \begin{formula}{diffusion_layer} + \desc{Cell layers}{}{} + \desc[german]{Zellschichten}{}{} + \begin{tikzpicture} + \tikzset{ + label/.style={color=fg1,anchor=center,rotate=90}, + } + \pgfmathsetmacro{\tkW}{8} % Total width + \pgfmathsetmacro{\tkH}{4} % Total height + \pgfmathsetmacro{\edW}{1} % electrode width + \pgfmathsetmacro{\hhW}{1} % helmholtz width + \pgfmathsetmacro{\ndW}{2} % nernst diffusion with + \pgfmathsetmacro{\eyW}{\tkW-\edW-\hhW-\ndW} % electrolyte width + \pgfmathsetmacro{\edX}{0} % electrode width + \pgfmathsetmacro{\hhX}{\edW} % helmholtz width + \pgfmathsetmacro{\ndX}{\edW+\hhW} % nernst diffusion with + \pgfmathsetmacro{\eyX}{\tkW-\eyW} % electrolyte width + + \path[fill=bg-orange] (\edX,0) rectangle (\edX+\edW,\tkH); \node[label] at (\edX+\edW/2,\tkH/2) {\GT{electrode}}; + \path[fill=bg-green!90!bg0] (\hhX,0) rectangle (\hhX+\hhW,\tkH); \node[label] at (\hhX+\hhW/2,\tkH/2) {\GT{helmholtz_layer}}; + \path[fill=bg-green!60!bg0] (\ndX,0) rectangle (\ndX+\ndW,\tkH); \node[label] at (\ndX+\ndW/2,\tkH/2) {\GT{nernst_layer}}; + \path[fill=bg-green!20!bg0] (\eyX,0) rectangle (\eyX+\eyW,\tkH); \node[label] at (\eyX+\eyW/2,\tkH/2) {\GT{electrolyte}}; + \draw (\hhX,2) -- (\ndX,3) -- (\tkW,3); + % axes + \draw[->] (0,0) -- (\tkW+0.2,0) node[anchor=north] {$x$}; + \draw[->] (0,0) -- (0,\tkH+0.2) node[anchor=east] {$c$}; + \tkYTick{2}{$c^\txS$}; + \tkYTick{3}{$c^0$}; + \end{tikzpicture} + \end{formula} + \Eng[c_surface]{surface \qtyRef{concentration}} + \Eng[c_bulk]{bulk \qtyRef{concentration}} + \Ger[c_surface]{Oberflächen-\qtyRef{concentration}} + \Ger[c_bulk]{Bulk-\qtyRef{concentration}} - \begin{formula}{diffusion_layer_thickness} - \desc{Nerst Diffusion layer thickness}{}{$c^0$ \GT{c_bulk}, $c^\txs$ \GT{c_surface}} - \desc[german]{Dicke der Nernstschen Diffusionsschicht}{}{} - \eq{\delta_\txN = \frac{c^0 - c^\txs}{\odv{c}{x}_{x=0}}} - \end{formula} + \begin{formula}{diffusion_layer_thickness} + \desc{Nerst Diffusion layer thickness}{}{$c^0$ \GT{c_bulk}, $c^\txS$ \GT{c_surface}} + \desc[german]{Dicke der Nernstschen Diffusionsschicht}{}{} + \eq{\delta_\txN = \frac{c^0 - c^\txS}{\odv{c}{x}_{x=0}}} + \end{formula} + + \begin{formula}{limiting_current} + \desc{(Limiting) current density}{}{$n$ \QtyRef{charge_number}, \ConstRef{faraday}, $c^0$ \GT{c_bulk}, $D$ \qtyRef{diffusion_coefficient}, $\delta_\text{diff}$ \secEqRef{diffusion_layer_thickness}} + % \desc[german]{Limitierender Strom}{}{} + \eq{ + \abs{j} &= nFD \frac{c^0-c^\txS}{\delta_\text{diff}} + \shortintertext{\GT{for} $c^\txS \to 0$} + \abs{j_\infty} &= nFD \frac{c^0}{\delta_\text{diff}} + } + \end{formula} + + \begin{formula}{relation?} + \desc{Current - concentration relation}{}{$c^0$ \GT{c_bulk}, $c^\txS$ \GT{c_surface}, $j$ \secEqRef{limiting_current}} + \desc[german]{Strom - Konzentrationsbeziehung}{}{} + \eq{\frac{j}{j_\infty} = 1 - \frac{c^\txS}{c^0}} + \end{formula} + + \begin{formula}{kinetic_current} + \desc{Kinetic current density}{}{$j_\text{meas}$ measured \qtyRef{current_density}, $j_\infty$ \secEqRef{limiting_current}} + \desc[german]{Kinetische Stromdichte}{}{$j_\text{meas}$ gemessene \qtyRef{current_density}, $j_\infty$ \secEqRef{limiting_current}} + \eq{j_\text{kin} = \frac{j_\text{meas} j_\infty}{j_\infty - j_\text{meas}}} + \end{formula} \begin{formula}{roughness_factor} \desc{Roughness factor}{Surface area related to electrode geometry}{} @@ -361,10 +395,10 @@ \begin{formula}{butler_volmer} \desc{Butler-Volmer equation}{Reaction kinetics near the equilibrium potentential} - {$j$ \qtyRef{current_density}, $j_0$ exchange current density, $\eta$ \fqEqRef{ch:el:kin:overpotential}, \QtyRef{temperature}, $z$ \qtyRef{charge_number}, \ConstRef{faraday}, \ConstRef{universal_gas}, $\alpha_{\txC/\txA}$ cathodic/anodic charge transfer coefficient} + {$j$ \qtyRef{current_density}, $j_0$ exchange current density, $\eta$ \fqEqRef{ch:el:kin:overpotential}, \QtyRef{temperature}, $z$ \qtyRef{charge_number}, \ConstRef{faraday}, \ConstRef{universal_gas}, $\alpha_{\txC/\txA}$ cathodic/anodic charge transfer coefficient, $\text{rf}$ \secEqRef{roughness_factor}} %Current through an electrode iof a unimolecular redox reaction with both anodic and cathodic reaction occuring on the same electrode \desc[german]{Butler-Volmer-Gleichung}{Reaktionskinetik in der Nähe des Gleichgewichtspotentials} - {$j$ \qtyRef{current_density}, $j_0$ Austauschstromdichte, $\eta$ \fqEqRef{ch:el:kin:overpotential}, \QtyRef{temperature}, $z$ \qtyRef{charge_number}, \ConstRef{faraday}, \ConstRef{universal_gas}, $\alpha_{\txC/\txA}$ Ladungstransferkoeffizient an der Kathode/Anode} + {$j$ \qtyRef{current_density}, $j_0$ Austauschstromdichte, $\eta$ \fqEqRef{ch:el:kin:overpotential}, \QtyRef{temperature}, $z$ \qtyRef{charge_number}, \ConstRef{faraday}, \ConstRef{universal_gas}, $\alpha_{\txC/\txA}$ Ladungstransferkoeffizient an der Kathode/Anode, $\text{rf}$ \secEqRef{roughness_factor}} \begin{gather} j = j_0 \,\rfactor\, \left[ \Exp{\frac{(1-a_\txC) z F \eta}{RT}} - \Exp{-\frac{\alpha_\txC z F \eta}{RT}}\right] \intertext{\GT{with}} @@ -434,46 +468,83 @@ \Subsubsection[ \eng{Cyclic voltammetry} \ger{Zyklische Voltammetrie} - ]{cycl_v} - \begin{formula}{duck} + ]{cv} + \begin{bigformula}{duck} \desc{Cyclic voltammogram}{}{} % \desc[german]{}{}{} - \begin{tikzpicture} - \pgfmathsetmacro{\Ax}{-2.3} - \pgfmathsetmacro{\Ay}{ 0.0} - \pgfmathsetmacro{\Bx}{ 0.0} - \pgfmathsetmacro{\By}{ 1.0} - \pgfmathsetmacro{\Cx}{ 0.4} - \pgfmathsetmacro{\Cy}{ 1.5} - \pgfmathsetmacro{\Dx}{ 2.0} - \pgfmathsetmacro{\Dy}{ 0.5} - \pgfmathsetmacro{\Ex}{ 0.0} - \pgfmathsetmacro{\Ey}{-1.5} - \pgfmathsetmacro{\Fx}{-0.4} - \pgfmathsetmacro{\Fy}{-2.0} - \pgfmathsetmacro{\Gx}{-2.3} - \pgfmathsetmacro{\Gy}{-0.3} - \begin{axis}[ymin=-3,ymax=3,xmax=3,xmin=-3, - % equal axis, - minor tick num=1, - xlabel={$U$}, xlabel style={at={(axis description cs:0.5,+0.02)}}, - ylabel={$I$}, ylabel style={at={(axis description cs:0.1,0.5)}}, - anchor=center, at={(0,0)}, - axis equal image,clip=false, - ] - % CV with beziers - \draw[thick, fg-blue] (axis cs:\Ax,\Ay) coordinate (A) node[left] {A} - ..controls (axis cs:\Ax+1.8, \Ay+0.0) and (axis cs:\Bx-0.2, \By-0.4) .. (axis cs:\Bx,\By) coordinate (B) node[left] {B} - ..controls (axis cs:\Bx+0.1, \By+0.2) and (axis cs:\Cx-0.3, \Cy+0.0) .. (axis cs:\Cx,\Cy) coordinate (C) node[above] {C} - ..controls (axis cs:\Cx+0.5, \Cy+0.0) and (axis cs:\Dx-1.3, \Dy+0.1) .. (axis cs:\Dx,\Dy) coordinate (D) node[right] {D} - ..controls (axis cs:\Dx-2.0, \Dy-0.1) and (axis cs:\Ex+0.3, \Ey+0.8) .. (axis cs:\Ex,\Ey) coordinate (E) node[right] {E} - ..controls (axis cs:\Ex-0.1, \Ey-0.2) and (axis cs:\Fx+0.2, \Fy+0.0) .. (axis cs:\Fx,\Fy) coordinate (F) node[below] {F} - ..controls (axis cs:\Fx-0.2, \Fy+0.0) and (axis cs:\Gx+1.5, \Gy-0.2) .. (axis cs:\Gx,\Gy) coordinate (G) node[left] {G}; - \node[above] at (A) {\rightarrow}; - \end{axis} - \end{tikzpicture} + + \begin{minipage}{0.44\textwidth} + + \begin{tikzpicture} + \pgfmathsetmacro{\Ax}{-2.3} + \pgfmathsetmacro{\Ay}{ 0.0} + \pgfmathsetmacro{\Bx}{ 0.0} + \pgfmathsetmacro{\By}{ 1.0} + \pgfmathsetmacro{\Cx}{ 0.4} + \pgfmathsetmacro{\Cy}{ 1.5} + \pgfmathsetmacro{\Dx}{ 2.0} + \pgfmathsetmacro{\Dy}{ 0.5} + \pgfmathsetmacro{\Ex}{ 0.0} + \pgfmathsetmacro{\Ey}{-1.5} + \pgfmathsetmacro{\Fx}{-0.4} + \pgfmathsetmacro{\Fy}{-2.0} + \pgfmathsetmacro{\Gx}{-2.3} + \pgfmathsetmacro{\Gy}{-0.3} + \pgfmathsetmacro{\x}{3} + \pgfmathsetmacro{\y}{3} + \begin{axis}[ymin=-\y,ymax=\y,xmax=\x,xmin=-\x, + % equal axis, + minor tick num=1, + xlabel={$E$}, xlabel style={at={(axis description cs:0.5,-0.06)}}, + ylabel={$j$}, ylabel style={at={(axis description cs:-0.06,0.5)}}, + anchor=center, at={(0,0)}, + axis equal image,clip=false, + ] + % CV with beziers + \draw[thick, fg-blue] (axis cs:\Ax,\Ay) coordinate (A) node[left] {A} + ..controls (axis cs:\Ax+1.8, \Ay+0.0) and (axis cs:\Bx-0.2, \By-0.4) .. (axis cs:\Bx,\By) coordinate (B) node[left] {B} + ..controls (axis cs:\Bx+0.1, \By+0.2) and (axis cs:\Cx-0.3, \Cy+0.0) .. (axis cs:\Cx,\Cy) coordinate (C) node[above] {C} + ..controls (axis cs:\Cx+0.5, \Cy+0.0) and (axis cs:\Dx-1.3, \Dy+0.1) .. (axis cs:\Dx,\Dy) coordinate (D) node[right] {D} + ..controls (axis cs:\Dx-2.0, \Dy-0.1) and (axis cs:\Ex+0.3, \Ey+0.8) .. (axis cs:\Ex,\Ey) coordinate (E) node[right] {E} + ..controls (axis cs:\Ex-0.1, \Ey-0.2) and (axis cs:\Fx+0.2, \Fy+0.0) .. (axis cs:\Fx,\Fy) coordinate (F) node[below] {F} + ..controls (axis cs:\Fx-0.2, \Fy+0.0) and (axis cs:\Gx+1.5, \Gy-0.2) .. (axis cs:\Gx,\Gy) coordinate (G) node[left] {G}; + \node[above] at (A) {\rightarrow}; + + \draw[dashed, fg2] (axis cs: \Bx,\By) -- (axis cs: \Ex, \Ey); + + \draw[->] (axis cs:-\x-0.6, 0.4) -- (axis cs:-\x-0.6, \y) node[left=0.3cm, anchor=east, rotate=90] {Cath / Red}; + \draw[->] (axis cs:-\x-0.6,-0.4) -- (axis cs:-\x-0.6,-\y) node[left=0.3cm, anchor=west, rotate=90] {An / Ox}; + \end{axis} + \end{tikzpicture} + \end{minipage} + \begin{minipage}{0.55\textwidth} + \begin{ttext} + \eng{\begin{itemize} + \item {\color{fg-blue}A-D}: Diffusion layer growth \rightarrow decreased current after peak + \item {\color{fg-blue}D}: Switching potential + \item {\color{fg-blue}B,E}: Equal concentrations of reactants + \item {\color{fg-blue}C,F}: Formal potential of redox pair: $E \approx \frac{E_\txC - E_\txF}{2}$ + \item {\color{fg-blue}C,F}: Peak separation for reverisble processes: $\Delta E_\text{rev} = E_\txC - E_\txF = n\,\SI{59}{\milli\volt}$ + \item Information about surface chemistry + \item Double-layer capacity (horizontal lines): $I = C v$ + \end{itemize}} + \end{ttext} + \end{minipage} + \end{bigformula} + + \begin{formula}{peak_current} + \desc{Randles-Sevcik equation}{For reversible reaction.\\Peak current depends on square root of the scan rate}{$n$ \qtyRef{charge_number}, \ConstRef{faraday}, $A$ electrode surface area, $c^0$ bulk \qtyRef{concentration}, $v$ \qtyRef{scan_rate}, $D_\text{ox}$ \qtyRef{diffusion_coefficient} of oxidized analyte, \ConstRef{universal_gas}, \QtyRef{temperature}} + \desc[german]{Randles-Sevcik Gleichung}{Spitzenstrom}{} + \eq{i_\text{peak} = 0.446\,nFAc^0 \sqrt{\frac{nFvD_\text{ox}}{RT}}} \end{formula} + \begin{hiddenformula}{scan_rate} + \desc{Scan rate}{}{} + \desc[german]{Scanrate}{}{} + \quantity{v}{\volt\per\s}{s} + \end{hiddenformula} + + \begin{formula}{upd} \desc{Underpotential deposition (UPD)}{}{} \desc[german]{}{}{} @@ -483,7 +554,7 @@ \Subsubsection[ \eng{Rotating disk electrodes} % \ger{} - ]{rde} + ]{rde} \abbrLink{rde}{RDE} \begin{formula}{viscosity} \desc{Dynamic viscosity}{}{} \desc[german]{Dynamisch Viskosität}{}{} @@ -504,8 +575,9 @@ \end{formula} \begin{formula}{limiting_current} - \desc{Limiting current}{}{$n$ \QtyRef{charge_number}, \ConstRef{faraday}, $c^0$ \GT{c_bulk}, $D$ \qtyRef{diffusion_coefficient}, $\delta_\text{diff}$ \secEqRef{diffusion_layer_thickness}, $\nu$ \qtyRef{kinematic_viscosity}, \QtyRef{angular_frequency}} + \desc{Limiting current density}{for a \abbrRef{rde}}{$n$ \QtyRef{charge_number}, \ConstRef{faraday}, $c^0$ \GT{c_bulk}, $D$ \qtyRef{diffusion_coefficient}, $\delta_\text{diff}$ \secEqRef{diffusion_layer_thickness}, $\nu$ \qtyRef{kinematic_viscosity}, \QtyRef{angular_frequency}} % \desc[german]{Limitierender Strom}{}{} - \eq{j^\infty = nFD \frac{c^0}{\delta_\text{diff}} = \frac{1}{1.61} nFD^{\frac{2}{3}} v^{\frac{-1}{6}} c^0 \sqrt{\omega}} + \eq{j_\infty = nFD \frac{c^0}{\delta_\text{diff}} = \frac{1}{1.61} nFD^{\frac{2}{3}} v^{\frac{-1}{6}} c^0 \sqrt{\omega}} \end{formula} + diff --git a/src/ch/misc.tex b/src/ch/misc.tex index 0c5eec2..a61a18c 100644 --- a/src/ch/misc.tex +++ b/src/ch/misc.tex @@ -90,18 +90,26 @@ \end{formula} - \Eng[cyanide]{Cyanide} - \Ger[cyanide]{Zyanid} - \Eng[ammonia]{Ammonia} - \Ger[ammonia]{Ammoniak} - \begin{formula}{common_chemicals} \desc{Common chemicals}{}{} \desc[german]{Häufige Chemikalien}{}{} \begin{tabular}{l|c} - \GT{name} & \GT{formula} \\ \hline\hline - \GT{cyanide} & \ce{CN} \\ \hline - \GT{ammonia} & \ce{NH3} + \GT{name} & \GT{formula} \\ \hline\hline + \begin{ttext}[cyanide]\eng{Cyanide}\ger{Zyanid}\end{ttext} & \ce{CN} \\ \hline + \begin{ttext}[ammonia]\eng{Ammonia}\ger{Ammoniak}\end{ttext} & \ce{NH3} \\ \hline + \begin{ttext}[hydrogen peroxide]\eng{Hydrogen Peroxide}\ger{Wasserstoffperoxid}\end{ttext} & \ce{H2O2} \\ \hline + \begin{ttext}[sulfuric acid]\eng{Sulfuric Acid}\ger{Schwefelsäure}\end{ttext} & \ce{H2SO4} \\ \hline + \begin{ttext}[ethanol]\eng{Ethanol}\ger{Ethanol}\end{ttext} & \ce{C2H5OH} \\ \hline + \begin{ttext}[acetic acid]\eng{Acetic Acid}\ger{Essigsäure}\end{ttext} & \ce{CH3COOH} \\ \hline + \begin{ttext}[methane]\eng{Methane}\ger{Methan}\end{ttext} & \ce{CH4} \\ \hline + \begin{ttext}[hydrochloric acid]\eng{Hydrochloric Acid}\ger{Salzsäure}\end{ttext} & \ce{HCl} \\ \hline + \begin{ttext}[sodium hydroxide]\eng{Sodium Hydroxide}\ger{Natriumhydroxid}\end{ttext} & \ce{NaOH} \\ \hline + \begin{ttext}[nitric acid]\eng{Nitric Acid}\ger{Salpetersäure}\end{ttext} & \ce{HNO3} \\ \hline + \begin{ttext}[calcium carbonate]\eng{Calcium Carbonate}\ger{Calciumcarbonat}\end{ttext} & \ce{CaCO3} \\ \hline + \begin{ttext}[glucose]\eng{Glucose}\ger{Glukose}\end{ttext} & \ce{C6H12O6} \\ \hline + \begin{ttext}[benzene]\eng{Benzene}\ger{Benzol}\end{ttext} & \ce{C6H6} \\ \hline + \begin{ttext}[acetone]\eng{Acetone}\ger{Aceton}\end{ttext} & \ce{C3H6O} \\ \hline + \begin{ttext}[ethylene]\eng{Ethylene}\ger{Ethylen}\end{ttext} & \ce{C2H4} \\ \hline + \begin{ttext}[potassium permanganate]\eng{Potassium Permanganate}\ger{Kaliumpermanganat}\end{ttext} & \ce{KMnO4} \\ \hline \end{tabular} \end{formula} - diff --git a/src/comp/ad.tex b/src/comp/ad.tex index d7dec09..aa92236 100644 --- a/src/comp/ad.tex +++ b/src/comp/ad.tex @@ -279,7 +279,7 @@ \ttxt{\eng{ \begin{itemize} \item Use empirical interaction potential instead of electronic structure - \baditem Force fields need to be fitted for specific material \Rightarrorw not transferable + \baditem Force fields need to be fitted for specific material \Rightarrow not transferable \gooditem Faster than \abbrRef{bomd} \item Example: \absRef{lennard_jones} \end{itemize} diff --git a/src/comp/qmb.tex b/src/comp/qmb.tex index 26c88a1..7093924 100644 --- a/src/comp/qmb.tex +++ b/src/comp/qmb.tex @@ -8,7 +8,7 @@ ]{models} \begin{formula}{heg} \desc{Homogeneous electron gas (HEG)}{Also "Jellium"}{} - \desc[german]{}{}{} + % \desc[german]{}{}{} \ttxt{ \eng{Both positive (nucleus) and negative (electron) charges are distributed uniformly.} } diff --git a/src/constants.tex b/src/constants.tex index 4b4dd12..d5c86f6 100644 --- a/src/constants.tex +++ b/src/constants.tex @@ -45,3 +45,10 @@ } \end{formula} + \begin{formula}{charge} + \desc{Unit charge}{}{} + \desc[german]{Elementarladung}{}{} + \constant{e}{def}{ + \val{1.602176634\xE{-19}}{\coulomb} + } + \end{formula} diff --git a/src/main.tex b/src/main.tex index fe722a8..76a8e7b 100644 --- a/src/main.tex +++ b/src/main.tex @@ -2,7 +2,7 @@ % (for vimtex) \documentclass[11pt, a4paper]{article} % SET LANGUAGE HERE -\usepackage[english]{babel} +\usepackage[german]{babel} \usepackage[left=2cm,right=2cm,top=2cm,bottom=2cm]{geometry} % ENVIRONMENTS etc \usepackage{adjustbox} @@ -31,11 +31,6 @@ \usepackage{array} % more array options \newcolumntype{C}{>{$}c<{$}} % math-mode version of "c" column type % \usepackage{sectsty} -% TRANSLATION -\usepackage{translations} -\input{util/translation.tex} -\input{util/colorscheme.tex} -\input{util/colors.tex} % after colorscheme % GRAPHICS \usepackage{pgfplots} \pgfplotsset{compat=1.18} @@ -74,6 +69,7 @@ \sisetup{separate-uncertainty} \sisetup{per-mode = power} \sisetup{exponent-product=\ensuremath{\cdot}} + % DEBUG % \usepackage{lua-visual-debug} % DUMB STUFF @@ -88,46 +84,12 @@ % \def\nu{\temoji{unicorn}} % \def\mu{\temoji{mouse}} - - \newcommand{\TODO}[1]{{\color{fg-red}TODO:#1}} \newcommand{\ts}{\textsuperscript} % \usepackage{xstring} -% LUA sutff -\newcommand\luavar[1]{\directlua{tex.sprint(#1)}} -\directlua{ - function string.startswith(s, start) - return string.sub(s,1,string.len(start)) == start - end -} -% Write directlua command to aux and run it as well -% This one expands the argument in the aux file: -\newcommand\directLuaAuxExpand[1]{ - \immediate\write\luaAuxFile{\noexpand\directlua{#1}} - \directlua{#1} -} -% This one does not: -\newcommand\directLuaAux[1]{ - \immediate\write\luaAuxFile{\noexpand\directlua{\detokenize{#1}}} - \directlua{#1} -} - -% read -\IfFileExists{\jobname.lua.aux}{% - \input{\jobname.lua.aux}% -}{% - % \@latex@warning@no@line{"Lua aux not loaded!"} -} -\def\luaAuxLoaded{False} - -% write -\newwrite\luaAuxFile -\immediate\openout\luaAuxFile=\jobname.lua.aux -\immediate\write\luaAuxFile{\noexpand\def\noexpand\luaAuxLoaded{True}}% -\AtEndDocument{\immediate\closeout\luaAuxFile} % Create a text file with relevant labels for vim-completion \newwrite\labelsFile @@ -137,14 +99,21 @@ } \AtEndDocument{\immediate\closeout\labelsFile} - -\input{util/fqname.tex} \input{circuit.tex} \input{util/macros.tex} \input{util/environments.tex} % requires util/translation.tex to be loaded first -\input{util/periodic_table.tex} % requires util/translation.tex to be loaded first - +\usepackage{pkg/mqlua} +\usepackage{pkg/mqfqname} +% TRANSLATION +% \usepackage{translations} +\usepackage{pkg/mqtranslation} +\input{util/colorscheme.tex} +\input{util/colors.tex} % after colorscheme +\usepackage{pkg/mqconstant} +\usepackage{pkg/mqquantity} +\usepackage{pkg/mqformula} +\usepackage{pkg/mqperiodictable} % INPUT % 1: starting pattern of files to input using the Input command. All other files are ignored @@ -159,7 +128,6 @@ } } - \title{Formelsammlung} \author{Matthias Quintern} \date{\today} @@ -168,12 +136,6 @@ \input{\jobname.translations.aux} }{} -\def\translationsAuxLoaded{False} -\newwrite\translationsaux -\immediate\openout\translationsaux=\jobname.translations.aux -\immediate\write\translationsaux{\noexpand\def\noexpand\translationsAuxLoaded{True}}% -\AtEndDocument{\immediate\closeout\translationsaux} - \makeatletter\let\percentchar\@percentchar\makeatother \maketitle @@ -183,7 +145,7 @@ \input{util/translations.tex} -% \InputOnly{comp} +% \InputOnly{ch} \Input{math/math} \Input{math/linalg} @@ -215,7 +177,6 @@ \Input{cm/topo} \Input{cm/mat} - \Input{particle} \Input{quantum_computing} @@ -253,7 +214,7 @@ ]{elements} \printAllElements \newpage -\Input{test} +% \Input{test} % \bibliographystyle{plain} % \bibliography{ref} diff --git a/src/math/linalg.tex b/src/math/linalg.tex index ad99fe0..8f9ecdf 100644 --- a/src/math/linalg.tex +++ b/src/math/linalg.tex @@ -96,7 +96,8 @@ \Subsection[ - + \eng{Misc} + \ger{Misc} ]{misc} \begin{formula}{normal_equation} diff --git a/src/pkg/mqconstant.sty b/src/pkg/mqconstant.sty new file mode 100644 index 0000000..6020a70 --- /dev/null +++ b/src/pkg/mqconstant.sty @@ -0,0 +1,62 @@ +\ProvidesPackage{mqconstant} +\RequirePackage{mqlua} +\RequirePackage{etoolbox} + +\directLuaAux{ + if constants == nil then + constants = {} + end +} + +% [1]: label to point to +% 2: key +% 3: symbol +% 4: either exp or def; experimentally or defined constant +\newcommand{\constant@new}[4][\relax]{ + \directLuaAux{ + constants["#2"] = {} + constants["#2"]["symbol"] = [[\detokenize{#3}]] + constants["#2"]["exp_or_def"] = [[\detokenize{#4}]] + constants["#2"]["values"] = {} %-- array of {value, unit} + } + \ifstrempty{#1}{}{ + \directLuaAuxExpand{ + constants["#2"]["linkto"] = [[#1]] %-- fqname required for getting the translation key + } + } +} + +% 1: key +% 2: value +% 3: units +\newcommand{\constant@addValue}[3]{ + \directlua{ + table.insert(constants["#1"]["values"], { value = [[\detokenize{#2}]], unit = [[\detokenize{#3}]] }) + } +} + +% 1: key +\newcommand\constant@print[1]{ + \begingroup % for label + Symbol: $\luavar{constants["#1"]["symbol"]}$ + % \\Unit: $\directlua{split_and_print_units(constants["#1"]["units"])}$ + \directlua{ + tex.print("\\\\\\GT{const:"..constants["#1"]["exp_or_def"].."}") + } + \directlua{ + %--tex.sprint("Hier steht Luatext" .. ":", #constVals) + for i, pair in ipairs(constants["#1"]["values"]) do + tex.sprint("\\\\\\hspace*{1cm}${", pair["value"], "}\\,\\si{", pair["unit"], "}$") + %--tex.sprint("VALUE ", i, v) + end + } + % label it only once + \directlua{ + if constants["#1"]["labeled"] == nil then + constants["#1"]["labeled"] = true + tex.print("\\label{const:#1}") + end + } + \endgroup +} +\newcounter{constant} diff --git a/src/pkg/mqformula.sty b/src/pkg/mqformula.sty new file mode 100644 index 0000000..664ce87 --- /dev/null +++ b/src/pkg/mqformula.sty @@ -0,0 +1,250 @@ +\ProvidesPackage{mqformula} + +\RequirePackage{mqfqname} +\RequirePackage{mqconstant} +\RequirePackage{mqquantity} + +% +% FORMULA ENVIRONMENT +% The following commands are meant to be used with the formula environment +% + +% Name in black and below description in gray +% [1]: minipage width +% 2: fqname of name +% 3: fqname of a translation that holds the explanation +\newcommand{\NameWithDescription}[3][\descwidth]{ + \begin{minipage}{#1} + \IfTranslationExists{#2}{ + \raggedright + \GT{#2} + }{\detokenize{#2}} + \IfTranslationExists{#3}{ + \\ {\color{fg1} \GT{#3}} + }{} + \end{minipage} +} + + +% TODO: rename +\newsavebox{\contentBoxBox} +% [1]: minipage width +% 2: fqname of a translation that holds the explanation +\newenvironment{ContentBoxWithExplanation}[2][\eqwidth]{ + \def\ContentFqName{#2} + \begin{lrbox}{\contentBoxBox} + \begin{minipage}{#1} +}{ + \IfTranslationExists{\ContentFqName}{% + \smartnewline + \noindent + \begingroup + \color{fg1} + \GT{\ContentFqName} + % \edef\temp{\GT{#1_defs}} + % \expandafter\StrSubstitute\expandafter{\temp}{:}{\\} + \endgroup + }{} + \end{minipage} + \end{lrbox} + \fbox{\usebox{\contentBoxBox}} +} + + +% Class defining commands shared by all formula environments +% 1: key +\newenvironment{formulainternal}[1]{ + % [1]: language + % 2: name + % 3: description + % 4: definitions/links + \newcommand{\desc}[4][english]{ + % language, name, description, definitions + \ifblank{##2}{}{\dt[#1]{##1}{##2}} + \ifblank{##3}{}{\dt[#1_desc]{##1}{##3}} + \ifblank{##4}{}{\dt[#1_defs]{##1}{##4}} + } + \directlua{n_formulaEntries = 0} + + % makes this formula referencable with \abbrRef{} + % [1]: label to use + % 2: Abbreviation to use for references + \newcommand{\abbrLabel}[2][#1]{ + \abbrLink[f:\fqname]{##1}{##2} + } + % makes this formula referencable with \absRef{} + % [1]: label to use + \newcommand{\absLabel}[1][#1]{ + \absLink[f:\fqname]{##1} + } + + \newcommand{\newFormulaEntry}{ + \directlua{ + if n_formulaEntries > 0 then + tex.print("\\vspace{0.3\\baselineskip}\\hrule\\vspace{0.3\\baselineskip}") + end + n_formulaEntries = n_formulaEntries + 1 + } + % \par\noindent\ignorespaces + } + % 1: equation for align environment + \newcommand{\eq}[1]{ + \newFormulaEntry + \begin{align} + % \label{eq:\fqname:#1} + ##1 + \end{align} + } + % 1: equation for alignat environment + \newcommand{\eqAlignedAt}[2]{ + \newFormulaEntry + \begin{flalign}% + \TODO{\text{remove macro}} + % dont place label when one is provided + % \IfSubStringInString{label}\unexpanded{#3}{}{ + % \label{eq:#1} + % } + ##1% + \end{flalign} + } + % 1: equation for flalign environment + \newcommand{\eqFLAlign}[2]{ + \newFormulaEntry + \begin{alignat}{##1}% + % dont place label when one is provided + % \IfSubStringInString{label}\unexpanded{#3}{}{ + % \label{eq:#1} + % } + ##2% + \end{alignat} + } + \newcommand{\fig}[2][1.0]{ + \newFormulaEntry + \centering + \includegraphics[width=##1\textwidth]{##2} + } + % 1: content for the ttext environment + \newcommand{\ttxt}[2][#1:desc]{ + \newFormulaEntry + \begin{ttext}[##1] + ##2 + \end{ttext} + } + % 1: symbol + % 2: units + % 3: comment key to translation + \newcommand{\quantity}[3]{% + \quantity@new[\fqname]{#1}{##1}{##2}{##3} + \newFormulaEntry + \quantity@print{#1} + } + + % must be used only in third argument of "constant" command + % 1: value + % 2: unit + \newcommand{\val}[2]{ + \constant@addValue{#1}{##1}{##2} + } + % 1: symbol + % 2: either exp or def; experimentally or defined constant + % 3: one or more \val{value}{unit} commands + \newcommand{\constant}[3]{ + \constant@new[\fqname]{#1}{##1}{##2} + \begingroup + ##3 + \endgroup + \newFormulaEntry + \constant@print{#1} + } +}{} + +\newenvironment{formula}[1]{ + \begin{formulainternal}{#1} + + \begingroup + \label{f:\fqname:#1} + \storeLabel{\fqname:#1} + \par\noindent\ignorespaces + % \textcolor{gray}{\hrule} + % \vspace{0.5\baselineskip} + \NameWithDescription[\descwidth]{\fqname:#1}{\fqname:#1_desc} + \hfill + \begin{ContentBoxWithExplanation}{\fqname:#1_defs} +}{ + \end{ContentBoxWithExplanation} + \endgroup + \separateEntries + % \textcolor{fg3}{\hrule} + % \vspace{0.5\baselineskip} + \ignorespacesafterend + \end{formulainternal} +} + + +% BIG FORMULA +\newenvironment{bigformula}[1]{ + \begin{formulainternal}{#1} + + \edef\tmpFormulaName{#1} + \par\noindent + \begin{minipage}{\textwidth} % using a minipage to now allow line breaks within the bigformula + \label{f:\fqname:#1} + \par\noindent\ignorespaces + % \textcolor{gray}{\hrule} + % \vspace{0.5\baselineskip} + \textbf{ + \IfTranslationExists{\fqname:#1}{% + \raggedright + \GT{\fqname:#1} + }{\detokenize{#1}} + } + \IfTranslationExists{\fqname:#1_desc}{ + : {\color{fg1} \GT{\fqname:#1_desc}} + }{} + \hfill + \par +}{ + \edef\tmpContentDefs{\fqname:\tmpFormulaName_defs} + \IfTranslationExists{\tmpContentDefs}{% + \smartnewline + \noindent + \begingroup + \color{fg1} + \GT{\tmpContentDefs} + % \edef\temp{\GT{#1_defs}} + % \expandafter\StrSubstitute\expandafter{\temp}{:}{\\} + \endgroup + }{} + \end{minipage} + \separateEntries + % \textcolor{fg3}{\hrule} + % \vspace{0.5\baselineskip} + \ignorespacesafterend + \end{formulainternal} +} + +\newenvironment{hiddenformula}[1]{ + \begin{formulainternal}{#1} + \renewcommand{\eq}[1]{} + \renewcommand{\eqAlignedAt}[2]{} + \renewcommand{\eqFLAlign}[2]{} + \renewcommand{\fig}[2][1.0]{} + \renewcommand{\ttxt}[2][#1:desc]{} + % 1: symbol + % 2: units + % 3: comment key to translation + \renewcommand{\quantity}[3]{% + \quantity@new[\fqname]{#1}{##1}{##2}{##3} + } + % 1: symbol + % 2: either exp or def; experimentally or defined constant + % 3: one or more \val{value}{unit} commands + \renewcommand{\constant}[3]{ + \constant@new[\fqname]{#1}{##1}{##2} + \begingroup + ##3 + \endgroup + } +}{ + \end{formulainternal} +} diff --git a/src/pkg/mqfqname.sty b/src/pkg/mqfqname.sty new file mode 100644 index 0000000..45c1dbd --- /dev/null +++ b/src/pkg/mqfqname.sty @@ -0,0 +1,209 @@ +\ProvidesPackage{mqfqname} +\RequirePackage{mqlua} +\RequirePackage{etoolbox} + + +\directlua{ + sections = sections or {} + + function fqnameEnter(name) + table.insert(sections, name) + % table.sort(sections) + end + + function fqnameLeave() + if table.getn(sections) > 0 then + table.remove(sections) + end + end + + function fqnameGet() + return table.concat(sections, ":") + end + + function fqnameLeaveOnlyFirstN(n) + if n >= 0 then + while table.getn(sections) > n do + table.remove(sections) + end + end + end +} +\newcommand{\mqfqname@update}{% + \edef\fqname{\luavar{fqnameGet()}} +} +\newcommand{\mqfqname@enter}[1]{% + \directlua{fqnameEnter("\luaescapestring{#1}")}% + \mqfqname@update +} +\newcommand{\mqfqname@leave}{% + \directlua{fqnameLeave()}% + \mqfqname@update +} + +\newcommand{\mqfqname@leaveOnlyFirstN}[1]{% + \directlua{fqnameLeaveOnlyFirstN(#1)}% +} + +% SECTIONING +% start
, get heading from translation, set label +% secFqname is the fully qualified name of sections: the keys of all previous sections joined with a ':' +% fqname is secFqname: where is the key/id of some environment, like formula +% [1]: code to run after setting \fqname, but before the \part, \section etc +% 2: key +\newcommand{\Part}[2][desc]{ + \newpage + \mqfqname@leaveOnlyFirstN{0} + \mqfqname@enter{#2} + \edef\secFqname{\fqname} + #1 + % this is necessary so that \part/\section... takes the fully expanded string. Otherwise the pdf toc will have just the fqname + \edef\fqnameText{\GT{\fqname}} + \part{\fqnameText} + \label{sec:\fqname} +} +\newcommand{\Section}[2][]{ + \mqfqname@leaveOnlyFirstN{1} + \mqfqname@enter{#2} + \edef\secFqname{\fqname} + #1 + \edef\fqnameText{\GT{\fqname}} + \section{\fqnameText} + \label{sec:\fqname} +} +\newcommand{\Subsection}[2][]{ + \mqfqname@leaveOnlyFirstN{2} + \mqfqname@enter{#2} + \edef\secFqname{\fqname} + #1 + \edef\fqnameText{\GT{\fqname}} + \subsection{\fqnameText} + \label{sec:\fqname} +} +\newcommand{\Subsubsection}[2][]{ + \mqfqname@leaveOnlyFirstN{3} + \mqfqname@enter{#2} + \edef\secFqname{\fqname} + #1 + \edef\fqnameText{\GT{\fqname}} + \subsubsection{\fqnameText} + \label{sec:\fqname} +} +\edef\fqname{NULL} + +\newcommand\printFqName{\expandafter\detokenize\expandafter{\fqname}} + + +\newcommand\luaDoubleFieldValue[3]{% + \directlua{ + if #1 \string~= nil and #1[#2] \string~= nil and #1[#2][#3] \string~= nil then + tex.sprint(#1[#2][#3]) + return + end + luatexbase.module_warning('luaDoubleFieldValue', 'Invalid indices to `#1`: `#2` and `#3`'); + tex.sprint("???") + }% +} +% REFERENCES +% All xyzRef commands link to the key using the translated name +% Uppercase (XyzRef) commands have different link texts, but the same link target +% 1: key/fully qualified name (without qty/eq/sec/const/el... prefix) + +% Equations/Formulas +% \newrobustcmd{\fqEqRef}[1]{% +\newrobustcmd{\fqEqRef}[1]{% + % \edef\fqeqrefname{\GT{#1}} + % \hyperref[eq:#1]{\fqeqrefname} + \hyperref[f:#1]{\GT{#1}}% +} +% Formula in the current section +\newrobustcmd{\secEqRef}[1]{% + % \edef\fqeqrefname{\GT{#1}} + % \hyperref[eq:#1]{\fqeqrefname} + \hyperref[f:\secFqname:#1]{\GT{\secFqname:#1}}% +} + +% Section +% +\newrobustcmd{\fqSecRef}[1]{% + \hyperref[sec:#1]{\GT{#1}}% +} +% Quantities +% +\newrobustcmd{\qtyRef}[1]{% + \edef\tempname{\luaDoubleFieldValue{quantities}{"#1"}{"linkto"}}% + \hyperref[qty:#1]{\expandafter\GT\expandafter{\tempname:#1}}% +} +% +\newrobustcmd{\QtyRef}[1]{% + $\luaDoubleFieldValue{quantities}{"#1"}{"symbol"}$ \qtyRef{#1}% +} +% Constants +% +\newrobustcmd{\constRef}[1]{% + \edef\tempname{\luaDoubleFieldValue{constants}{"#1"}{"linkto"}}% + \hyperref[const:#1]{\expandafter\GT\expandafter{\tempname:#1}}% +} +% +\newrobustcmd{\ConstRef}[1]{% + $\luaDoubleFieldValue{constants}{"#1"}{"symbol"}$ \constRef{#1}% +} +% Element from periodic table +% +\newrobustcmd{\elRef}[1]{% + \hyperref[el:#1]{{\color{fg0}#1}}% +} +% +\newrobustcmd{\ElRef}[1]{% + \hyperref[el:#1]{\GT{el:#1}}% +} + + + +% "LABELS" +% These currently do not place a label, +% instead they provide an alternative way to reference an existing label +\directLuaAux{ + absLabels = absLabels or {} + abbrLabels = abbrLabel or {} +} +% [1]: target (fqname to point to) +% 2: key +\newcommand{\absLink}[2][sec:\fqname]{ + \directLuaAuxExpand{ + absLabels["#2"] = [[#1]] + } +} +% [1]: target (fqname to point to) +% 2: key +% 3: label (abbreviation) +\newcommand{\abbrLink}[3][sec:\fqname]{ + \directLuaAuxExpand{ + abbrLabels["#2"] = {} + abbrLabels["#2"]["abbr"] = [[#3]] + abbrLabels["#2"]["fqname"] = [[#1]] + } +} +% [1]: +\newrobustcmd{\absRef}[2][\relax]{% + \directlua{ + if absLabels["#2"] == nil then + tex.sprint("\\detokenize{#2}???") + else + if "#1" == "" then %-- if [#1] is not given, use translation of key as text, else us given text + tex.sprint("\\hyperref[" .. absLabels["#2"] .. "]{\\GT{" .. absLabels["#2"] .. "}}") + else + tex.sprint("\\hyperref[" .. absLabels["#2"] .. "]{\luaescapestring{#1}}") + end + end + } +} +\newrobustcmd{\abbrRef}[1]{% + \directlua{ + if abbrLabels["#1"] == nil then + tex.sprint("\\detokenize{#1}???") + else + tex.sprint("\\hyperref[" .. abbrLabels["#1"]["fqname"] .. "]{" .. abbrLabels["#1"]["abbr"] .. "}") + end + } +} diff --git a/src/pkg/mqlua.sty b/src/pkg/mqlua.sty new file mode 100644 index 0000000..b920967 --- /dev/null +++ b/src/pkg/mqlua.sty @@ -0,0 +1,88 @@ +\ProvidesPackage{mqlua} + +\RequirePackage{luacode} +\LuaCodeDebugOn + +\newcommand\luavar[1]{\directlua{tex.sprint(#1)}} + +\begin{luacode*} +function warning(message) + -- Get the current file name and line number + -- local info = debug.getinfo(2, "Sl") + -- local file_name = info.source + -- local line_number = info.currentline + -- tex.error(string.format("Warning %s at %s:%d", message, file_name, line_number)) + texio.write("\nWARNING: " .. message .. "\n") +end + +OUTDIR = os.getenv("TEXMF_OUTPUT_DIRECTORY") or "." + +function fileExists(file) + local f = io.open(file, "rb") + if f then f:close() end + return f ~= nil +end + + +warning("TEST") +\end{luacode*} + +% units: siunitx units arguments, possibly chained by '=' +% returns: 1\si{unit1} = 1\si{unit2} = ... +\directlua{ +function split_and_print_units(units) + if units == nil then + tex.print("1") + return + end + + local parts = {} + for part in string.gmatch(units, "[^=]+") do + table.insert(parts, part) + end + local result = "" + for i, unit in ipairs(parts) do + if i > 1 then result = result .. " = " end + result = result .. "\\SI{1}{" .. unit .. "}" + end + tex.print(result) +end +} + +% STRING UTILITY +\luadirect{ + function string.startswith(s, start) + return string.sub(s,1,string.len(start)) == start + end + + function string.sanitize(s) + % -- Use gsub to replace the specified characters with an empty string + local result = s:gsub("[_^&]", "") + return result + end +} +% Write directlua command to aux and run it as well +% This one expands the argument in the aux file: +\newcommand\directLuaAuxExpand[1]{ + \immediate\write\luaAuxFile{\noexpand\directlua{#1}} + \directlua{#1} +} +% This one does not: +\newcommand\directLuaAux[1]{ + \immediate\write\luaAuxFile{\noexpand\directlua{\detokenize{#1}}} + \directlua{#1} +} + +% read +\IfFileExists{\jobname.lua.aux}{% + \input{\jobname.lua.aux}% +}{% + % \@latex@warning@no@line{"Lua aux not loaded!"} +} +\def\luaAuxLoaded{False} + +% write +\newwrite\luaAuxFile +\immediate\openout\luaAuxFile=\jobname.lua.aux +\immediate\write\luaAuxFile{\noexpand\def\noexpand\luaAuxLoaded{True}}% +\AtEndDocument{\immediate\closeout\luaAuxFile} diff --git a/src/util/periodic_table.tex b/src/pkg/mqperiodictable.sty similarity index 98% rename from src/util/periodic_table.tex rename to src/pkg/mqperiodictable.sty index d74f7ee..216b11a 100644 --- a/src/util/periodic_table.tex +++ b/src/pkg/mqperiodictable.sty @@ -1,3 +1,6 @@ +\ProvidesPackage{mqperiodictable} +\RequirePackage{mqtranslation} +\RequirePackage{mqlua} % Store info about elements in a lua table % Print as list or as periodic table % The data is taken from https://pse-info.de/de/data as json and parsed by the scripts/periodic_table.py @@ -164,7 +167,4 @@ end } \end{tikzpicture} - - - } diff --git a/src/pkg/mqquantity.sty b/src/pkg/mqquantity.sty new file mode 100644 index 0000000..14a8501 --- /dev/null +++ b/src/pkg/mqquantity.sty @@ -0,0 +1,43 @@ +\ProvidesPackage{mqquantity} +\RequirePackage{mqlua} +\RequirePackage{etoolbox} + +\directLuaAux{ + if quantities == nil then + quantities = {} + end +} + +% [1]: label to point to +% 2: key - must expand to a valid lua string! +% 3: symbol +% 4: units +% 5: comment key to translation +\newcommand{\quantity@new}[5][\relax]{% + \directLuaAux{ + quantities["#2"] = {} + quantities["#2"]["symbol"] = [[\detokenize{#3}]] + quantities["#2"]["units"] = [[\detokenize{#4}]] + quantities["#2"]["comment"] = [[\detokenize{#5}]] + } + \ifstrempty{#1}{}{ + \directLuaAuxExpand{ + quantities["#2"]["linkto"] = [[#1]] %-- fqname required for getting the translation key + } + } +} + +% 1: key +\newcommand\quantity@print[1]{ + \begingroup % for label + Symbol: $\luavar{quantities["#1"]["symbol"]}$ + \\Unit: $\directlua{split_and_print_units(quantities["#1"]["units"])}$ + % label it only once + \directlua{ + if quantities["#1"]["labeled"] == nil then + quantities["#1"]["labeled"] = true + tex.print("\\label{qty:#1}") + end + } + \endgroup +} diff --git a/src/pkg/mqtranslation.sty b/src/pkg/mqtranslation.sty new file mode 100644 index 0000000..f5c29c5 --- /dev/null +++ b/src/pkg/mqtranslation.sty @@ -0,0 +1,177 @@ +\ProvidesPackage{mqtranslation} +\RequirePackage{mqfqname} +\RequirePackage{etoolbox} +\RequirePackage{amsmath} +\RequirePackage{mqlua} + +% TODO resolve circular dependency with fqname + +\begin{luacode} + translations = translations or {} + -- string to append to missing translations + -- unknownTranslation = "???" + unknownTranslation = "" + language = "\languagename" + fallbackLanguage = "english" + -- using additional .aux extension because vimtex wouldnt stop compiling otherwise + translationsFilepath = OUTDIR .. "/translations.lua.aux" or "/tmp/translations.lua" + + function tlAdd(language, key, value) + if value == "" then + return + end + if translations[language] == nil then + translations[language] = {} + end + translations[language][key] = value + end + + + function tlExists(language, key) + return not (translations[language] == nil or translations[language][key] == nil) + end + + function tlExistsFallback(language, key) + if tlExists(language, key) then + return true + end + return tlExists(fallbackLanguage, key) + end + + + function tlGet(language, key) + if tlExists(language, key) then + return translations[language][key] + end + return string.sanitize(key .. unknownTranslation) + end + + function tlGetFallback(language, key) + if tlExists(language, key) then + return translations[language][key] + end + if language ~= fallbackLanguage then + if tlExists(fallbackLanguage, key) then + return translations[fallbackLanguage][key] + end + end + return string.sanitize(key .. unknownTranslation) + end + + function tlGetCurrent(key) + return tlGet(language, key) + end + + function tlGetFallbackCurrent(key) + return tlGetFallback(language, key) + end + +\end{luacode} + +% Write the translations table as lua code to an auxiliary file +% If the file exists, read it when loading the package. +% This way, translations may be used before they are defined, since it will exist in the second compilation. +\begin{luacode*} + function serialize(tbl) + local result = {} + for k, v in pairs(tbl) do + local key = type(k) == "string" and ("[\"%s\"]"):format(k) or "[" .. tostring(k) .. "]" + -- using level 2 multiline string to avoid problems when a string ends with ] + local value = type(v) == "table" and serialize(v) or "[==[" .. tostring(v) .. "]==]" + table.insert(result, key .. " = " .. value) + end + return "{" .. table.concat(result, ",\n" ) .. "}\n" + end + + + function dumpTranslations() + local file = io.open(translationsFilepath, "w") + file:write("return " .. serialize(translations) .. "\n") + file:close() + end + + if fileExists(translationsFilepath) then + translations = dofile(translationsFilepath) or {} + end +\end{luacode*} + + +\AtEndDocument{\directlua{dumpTranslations()}} + +% +% TRANSLATION COMMANDS +% +% The lower case commands use \fqname based keys, the upper case absolute keys. +% Example: +% \dt[example]{german}{Beispiel} % defines the key \fqname:example +% \ger[example]{Beispiel} % defines the key \fqname:example +% \DT[example]{german}{Beispiel} % defines the key example +% \Ger[example]{Beispiel} % defines the key example +% +% For ease of use in the ttext environment and the optional argument of the \Part, \Section, ... commands, +% all "define translation" commands use \fqname as default key + +% Get a translation +% expandafter required because the translation commands dont expand anything +% shortcuts for translations +% 1: key +\newcommand{\gt}[1]{\luavar{tlGetFallbackCurrent(\luastring{\fqname:#1})}} +\newrobustcmd{\robustGT}[1]{\luavar{tlGetFallbackCurrent(\luastring{#1})}} +\newcommand{\GT}[1]{\luavar{tlGetFallbackCurrent(\luastring{#1})}} + +% text variants for use in math mode +\newcommand{\tgt}[1]{\text{\gt{#1}}} +\newcommand{\tGT}[1]{\text{\GT{#1}}} + +% Define a new translation +% [1]: key, 2: lang, 3: translation +\newcommand{\dt}[3][\fqname]{% + \directlua{ + if \luastring{#1} == \luastring{\fqname} then + tlAdd(\luastring{#2}, \luastring{\fqname}, \luastringN{#3}) + else + tlAdd(\luastring{#2}, \luastring{\fqname:#1}, \luastringN{#3}) + end + } +} + +% Define a new translation +% [1]: key, 2: lang, 3: translation +\newcommand{\DT}[3][\fqname]{% + \directlua{ + if \luastring{#1} == \luastring{\fqname} then + tlAdd(\luastring{#2}, \luastring{\fqname}, \luastringN{#3}) + else + tlAdd(\luastring{#2}, \luastring{#1}, \luastringN{#3}) + end + } +} +% [1]: key, 2: translation +\newcommand{\ger}[2][\fqname]{\dt[#1]{german}{#2}} +\newcommand{\eng}[2][\fqname]{\dt[#1]{english}{#2}} + +\newcommand{\Ger}[2][\fqname]{\DT[#1]{german}{#2}} +\newcommand{\Eng}[2][\fqname]{\DT[#1]{english}{#2}} + +\newcommand{\IfTranslationExists}[3]{% + \directlua{ + if tlExistsFallback(language, \luastring{#1}) then + tex.sprint(\luastringN{#2}) + else + tex.sprint(\luastringN{#3}) + end + } +} + + +% use this to define text in different languages for the key +% the translation for is printed when the environment ends. +% (temporarily change fqname to the \fqname: to allow +% the use of \eng and \ger without the key parameter) +% [1]: key +\newenvironment{ttext}[1][desc]{% + \mqfqname@enter{#1}% +}{% + \GT{\fqname}% + \mqfqname@leave% +} diff --git a/src/quantities.tex b/src/quantities.tex index 01903eb..87ea284 100644 --- a/src/quantities.tex +++ b/src/quantities.tex @@ -82,6 +82,13 @@ \quantity{\tau}{\newton\m=\kg\m^2\per\s^2}{v} \end{formula} + \begin{formula}{pressure} + \desc{Pressure}{}{} + \desc[german]{Druck}{}{} + \quantity{p}{\newtone\per\m^2}{} + \end{formula} + + \Subsection[ \eng{Thermodynamics} \ger{Thermodynamik} @@ -106,9 +113,10 @@ \desc[german]{Ladung}{}{} \quantity{q}{\coulomb=\ampere\s}{} \end{formula} + \begin{formula}{charge_number} \desc{Charge number}{}{} - \desc[german]{ladungszahl}{Anzahl der Elementarladungen}{} + \desc[german]{Ladungszahl}{Anzahl der Elementarladungen}{} \quantity{Z}{}{} \end{formula} \begin{formula}{charge_density} @@ -136,6 +144,12 @@ \eq{T = \frac{1}{f}} \end{formula} + \begin{formula}{conductivity} + \desc{Conductivity}{}{} + \desc[german]{Leitfähigkeit}{}{} + \quantity{\sigma}{\per\ohm\m}{} + \end{formula} + \Subsection[ \eng{Others} \ger{Sonstige} diff --git a/src/quantum_computing.tex b/src/quantum_computing.tex index 5992888..071662c 100644 --- a/src/quantum_computing.tex +++ b/src/quantum_computing.tex @@ -22,8 +22,12 @@ \ger{Gates} ]{gates} \begin{formula}{gates} - \desc{}{}{} - \desc[german]{}{}{} + \desc{Gates}{}{} + \desc[german]{Gates}{}{} + \eng[bitflip]{Bitflip} + \eng[bitphaseflip]{Bit-Phase flip} + \eng[phaseflip]{Phaseflip} + \eng[hadamard]{Hadamard} \begin{alignat}{2} & \text{\gt{bitflip}:} & \hat{X} &= \sigma_x = \sigmaxmatrix \\ & \text{\gt{bitphaseflip}:} & \hat{Y} &= \sigma_y = \sigmaymatrix \\ @@ -456,7 +460,7 @@ \eq{\Gamma_1 = \frac{1}{T_1} = \Gamma_{1\uparrow} + \Gamma_{1\downarrow}} \end{formula} - \begin{ttext}[long] + \begin{ttext}[longdesc] \eng{$\Gamma_{1\uparrow}$ is supressed at low temperatures because of detailed balance} \ger{$\Gamma_{1\uparrow}$ ist bei niedrigen Temperaturen unterdrückt wegen detailed balance} \end{ttext} diff --git a/src/test.tex b/src/test.tex index ac1058e..448f7ef 100644 --- a/src/test.tex +++ b/src/test.tex @@ -1,17 +1,24 @@ \part{Testing} +% \directlua{tex.sprint("Compiled in directory: \\detokenize{" .. lfs.currentdir() .. "}")} \\ +% \directlua{tex.sprint("Jobname: " .. tex.jobname)} \\ +% \directlua{tex.sprint("Output directory \\detokenize{" .. os.getenv("TEXMF_OUTPUT_DIRECTORY") .. "}")} \\ +% \directlua{tex.sprint("String sanitize \\detokenize{" .. string.sanitize("m_a^th?") .. "}")} + +\languagename + \paragraph{File loading} \noindent Lua Aux loaded? \luaAuxLoaded\\ -Translations Aux loaded? \translationsAuxLoaded\\ +% Translations Aux loaded? \translationsAuxLoaded\\ Input only: \inputOnlyFile \paragraph{Testing GT, GetTranslation, IfTranslationExists, IfTranslation} \addtranslation{english}{ttest}{This is the english translation of \texttt{ttest}} \noindent GT: ttest = \GT{ttest}\\ -GetTranslation: ttest = \GetTranslation{ttest}\\ -Is english? = \IfTranslation{english}{ttest}{yes}{no} \\ -Is german? = \IfTranslation{german}{ttest}{yes}{no} \\ +% GetTranslation: ttest = \GetTranslation{ttest}\\ +% Is english? = \IfTranslation{english}{ttest}{yes}{no} \\ +% Is german? = \IfTranslation{german}{ttest}{yes}{no} \\ Is defined = \IfTranslationExists{ttest}{yes}{no} \\ \paragraph{Testing translation keys containing macros} @@ -24,11 +31,11 @@ Is defined = \IfTranslationExists{ttest}{yes}{no} \\ \DT[\ttest:name]{german}{DT Mit Variable} \noindent GT: {\textbackslash}ttest:name = \GT{\ttest:name}\\ -GetTranslation: {\textbackslash}ttest:name = \GetTranslation{\ttest:name}\\ -Is english? = \IfTranslation{english}{\ttest:name}{yes}{no} \\ -Is german? = \IfTranslation{german}{\ttest:name}{yes}{no} \\ -Is defined? = \IfTranslationExists{\ttest:name}{yes}{no} \\ -Is defined? = \expandafter\IfTranslationExists\expandafter{\ttest:name}{yes}{no} +% GetTranslation: {\textbackslash}ttest:name = \GetTranslation{\ttest:name}\\ +% Is english? = \IfTranslation{english}{\ttest:name}{yes}{no} \\ +% Is german? = \IfTranslation{german}{\ttest:name}{yes}{no} \\ +% Is defined? = \IfTranslationExists{\ttest:name}{yes}{no} \\ +% Is defined? = \expandafter\IfTranslationExists\expandafter{\ttest:name}{yes}{no} \paragraph{Testing relative translations} \begingroup diff --git a/src/util/colorscheme.tex b/src/util/colorscheme.tex index c8d0b47..108423e 100644 --- a/src/util/colorscheme.tex +++ b/src/util/colorscheme.tex @@ -1,28 +1,38 @@ % This file was generated by scripts/formulary.py % Do not edit it directly, changes will be overwritten -\definecolor{fg0}{HTML}{1d2021} -\definecolor{bg0}{HTML}{f9f5d7} -\definecolor{fg1}{HTML}{3c3836} -\definecolor{fg2}{HTML}{504945} -\definecolor{fg3}{HTML}{665c54} -\definecolor{fg4}{HTML}{7c6f64} -\definecolor{bg1}{HTML}{ebdbb2} -\definecolor{bg2}{HTML}{d5c4a1} -\definecolor{bg3}{HTML}{bdae93} -\definecolor{bg4}{HTML}{a89984} -\definecolor{fg-red}{HTML}{9d0006} -\definecolor{fg-orange}{HTML}{af3a03} -\definecolor{fg-yellow}{HTML}{b57614} -\definecolor{fg-green}{HTML}{79740e} +\definecolor{fg-blue}{HTML}{072140} +\definecolor{bg-blue}{HTML}{5E94D4} +\definecolor{alt-blue}{HTML}{3070B3} +\definecolor{bg-yellow}{HTML}{FED702} +\definecolor{fg-yellow}{HTML}{CBAB01} +\definecolor{alt-yellow}{HTML}{FEDE34} +\definecolor{bg-orange}{HTML}{F7811E} +\definecolor{fg-orange}{HTML}{D99208} +\definecolor{alt-orange}{HTML}{F9BF4E} +\definecolor{bg-purple}{HTML}{B55CA5} +\definecolor{fg-purple}{HTML}{9B468D} +\definecolor{alt-purple}{HTML}{C680BB} +\definecolor{bg-red}{HTML}{EA7237} +\definecolor{fg-red}{HTML}{D95117} +\definecolor{alt-red}{HTML}{EF9067} +\definecolor{bg-green}{HTML}{9FBA36} +\definecolor{fg-green}{HTML}{7D922A} +\definecolor{alt-green}{HTML}{B6CE55} +\definecolor{bg-gray}{HTML}{475058} +\definecolor{fg-gray}{HTML}{20252A} +\definecolor{alt-gray}{HTML}{333A41} +\definecolor{bg-aqua}{HTML}{689d6a} \definecolor{fg-aqua}{HTML}{427b58} -\definecolor{fg-blue}{HTML}{076678} -\definecolor{fg-purple}{HTML}{8f3f71} -\definecolor{fg-gray}{HTML}{7c6f64} -\definecolor{bg-red}{HTML}{fb4934} -\definecolor{bg-orange}{HTML}{f38019} -\definecolor{bg-yellow}{HTML}{fabd2f} -\definecolor{bg-green}{HTML}{b8bb26} -\definecolor{bg-aqua}{HTML}{8ec07c} -\definecolor{bg-blue}{HTML}{83a598} -\definecolor{bg-purple}{HTML}{d3869b} -\definecolor{bg-gray}{HTML}{a89984} +\definecolor{fg0-hard}{HTML}{000000} +\definecolor{fg0}{HTML}{000000} +\definecolor{fg0-soft}{HTML}{20252A} +\definecolor{fg1}{HTML}{072140} +\definecolor{fg2}{HTML}{333A41} +\definecolor{fg3}{HTML}{475058} +\definecolor{fg4}{HTML}{6A757E} +\definecolor{bg0-hard}{HTML}{FFFFFF} +\definecolor{bg0}{HTML}{FBF9FA} +\definecolor{bg0-soft}{HTML}{EBECEF} +\definecolor{bg1}{HTML}{DDE2E6} +\definecolor{bg2}{HTML}{E3EEFA} +\definecolor{bg3}{HTML}{F0F5FA} diff --git a/src/util/environments.tex b/src/util/environments.tex index 07d0f1d..b0b490f 100644 --- a/src/util/environments.tex +++ b/src/util/environments.tex @@ -1,17 +1,3 @@ -% use this to define text in different languages for the key -% the translation for is printed when the environment ends. -% (temporarily change fqname to the \fqname: to allow -% the use of \eng and \ger without the key parameter) -% [1]: key -\newenvironment{ttext}[1][desc]{ - \edef\realfqname{\fqname} - \edef\fqname{\fqname:#1} -}{ - \expandafter\GT\expandafter{\fqname}% \\ - \edef\fqname{\realfqname} -} - - \def\descwidth{0.3\textwidth} \def\eqwidth{0.6\textwidth} @@ -22,336 +8,6 @@ } -% -% FORMULA ENVIRONMENT -% The following commands are meant to be used with the formula environment -% - -% Name in black and below description in gray -% [1]: minipage width -% 2: fqname of name -% 3: fqname of a translation that holds the explanation -\newcommand{\NameWithDescription}[3][\descwidth]{ - \begin{minipage}{#1} - \IfTranslationExists{#2}{ - \raggedright - \GT{#2} - }{\detokenize{#2}} - \IfTranslationExists{#3}{ - \\ {\color{fg1} \GT{#3}} - }{} - \end{minipage} -} - - -% TODO: rename -\newsavebox{\contentBoxBox} -% [1]: minipage width -% 2: fqname of a translation that holds the explanation -\newenvironment{ContentBoxWithExplanation}[2][\eqwidth]{ - \def\ContentFqName{#2} - \begin{lrbox}{\contentBoxBox} - \begin{minipage}{#1} -}{ - \IfTranslationExists{\ContentFqName}{% - \smartnewline - \noindent - \begingroup - \color{fg1} - \GT{\ContentFqName} - % \edef\temp{\GT{#1_defs}} - % \expandafter\StrSubstitute\expandafter{\temp}{:}{\\} - \endgroup - }{} - \end{minipage} - \end{lrbox} - \fbox{\usebox{\contentBoxBox}} -} - - - - -\newenvironment{formula}[1]{ - % [1]: language - % 2: name - % 3: description - % 4: definitions/links - \newcommand{\desc}[4][english]{ - % language, name, description, definitions - \ifblank{##2}{}{\dt[#1]{##1}{##2}} - \ifblank{##3}{}{\dt[#1_desc]{##1}{##3}} - \ifblank{##4}{}{\dt[#1_defs]{##1}{##4}} - } - \directlua{n_formulaEntries = 0} - - % makes this formula referencable with \abbrRef{} - % [1]: label to use - % 2: Abbreviation to use for references - \newcommand{\abbrLabel}[2][#1]{ - \abbrLink[f:\fqname]{##1}{##2} - } - % makes this formula referencable with \absRef{} - % [1]: label to use - \newcommand{\absLabel}[1][#1]{ - \absLink[f:\fqname]{##1} - } - - \newcommand{\newFormulaEntry}{ - \directlua{ - if n_formulaEntries > 0 then - tex.print("\\vspace{0.3\\baselineskip}\\hrule\\vspace{0.3\\baselineskip}") - end - n_formulaEntries = n_formulaEntries + 1 - } - % \par\noindent\ignorespaces - } - % 1: equation for align environment - \newcommand{\eq}[1]{ - \newFormulaEntry - \begin{align} - % \label{eq:\fqname:#1} - ##1 - \end{align} - } - % 1: equation for alignat environment - \newcommand{\eqAlignedAt}[2]{ - \newFormulaEntry - \begin{flalign}% - \TODO{\text{remove macro}} - % dont place label when one is provided - % \IfSubStringInString{label}\unexpanded{#3}{}{ - % \label{eq:#1} - % } - ##1% - \end{flalign} - } - % 1: equation for flalign environment - \newcommand{\eqFLAlign}[2]{ - \newFormulaEntry - \begin{alignat}{##1}% - % dont place label when one is provided - % \IfSubStringInString{label}\unexpanded{#3}{}{ - % \label{eq:#1} - % } - ##2% - \end{alignat} - } - \newcommand{\fig}[2][1.0]{ - \newFormulaEntry - \centering - \includegraphics[width=##1\textwidth]{##2} - } - % 1: content for the ttext environment - \newcommand{\ttxt}[2][#1:desc]{ - \newFormulaEntry - \begin{ttext}[##1] - ##2 - \end{ttext} - } - % 1: key - must expand to a valid lua string! - % 2: symbol - % 3: units - % 4: comment key to translation - \newcommand{\quantity}[3]{% - \directLuaAux{ - quantities["#1"] = {} - quantities["#1"]["symbol"] = [[\detokenize{##1}]] - quantities["#1"]["units"] = [[\detokenize{##2}]] - quantities["#1"]["comment"] = [[\detokenize{##3}]] - }\directLuaAuxExpand{ - quantities["#1"]["fqname"] = [[\fqname]] %-- fqname required for getting the translation key - } - \newFormulaEntry - \printQuantity{#1} - } - - % must be used only in third argument of "constant" command - % 1: value - % 2: unit - \newcommand{\val}[2]{ - \directLuaAux{ - table.insert(constants["#1"]["values"], { value = [[\detokenize{##1}]], unit = [[\detokenize{##2}]] }) - } - } - % 1: symbol - % 2: either exp or def; experimentally or defined constant - % 3: one or more \val{value}{unit} commands - \newcommand{\constant}[3]{ - \directLuaAux{ - constants["#1"] = {} - constants["#1"]["symbol"] = [[\detokenize{##1}]] - constants["#1"]["exp_or_def"] = [[\detokenize{##2}]] - constants["#1"]["values"] = {} %-- array of {value, unit} - }\directLuaAuxExpand{ - constants["#1"]["fqname"] = [[\fqname]] %-- fqname required for getting the translation key - } - \begingroup - ##3 - \endgroup - \newFormulaEntry - \printConstant{#1} - } - - \begingroup - \label{f:\fqname:#1} - \storeLabel{\fqname:#1} - \par\noindent\ignorespaces - % \textcolor{gray}{\hrule} - % \vspace{0.5\baselineskip} - \NameWithDescription[\descwidth]{\fqname:#1}{\fqname:#1_desc} - \hfill - \begin{ContentBoxWithExplanation}{\fqname:#1_defs} -}{ - \end{ContentBoxWithExplanation} - \endgroup - \separateEntries - % \textcolor{fg3}{\hrule} - % \vspace{0.5\baselineskip} - \ignorespacesafterend -} - - -% BIG FORMULA -\newenvironment{bigformula}[1]{ - % [1]: language - % 2: name - % 3: description - % 4: definitions/links - \newcommand{\desc}[4][english]{ - % language, name, description, definitions - \ifblank{##2}{}{\dt[#1]{##1}{##2}} - \ifblank{##3}{}{\dt[#1_desc]{##1}{##3}} - \ifblank{##4}{}{\dt[#1_defs]{##1}{##4}} - } - \directlua{n_formulaEntries = 0} - \newcommand{\newFormulaEntry}{ - \directlua{ - if n_formulaEntries > 0 then - tex.print("\\vspace{0.3\\baselineskip}\\hrule\\vspace{0.3\\baselineskip}") - end - n_formulaEntries = n_formulaEntries + 1 - } - % \par\noindent\ignorespaces - } - % 1: equation for align environment - - \edef\tmpFormulaName{#1} - \par\noindent - \begin{minipage}{\textwidth} % using a minipage to now allow line breaks within the bigformula - \label{f:\fqname:#1} - \par\noindent\ignorespaces - % \textcolor{gray}{\hrule} - % \vspace{0.5\baselineskip} - \textbf{ - \IfTranslationExists{\fqname:#1}{% - \raggedright - \GT{\fqname:#1} - }{\detokenize{#1}} - } - \IfTranslationExists{\fqname:#1_desc}{ - : {\color{fg1} \GT{\fqname:#1_desc}} - }{} - \hfill - \par -}{ - \edef\tmpContentDefs{\fqname:\tmpFormulaName_defs} - \IfTranslationExists{\tmpContentDefs}{% - \smartnewline - \noindent - \begingroup - \color{fg1} - \GT{\tmpContentDefs} - % \edef\temp{\GT{#1_defs}} - % \expandafter\StrSubstitute\expandafter{\temp}{:}{\\} - \endgroup - }{} - \end{minipage} - \separateEntries - % \textcolor{fg3}{\hrule} - % \vspace{0.5\baselineskip} - \ignorespacesafterend -} -% -% QUANTITY -% - -% units: siunitx units arguments, possibly chained by '=' -% returns: 1\si{unit1} = 1\si{unit2} = ... -\directlua{ - function split_and_print_units(units) - if units == nil then - tex.print("1") - return - end - - local parts = {} - for part in string.gmatch(units, "[^=]+") do - table.insert(parts, part) - end - local result = "" - for i, unit in ipairs(parts) do - if i > 1 then result = result .. " = " end - result = result .. "\\SI{1}{" .. unit .. "}" - end - tex.print(result) - end -} - - -% % for TOC -% \refstepcounter{constant}% -% % \addquantity{\expandafter\gt\expandafter{\qtyname}}% -% % \noindent\textbf{My Environment \themyenv: #1}\par% -% } -\directLuaAux{ - if constants == nil then - constants = {} - end -} -\newcommand\printConstant[1]{ - \begingroup % for label - Symbol: $\luavar{constants["#1"]["symbol"]}$ - % \\Unit: $\directlua{split_and_print_units(constants["#1"]["units"])}$ - \directlua{ - tex.print("\\\\\\GT{const:"..constants["#1"]["exp_or_def"].."}") - } - \directlua{ - %--tex.sprint("Hier steht Luatext" .. ":", #constVals) - for i, pair in ipairs(constants["#1"]["values"]) do - tex.sprint("\\\\\\hspace*{1cm}${", pair["value"], "}\\,\\si{", pair["unit"], "}$") - %--tex.sprint("VALUE ", i, v) - end - } - % label it only once - \directlua{ - if constants["#1"]["labeled"] == nil then - constants["#1"]["labeled"] = true - tex.print("\\label{const:#1}") - end - } - \endgroup -} - -\newcounter{constant} - -\directLuaAux{ - if quantities == nil then - quantities = {} - end -} -\newcommand\printQuantity[1]{ - \begingroup % for label - Symbol: $\luavar{quantities["#1"]["symbol"]}$ - \\Unit: $\directlua{split_and_print_units(quantities["#1"]["units"])}$ - % label it only once - \directlua{ - if quantities["#1"]["labeled"] == nil then - quantities["#1"]["labeled"] = true - tex.print("\\label{qty:#1}") - end - } - \endgroup -} % Custon environment with table of contents, requires etoolbox? % Define a custom list diff --git a/src/util/translation.tex b/src/util/translation.tex deleted file mode 100644 index 6a57059..0000000 --- a/src/util/translation.tex +++ /dev/null @@ -1,102 +0,0 @@ -% -% TRANSLATION COMMANDS -% -% The lower case commands use \fqname based keys, the upper case absolute keys. -% Example: -% \dt[example]{german}{Beispiel} % defines the key \fqname:example -% \ger[example]{Beispiel} % defines the key \fqname:example -% \DT[example]{german}{Beispiel} % defines the key example -% \Ger[example]{Beispiel} % defines the key example -% -% For ease of use in the ttext environment and the optional argument of the \Part, \Section, ... commands, -% all "define translation" commands use \fqname as default key - -% Get a translation -% expandafter required because the translation commands dont expand anything -% shortcuts for translations -% 1: key - -\newcommand{\IfTranslationExists}[1]{% - % only check english. All translations must be defined for english - \def\tempiftranslation{\IfTranslation{english}}% - \expandafter\tempiftranslation\expandafter{#1}% -} -\newcommand{\iftranslation}[1]{% - \IfTranslation{english}{\fqname:#1} - % \expandafter\IfTranslationExists\expandafter{\fqname:#1} -} - -\newrobustcmd{\robustGt}[1]{% - \IfTranslationExists{\fqname:#1}{% - \expandafter\GetTranslation\expandafter{\fqname:#1}% - }{% - \printFqName:\detokenize{#1}% - }% -} -\newcommand{\gt}[1]{% - \IfTranslationExists{\fqname:#1}{% - \expandafter\GetTranslation\expandafter{\fqname:#1}% - }{% - \printFqName:\detokenize{#1}% - }% -} -\newrobustcmd{\GT}[1]{%\expandafter\GetTranslation\expandafter{#1}} - \IfTranslationExists{#1}{% - \expandafter\GetTranslation\expandafter{#1}% - }{% ?? - \detokenize{#1}% - }% -} -% text variants for use in math mode -\newcommand{\tgt}[1]{\text{\gt{#1}}} -\newcommand{\tGT}[1]{\text{\GT{#1}}} - -% Define a translation and also make the fallback if it is the english translation -% 1: lang, 2: key, 3: translation -\newcommand{\addtranslationcustom}[3]{ - \ifstrequal{#1}{english}{ - \addtranslationfallback{#2}{#3} - \immediate\write\translationsaux{\noexpand\addtranslationfallback{#2}{\detokenize{#3}}} - % \immediate\write\translationsaux{\noexpand\addtranslationfallback{#2}{{#3}}}% - }{} - \immediate\write\translationsaux{\noexpand\addtranslation{#1}{#2}{\detokenize{#3}}} - \addtranslation{#1}{#2}{#3} -} - -% Define a new translation -% [1]: key, 2: lang, 3: translation -\newcommand{\dt}[3][\fqname]{ - \ifstrempty{#3}{}{ % dont add empty translations so that the fallback will be used instead - % hack because using expandafter on the second arg didnt work - \def\tempaddtranslation{\addtranslationcustom{#2}} - \ifstrequal{#1}{\fqname}{ - % \expandafter\tempaddtranslation\expandafter{\fqname}{#3} - \addtranslationcustom{#2}{#1}{#3} - }{ - \addtranslationcustom{#2}{\fqname:#1}{#3} - % \expandafter\tempaddtranslation\expandafter{\fqname:#1}{#3} - } - } -} -% Define a new translation -% [1]: key, 2: lang, 3: translation -\newcommand{\DT}[3][dummy]{ - \ifstrempty{#3}{}{ % dont add empty translations so that the fallback will be used instead - % hack because using expandafter on the second arg didnt work - \def\tempaddtranslation{\addtranslationcustom{#2}} - \ifstrequal{#1}{dummy}{ - % \expandafter\tempaddtranslation\expandafter{\fqname}{#3} - \addtranslationcustom{#2}{\fqname}{#3} - }{ - % \expandafter\tempaddtranslation\expandafter{#1}{#3} - \addtranslationcustom{#2}{#1}{#3} - } - } -} -% [1]: key, 2: translation -\newcommand{\ger}[2][\fqname]{\dt[#1]{german}{#2}} -\newcommand{\eng}[2][\fqname]{\dt[#1]{english}{#2}} - -\newcommand{\Ger}[2][\fqname]{\DT[#1]{german}{#2}} -\newcommand{\Eng}[2][\fqname]{\DT[#1]{english}{#2}} -