-- | Defines main LaTeX printer functions. For more information on each of the helper functions, please view the [source files](https://jacquescarette.github.io/Drasil/docs/full/drasil-printers-0.1.10.0/src/Language.Drasil.TeX.Print.html).
module Language.Drasil.TeX.Print(genTeX, pExpr, pUnit, spec) where

import Prelude hiding (print)
import Data.Bifunctor (bimap)
import Data.List (transpose, partition)
import Text.PrettyPrint (integer, text, (<+>))
import qualified Text.PrettyPrint as TP
import Numeric (showEFloat)
import Control.Arrow (second)

import qualified Language.Drasil as L
import qualified Language.Drasil.Display as LD

import Language.Drasil.Config (colAwidth, colBwidth, bibStyleT, bibFname)
import Language.Drasil.Printing.AST (Spec, ItemType(Nested, Flat), 
  ListType(Ordered, Unordered, Desc, Definitions, Simple), 
  Spec(Quote, EmptyS, Ref, S, Sp, HARDNL, E, (:+:)), 
  Fence(Norm, Abs, Curly, Paren), Expr, 
  Ops(..), Spacing(Thin), Fonts(Emph, Bold), 
  Expr(..), OverSymb(Hat), Label,
  LinkType(Internal, Cite2, External))
import Language.Drasil.Printing.Citation (HP(Verb, URL), CiteField(HowPublished, 
  Year, Volume, Type, Title, Series, School, Publisher, Organization, Pages,
  Month, Number, Note, Journal, Editor, Chapter, Institution, Edition, BookTitle,
  Author, Address), Citation(Cite), BibRef)
import Language.Drasil.Printing.LayoutObj (Document(Document), LayoutObj(..))
import qualified Language.Drasil.Printing.Import as I
import Language.Drasil.Printing.Helpers hiding (br, paren, sq, sqbrac)
import Language.Drasil.TeX.Helpers (author, bold, br, caption, center, centering,
  cite, command, command0, commandD, command2D, description, document, empty,
  enumerate, externalref, figure, fraction, includegraphics, item, item',
  itemize, label, maketitle, maketoc, mathbb, mkEnv, mkEnvArgBr, mkEnvArgSq,
  mkMinipage, newline, newpage, parens, quote, sec, snref, sq, superscript,
  symbDescription, texSym, title, toEqn)
import Language.Drasil.TeX.Monad (D, MathContext(Curr, Math, Text), (%%), ($+$),
  hpunctuate, lub, runPrint, switch, toMath, toText, unPL, vcat, vpunctuate)
import Language.Drasil.TeX.Preamble (genPreamble)
import Language.Drasil.Printing.PrintingInformation (PrintingInformation)

-- | Generates a LaTeX document.
genTeX :: L.Document -> PrintingInformation -> TP.Doc
genTeX :: Document -> PrintingInformation -> Doc
genTeX doc :: Document
doc@(L.Document _ _ toC :: ShowTableOfContents
toC _) sm :: PrintingInformation
sm = 
  PrintLaTeX Doc -> MathContext -> Doc
forall a. PrintLaTeX a -> MathContext -> a
runPrint (PrintingInformation
-> ShowTableOfContents -> Document -> PrintLaTeX Doc
buildStd PrintingInformation
sm ShowTableOfContents
toC (Document -> PrintLaTeX Doc) -> Document -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ PrintingInformation -> Document -> Document
I.makeDocument PrintingInformation
sm (Document -> Document) -> Document -> Document
forall a b. (a -> b) -> a -> b
$ Document -> Document
L.checkToC Document
doc) MathContext
Text
genTeX L.Notebook{} _ = Doc
TP.empty

-- | Helper to build the document.
buildStd :: PrintingInformation -> L.ShowTableOfContents -> Document -> D
buildStd :: PrintingInformation
-> ShowTableOfContents -> Document -> PrintLaTeX Doc
buildStd sm :: PrintingInformation
sm toC :: ShowTableOfContents
toC (Document t :: Title
t a :: Title
a c :: [LayoutObj]
c) =
  [LayoutObj] -> PrintLaTeX Doc
genPreamble [LayoutObj]
c PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%%
  PrintLaTeX Doc -> PrintLaTeX Doc
title (Title -> PrintLaTeX Doc
spec Title
t) PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%%
  PrintLaTeX Doc -> PrintLaTeX Doc
author (Title -> PrintLaTeX Doc
spec Title
a) PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%%
  case ShowTableOfContents
toC of 
    L.ToC -> PrintLaTeX Doc -> PrintLaTeX Doc
document (PrintLaTeX Doc
maketitle PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% PrintLaTeX Doc
maketoc PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% PrintLaTeX Doc
newpage PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% PrintingInformation -> [LayoutObj] -> PrintLaTeX Doc
print PrintingInformation
sm [LayoutObj]
c) -- includes ToC generation
    _ -> PrintLaTeX Doc -> PrintLaTeX Doc
document (PrintLaTeX Doc
maketitle PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% PrintLaTeX Doc
newpage PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% PrintingInformation -> [LayoutObj] -> PrintLaTeX Doc
print PrintingInformation
sm [LayoutObj]
c) -- omits ToC generation

-- clean until here; lo needs its sub-functions fixed first though
-- | Helper for converting layout objects into a more printable form.
lo :: LayoutObj -> PrintingInformation -> D
lo :: LayoutObj -> PrintingInformation -> PrintLaTeX Doc
lo (Header d :: Depth
d t :: Title
t l :: Title
l)         _ = Depth -> PrintLaTeX Doc -> PrintLaTeX Doc
sec Depth
d (Title -> PrintLaTeX Doc
spec Title
t) PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% PrintLaTeX Doc -> PrintLaTeX Doc
label (Title -> PrintLaTeX Doc
spec Title
l)
lo (HDiv _ con :: [LayoutObj]
con _)        sm :: PrintingInformation
sm = PrintingInformation -> [LayoutObj] -> PrintLaTeX Doc
print PrintingInformation
sm [LayoutObj]
con -- FIXME ignoring 2 arguments?
lo (Paragraph contents :: Title
contents)   _ = PrintLaTeX Doc -> PrintLaTeX Doc
toText (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ PrintLaTeX Doc -> PrintLaTeX Doc
newline (Title -> PrintLaTeX Doc
spec Title
contents)
lo (EqnBlock contents :: Title
contents)    _ = Title -> PrintLaTeX Doc
makeEquation Title
contents
lo (Table _ rows :: [[Title]]
rows r :: Title
r bl :: Bool
bl t :: Title
t)  _ = PrintLaTeX Doc -> PrintLaTeX Doc
toText (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ [[Title]]
-> PrintLaTeX Doc -> Bool -> PrintLaTeX Doc -> PrintLaTeX Doc
makeTable [[Title]]
rows (Title -> PrintLaTeX Doc
spec Title
r) Bool
bl (Title -> PrintLaTeX Doc
spec Title
t)
lo (Definition _ ssPs :: [(String, [LayoutObj])]
ssPs l :: Title
l) sm :: PrintingInformation
sm = PrintLaTeX Doc -> PrintLaTeX Doc
toText (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ PrintingInformation
-> [(String, [LayoutObj])] -> PrintLaTeX Doc -> PrintLaTeX Doc
makeDefn PrintingInformation
sm [(String, [LayoutObj])]
ssPs (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Title -> PrintLaTeX Doc
spec Title
l
lo (List l :: ListType
l)               _ = PrintLaTeX Doc -> PrintLaTeX Doc
toText (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ ListType -> PrintLaTeX Doc
makeList ListType
l
lo (Figure r :: Title
r c :: Title
c f :: String
f wp :: MaxWidthPercent
wp)      _ = PrintLaTeX Doc -> PrintLaTeX Doc
toText (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ PrintLaTeX Doc
-> PrintLaTeX Doc -> String -> MaxWidthPercent -> PrintLaTeX Doc
makeFigure (Title -> PrintLaTeX Doc
spec Title
r) (Title -> PrintLaTeX Doc
spec Title
c) String
f MaxWidthPercent
wp
lo (Bib bib :: BibRef
bib)             sm :: PrintingInformation
sm = PrintLaTeX Doc -> PrintLaTeX Doc
toText (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ PrintingInformation -> BibRef -> PrintLaTeX Doc
makeBib PrintingInformation
sm BibRef
bib
lo (Graph ps :: [(Title, Title)]
ps w :: Maybe MaxWidthPercent
w h :: Maybe MaxWidthPercent
h c :: Title
c l :: Title
l)    _  = PrintLaTeX Doc -> PrintLaTeX Doc
toText (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ [(PrintLaTeX Doc, PrintLaTeX Doc)]
-> PrintLaTeX Doc
-> PrintLaTeX Doc
-> PrintLaTeX Doc
-> PrintLaTeX Doc
-> PrintLaTeX Doc
makeGraph
  (((Title, Title) -> (PrintLaTeX Doc, PrintLaTeX Doc))
-> [(Title, Title)] -> [(PrintLaTeX Doc, PrintLaTeX Doc)]
forall a b. (a -> b) -> [a] -> [b]
map ((Title -> PrintLaTeX Doc)
-> (Title -> PrintLaTeX Doc)
-> (Title, Title)
-> (PrintLaTeX Doc, PrintLaTeX Doc)
forall (p :: * -> * -> *) a b c d.
Bifunctor p =>
(a -> b) -> (c -> d) -> p a c -> p b d
bimap Title -> PrintLaTeX Doc
spec Title -> PrintLaTeX Doc
spec) [(Title, Title)]
ps)
  (Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text (String -> Doc) -> String -> Doc
forall a b. (a -> b) -> a -> b
$ String
-> (MaxWidthPercent -> String) -> Maybe MaxWidthPercent -> String
forall b a. b -> (a -> b) -> Maybe a -> b
maybe "" (\x :: MaxWidthPercent
x -> "text width = " String -> String -> String
forall a. [a] -> [a] -> [a]
++ MaxWidthPercent -> String
forall a. Show a => a -> String
show MaxWidthPercent
x String -> String -> String
forall a. [a] -> [a] -> [a]
++ "em ,") Maybe MaxWidthPercent
w)
  (Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text (String -> Doc) -> String -> Doc
forall a b. (a -> b) -> a -> b
$ String
-> (MaxWidthPercent -> String) -> Maybe MaxWidthPercent -> String
forall b a. b -> (a -> b) -> Maybe a -> b
maybe "" (\x :: MaxWidthPercent
x -> "minimum height = " String -> String -> String
forall a. [a] -> [a] -> [a]
++ MaxWidthPercent -> String
forall a. Show a => a -> String
show MaxWidthPercent
x String -> String -> String
forall a. [a] -> [a] -> [a]
++ "em, ") Maybe MaxWidthPercent
h)
  (Title -> PrintLaTeX Doc
spec Title
c) (Title -> PrintLaTeX Doc
spec Title
l)
lo (Cell _) _               = PrintLaTeX Doc
empty

-- | Converts layout objects into a document form.
print :: PrintingInformation -> [LayoutObj] -> D
print :: PrintingInformation -> [LayoutObj] -> PrintLaTeX Doc
print sm :: PrintingInformation
sm = (LayoutObj -> PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> [LayoutObj] -> PrintLaTeX Doc
forall (t :: * -> *) a b.
Foldable t =>
(a -> b -> b) -> b -> t a -> b
foldr (PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
($+$) (PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc)
-> (LayoutObj -> PrintLaTeX Doc)
-> LayoutObj
-> PrintLaTeX Doc
-> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (LayoutObj -> PrintingInformation -> PrintLaTeX Doc
`lo` PrintingInformation
sm)) PrintLaTeX Doc
empty

-- | Determine wether braces and brackets are opening or closing.
data OpenClose = Open | Close

-----------------------------------------------------------------
------------------ EXPRESSION PRINTING----------------------
-----------------------------------------------------------------
-- (Since this is all implicitly in Math, leave it as String for now)

-- | Escape all special TeX characters.
-- TODO: This function should be improved. It should escape all special
--       TeX symbols that would affect rendering. For example, `_`
--       turns the RHS of text into subscript, and `^` would turn it
--       into superscript. This will need to be much more comprehensive.
--       e.g., `%`, `&`, `#`, etc
escapeIdentSymbols :: String -> String
escapeIdentSymbols :: String -> String
escapeIdentSymbols ('_':ss :: String
ss) = '\\' Char -> String -> String
forall a. a -> [a] -> [a]
: '_' Char -> String -> String
forall a. a -> [a] -> [a]
: String -> String
escapeIdentSymbols String
ss
escapeIdentSymbols (s :: Char
s:ss :: String
ss) = Char
s Char -> String -> String
forall a. a -> [a] -> [a]
: String -> String
escapeIdentSymbols String
ss
escapeIdentSymbols [] = []

-- | Print an expression to a document.
pExpr :: Expr -> D
pExpr :: Expr -> PrintLaTeX Doc
pExpr (Dbl d :: Double
d)        = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc)
-> (String -> Doc) -> String -> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> Doc
text (String -> PrintLaTeX Doc) -> String -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Maybe Depth -> Double -> String -> String
forall a. RealFloat a => Maybe Depth -> a -> String -> String
showEFloat Maybe Depth
forall a. Maybe a
Nothing Double
d ""
pExpr (Int i :: Integer
i)        = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Integer -> Doc
integer Integer
i)
pExpr (Str s :: String
s)        = PrintLaTeX Doc -> PrintLaTeX Doc
toText (PrintLaTeX Doc -> PrintLaTeX Doc)
-> (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PrintLaTeX Doc -> PrintLaTeX Doc
quote (PrintLaTeX Doc -> PrintLaTeX Doc)
-> (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text String
s
pExpr (Div n :: Expr
n d :: Expr
d)      = String -> PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
command2D "frac" (Expr -> PrintLaTeX Doc
pExpr Expr
n) (Expr -> PrintLaTeX Doc
pExpr Expr
d)
pExpr (Case ps :: [(Expr, Expr)]
ps)      = String -> PrintLaTeX Doc -> PrintLaTeX Doc
mkEnv "cases" ([(Expr, Expr)] -> PrintLaTeX Doc
cases [(Expr, Expr)]
ps)
pExpr (Mtx a :: [[Expr]]
a)        = String -> PrintLaTeX Doc -> PrintLaTeX Doc
mkEnv "bmatrix" ([[Expr]] -> PrintLaTeX Doc
pMatrix [[Expr]]
a)
pExpr (Row [x :: Expr
x])      = PrintLaTeX Doc -> PrintLaTeX Doc
br (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Expr -> PrintLaTeX Doc
pExpr Expr
x -- FIXME: Hack needed for symbols with multiple subscripts, etc.
pExpr (Row l :: [Expr]
l)        = (PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc)
-> [PrintLaTeX Doc] -> PrintLaTeX Doc
forall (t :: * -> *) a. Foldable t => (a -> a -> a) -> t a -> a
foldl1 PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
(<>) ((Expr -> PrintLaTeX Doc) -> [Expr] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map Expr -> PrintLaTeX Doc
pExpr [Expr]
l)
pExpr (Ident s :: String
s@[_])  = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc)
-> (String -> Doc) -> String -> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> Doc
text (String -> Doc) -> (String -> String) -> String -> Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> String
escapeIdentSymbols (String -> PrintLaTeX Doc) -> String -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String
s
pExpr (Ident s :: String
s)      = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "mathit" (Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc)
-> (String -> Doc) -> String -> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> Doc
text (String -> Doc) -> (String -> String) -> String -> Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> String
escapeIdentSymbols (String -> PrintLaTeX Doc) -> String -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String
s)
pExpr (Label s :: String
s)      = String -> String -> PrintLaTeX Doc
command "text" String
s
pExpr (Spec s :: Special
s)       = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc)
-> (String -> Doc) -> String -> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> Doc
text (String -> PrintLaTeX Doc) -> String -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Latex -> String
unPL (Latex -> String) -> Latex -> String
forall a b. (a -> b) -> a -> b
$ Special -> Latex
forall r. RenderSpecial r => Special -> r
L.special Special
s
--pExpr (Gr g)         = unPL $ greek g
pExpr (Sub e :: Expr
e)        = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure Doc
unders PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> PrintLaTeX Doc -> PrintLaTeX Doc
br (Expr -> PrintLaTeX Doc
pExpr Expr
e)
pExpr (Sup e :: Expr
e)        = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure Doc
hat    PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> PrintLaTeX Doc -> PrintLaTeX Doc
br (Expr -> PrintLaTeX Doc
pExpr Expr
e)
pExpr (Over Hat s :: Expr
s)   = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "hat" (Expr -> PrintLaTeX Doc
pExpr Expr
s)
pExpr (MO o :: Ops
o)         = Ops -> PrintLaTeX Doc
pOps Ops
o
pExpr (Fenced l :: Fence
l r :: Fence
r m :: Expr
m) = OpenClose -> Fence -> PrintLaTeX Doc
fence OpenClose
Open Fence
l PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> Expr -> PrintLaTeX Doc
pExpr Expr
m PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> OpenClose -> Fence -> PrintLaTeX Doc
fence OpenClose
Close Fence
r
pExpr (Font Bold e :: Expr
e)  = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "symbf" (Expr -> PrintLaTeX Doc
pExpr Expr
e)
pExpr (Font Emph e :: Expr
e)  = Expr -> PrintLaTeX Doc
pExpr Expr
e -- Emph is ignored here because we're in Math mode
pExpr (Spc Thin)     = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc)
-> (String -> Doc) -> String -> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> Doc
text (String -> PrintLaTeX Doc) -> String -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ "\\,"
pExpr (Sqrt e :: Expr
e)       = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "sqrt" (Expr -> PrintLaTeX Doc
pExpr Expr
e)

-- | Prints operators.
pOps :: Ops -> D
pOps :: Ops -> PrintLaTeX Doc
pOps IsIn     = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "in" PrintLaTeX Doc
empty
pOps Integer  = String -> PrintLaTeX Doc
mathbb "Z"
pOps Rational = String -> PrintLaTeX Doc
mathbb "Q"
pOps Real     = String -> PrintLaTeX Doc
mathbb "R"
pOps Natural  = String -> PrintLaTeX Doc
mathbb "N"
pOps Boolean  = String -> PrintLaTeX Doc
mathbb "B"
pOps Comma    = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text ","
pOps Prime    = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text "'"
pOps Log      = String -> PrintLaTeX Doc
texSym "log"
pOps Ln       = String -> PrintLaTeX Doc
texSym "ln"
pOps Sin      = String -> PrintLaTeX Doc
texSym "sin"
pOps Cos      = String -> PrintLaTeX Doc
texSym "cos"
pOps Tan      = String -> PrintLaTeX Doc
texSym "tan"
pOps Sec      = String -> PrintLaTeX Doc
texSym "sec"
pOps Csc      = String -> PrintLaTeX Doc
texSym "csc"
pOps Cot      = String -> PrintLaTeX Doc
texSym "cot"
pOps Arcsin   = String -> PrintLaTeX Doc
texSym "arcsin"
pOps Arccos   = String -> PrintLaTeX Doc
texSym "arccos"
pOps Arctan   = String -> PrintLaTeX Doc
texSym "arctan"
pOps Not      = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "neg" PrintLaTeX Doc
empty
pOps Dim      = String -> String -> PrintLaTeX Doc
command "mathsf" "dim"
pOps Exp      = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text "e"
pOps Neg      = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure Doc
hyph
pOps Cross    = String -> PrintLaTeX Doc
texSym "times"
pOps Dot      = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "cdot" PrintLaTeX Doc
empty
pOps Eq       = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure Doc
assign
pOps NEq      = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "neq" PrintLaTeX Doc
empty
-- Old way of doing less than and greater than
-- pOps Lt       = pure lt
-- pOps Gt       = pure gt
pOps Lt       = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "lt" PrintLaTeX Doc
empty
pOps Gt       = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "gt" PrintLaTeX Doc
empty
pOps GEq      = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "geq" PrintLaTeX Doc
empty
pOps LEq      = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "leq" PrintLaTeX Doc
empty
pOps Impl     = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "implies" PrintLaTeX Doc
empty
pOps Iff      = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "iff" PrintLaTeX Doc
empty
pOps Subt     = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure Doc
hyph
pOps And      = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "land" PrintLaTeX Doc
empty
pOps Or       = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "lor" PrintLaTeX Doc
empty
pOps Add      = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure Doc
pls
pOps Mul      = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text " "
pOps Summ     = String -> PrintLaTeX Doc
command0 "displaystyle" PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> String -> PrintLaTeX Doc
command0 "sum"
pOps Prod     = String -> PrintLaTeX Doc
command0 "displaystyle" PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> String -> PrintLaTeX Doc
command0 "prod"
pOps Inte     = String -> PrintLaTeX Doc
texSym "int"
pOps Point    = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text "."
pOps Perc     = String -> PrintLaTeX Doc
texSym "%"
pOps LArrow   = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "leftarrow"  PrintLaTeX Doc
empty
pOps RArrow   = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "rightarrow" PrintLaTeX Doc
empty
pOps ForAll   = String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD "ForAll"     PrintLaTeX Doc
empty

-- | Prints fencing notation ("(),{},|,||").
fence :: OpenClose -> Fence -> D
fence :: OpenClose -> Fence -> PrintLaTeX Doc
fence Open Paren  = String -> PrintLaTeX Doc
texSym "left("
fence Close Paren = String -> PrintLaTeX Doc
texSym "right)"
fence Open Curly  = String -> PrintLaTeX Doc
texSym "{"
fence Close Curly = String -> PrintLaTeX Doc
texSym "}"
fence _ Abs       = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text "|"
fence _ Norm      = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text "\\|"

-- | For printing a Matrix.
pMatrix :: [[Expr]] -> D
pMatrix :: [[Expr]] -> PrintLaTeX Doc
pMatrix e :: [[Expr]]
e = Doc -> [PrintLaTeX Doc] -> PrintLaTeX Doc
vpunctuate Doc
dbs (([Expr] -> PrintLaTeX Doc) -> [[Expr]] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map [Expr] -> PrintLaTeX Doc
pIn [[Expr]]
e)
  where pIn :: [Expr] -> PrintLaTeX Doc
pIn x :: [Expr]
x = Doc -> [PrintLaTeX Doc] -> PrintLaTeX Doc
hpunctuate (String -> Doc
text " & ") ((Expr -> PrintLaTeX Doc) -> [Expr] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map Expr -> PrintLaTeX Doc
pExpr [Expr]
x)

-- | Helper for printing case expression.
cases :: [(Expr,Expr)] -> D
cases :: [(Expr, Expr)] -> PrintLaTeX Doc
cases [] = String -> PrintLaTeX Doc
forall a. HasCallStack => String -> a
error "Attempt to create case expression without cases"
cases e :: [(Expr, Expr)]
e  = Doc -> [PrintLaTeX Doc] -> PrintLaTeX Doc
vpunctuate Doc
dbs (((Expr, Expr) -> PrintLaTeX Doc)
-> [(Expr, Expr)] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map (Expr, Expr) -> PrintLaTeX Doc
_case [(Expr, Expr)]
e)
  where _case :: (Expr, Expr) -> PrintLaTeX Doc
_case (x :: Expr
x, y :: Expr
y) = Doc -> [PrintLaTeX Doc] -> PrintLaTeX Doc
hpunctuate (String -> Doc
text ", & ") ((Expr -> PrintLaTeX Doc) -> [Expr] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map Expr -> PrintLaTeX Doc
pExpr [Expr
x, Expr
y])

-----------------------------------------------------------------
------------------ TABLE PRINTING---------------------------
-----------------------------------------------------------------

-- | Prints a table. Takes in data for the table, a label,
-- a boolean that determines if the caption is shown, and a caption.
makeTable :: [[Spec]] -> D -> Bool -> D -> D
makeTable :: [[Title]]
-> PrintLaTeX Doc -> Bool -> PrintLaTeX Doc -> PrintLaTeX Doc
makeTable [] _ _ _ = String -> PrintLaTeX Doc
forall a. HasCallStack => String -> a
error "Completely empty table (not even header)"
makeTable [_] _ _ _ = PrintLaTeX Doc
empty -- table with no actual contents... don't error
makeTable lls :: [[Title]]
lls@(h :: [Title]
h:tlines :: [[Title]]
tlines) r :: PrintLaTeX Doc
r bool :: Bool
bool t :: PrintLaTeX Doc
t = String -> String -> PrintLaTeX Doc -> PrintLaTeX Doc
mkEnvArgBr String
ltab ([String] -> String
unwords ([String] -> String) -> [String] -> String
forall a b. (a -> b) -> a -> b
$ [[Title]] -> [String]
anyBig [[Title]]
lls) (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$
  String -> PrintLaTeX Doc
command0 "toprule"
  PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% [Title] -> PrintLaTeX Doc
makeHeaders [Title]
h
  PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% String -> PrintLaTeX Doc
command0 "midrule"
  PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% String -> PrintLaTeX Doc
command0 "endhead"
  PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% [[Title]] -> PrintLaTeX Doc
makeRows [[Title]]
tlines
  PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% String -> PrintLaTeX Doc
command0 "bottomrule"
  PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% (if Bool
bool then PrintLaTeX Doc -> PrintLaTeX Doc
caption PrintLaTeX Doc
t else PrintLaTeX Doc -> PrintLaTeX Doc
caption PrintLaTeX Doc
empty)
  PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% PrintLaTeX Doc -> PrintLaTeX Doc
label PrintLaTeX Doc
r
  where
    --Only needed if "X[l]" is used
    ltab :: String
ltab = if [[Title]] -> Bool
anyLong [[Title]]
lls then "longtabu" else "longtable"
    descr :: Bool -> String
descr True  = "X[l]"
    descr False = "l"
    --returns "X[l]" for columns with long fields
    anyLong :: [[Title]] -> Bool
anyLong = ([Title] -> Bool) -> [[Title]] -> Bool
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Bool
any [Title] -> Bool
longColumn ([[Title]] -> Bool)
-> ([[Title]] -> [[Title]]) -> [[Title]] -> Bool
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [[Title]] -> [[Title]]
forall a. [[a]] -> [[a]]
transpose
    anyBig :: [[Title]] -> [String]
anyBig = ([Title] -> String) -> [[Title]] -> [String]
forall a b. (a -> b) -> [a] -> [b]
map (Bool -> String
descr (Bool -> String) -> ([Title] -> Bool) -> [Title] -> String
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [Title] -> Bool
longColumn) ([[Title]] -> [String])
-> ([[Title]] -> [[Title]]) -> [[Title]] -> [String]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [[Title]] -> [[Title]]
forall a. [[a]] -> [[a]]
transpose
    longColumn :: [Title] -> Bool
longColumn = (Title -> Bool) -> [Title] -> Bool
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Bool
any (\x :: Title
x -> Title -> Depth
specLength Title
x Depth -> Depth -> Bool
forall a. Ord a => a -> a -> Bool
> 50)

-- | Determines the length of a 'Spec'.
specLength :: Spec -> Int
specLength :: Title -> Depth
specLength (E x :: Expr
x)       = String -> Depth
forall (t :: * -> *) a. Foldable t => t a -> Depth
length (String -> Depth) -> String -> Depth
forall a b. (a -> b) -> a -> b
$ (Char -> Bool) -> String -> String
forall a. (a -> Bool) -> [a] -> [a]
filter (Char -> String -> Bool
forall (t :: * -> *) a. (Foldable t, Eq a) => a -> t a -> Bool
`notElem` String
dontCount) (String -> String) -> String -> String
forall a b. (a -> b) -> a -> b
$ Doc -> String
TP.render (Doc -> String) -> Doc -> String
forall a b. (a -> b) -> a -> b
$ PrintLaTeX Doc -> MathContext -> Doc
forall a. PrintLaTeX a -> MathContext -> a
runPrint (Expr -> PrintLaTeX Doc
pExpr Expr
x) MathContext
Curr
specLength (S x :: String
x)       = String -> Depth
forall (t :: * -> *) a. Foldable t => t a -> Depth
length String
x
specLength (a :: Title
a :+: b :: Title
b)   = Title -> Depth
specLength Title
a Depth -> Depth -> Depth
forall a. Num a => a -> a -> a
+ Title -> Depth
specLength Title
b
specLength (Sp _)      = 1
specLength (Ref Internal r :: String
r _) = String -> Depth
forall (t :: * -> *) a. Foldable t => t a -> Depth
length String
r
specLength (Ref (Cite2 n :: Title
n)   r :: String
r i :: Title
i ) = String -> Depth
forall (t :: * -> *) a. Foldable t => t a -> Depth
length String
r Depth -> Depth -> Depth
forall a. Num a => a -> a -> a
+ Title -> Depth
specLength Title
i Depth -> Depth -> Depth
forall a. Num a => a -> a -> a
+ Title -> Depth
specLength Title
n --may need to change?
specLength (Ref External _ t :: Title
t) = Title -> Depth
specLength Title
t
specLength EmptyS      = 0
specLength (Quote q :: Title
q)   = 4 Depth -> Depth -> Depth
forall a. Num a => a -> a -> a
+ Title -> Depth
specLength Title
q
specLength HARDNL      = 0

-- | Invalid characters, not included in an expression.
dontCount :: String
dontCount :: String
dontCount = "\\/[]{}()_^$:"

-- | Creates the header for a table.
makeHeaders :: [Spec] -> D
makeHeaders :: [Title] -> PrintLaTeX Doc
makeHeaders ls :: [Title]
ls = Doc -> [PrintLaTeX Doc] -> PrintLaTeX Doc
hpunctuate (String -> Doc
text " & ") ((Title -> PrintLaTeX Doc) -> [Title] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map (PrintLaTeX Doc -> PrintLaTeX Doc
bold (PrintLaTeX Doc -> PrintLaTeX Doc)
-> (Title -> PrintLaTeX Doc) -> Title -> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Title -> PrintLaTeX Doc
spec) [Title]
ls) PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure Doc
dbs

-- | Creates the rows for a table.
makeRows :: [[Spec]] -> D
makeRows :: [[Title]] -> PrintLaTeX Doc
makeRows = [PrintLaTeX Doc] -> PrintLaTeX Doc
forall a. Monoid a => [a] -> a
mconcat ([PrintLaTeX Doc] -> PrintLaTeX Doc)
-> ([[Title]] -> [PrintLaTeX Doc]) -> [[Title]] -> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ([Title] -> PrintLaTeX Doc) -> [[Title]] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map (\c :: [Title]
c -> [Title] -> PrintLaTeX Doc
makeColumns [Title]
c PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure Doc
dbs)

-- | Creates the columns for a table.
makeColumns :: [Spec] -> D
makeColumns :: [Title] -> PrintLaTeX Doc
makeColumns ls :: [Title]
ls = Doc -> [PrintLaTeX Doc] -> PrintLaTeX Doc
hpunctuate (String -> Doc
text " & ") ([PrintLaTeX Doc] -> PrintLaTeX Doc)
-> [PrintLaTeX Doc] -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ (Title -> PrintLaTeX Doc) -> [Title] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map Title -> PrintLaTeX Doc
spec [Title]
ls

------------------ Spec -----------------------------------

-- | Helper that determines the printing context based on the kind of 'Spec'.
needs :: Spec -> MathContext
needs :: Title -> MathContext
needs (a :: Title
a :+: b :: Title
b) = Title -> MathContext
needs Title
a MathContext -> MathContext -> MathContext
`lub` Title -> MathContext
needs Title
b
needs (S _)     = MathContext
Text
needs (E _)     = MathContext
Math
needs (Sp _)    = MathContext
Math
needs HARDNL    = MathContext
Text
needs Ref{}     = MathContext
Text
needs EmptyS    = MathContext
Text
needs (Quote _) = MathContext
Text

-- | Prints all 'Spec's.
spec :: Spec -> D
spec :: Title -> PrintLaTeX Doc
spec a :: Title
a@(s :: Title
s :+: t :: Title
t) = PrintLaTeX Doc
s' PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> PrintLaTeX Doc
t'
  where
    ctx :: b -> MathContext
ctx = MathContext -> b -> MathContext
forall a b. a -> b -> a
const (MathContext -> b -> MathContext)
-> MathContext -> b -> MathContext
forall a b. (a -> b) -> a -> b
$ Title -> MathContext
needs Title
a
    s' :: PrintLaTeX Doc
s' = (MathContext -> MathContext) -> PrintLaTeX Doc -> PrintLaTeX Doc
switch MathContext -> MathContext
forall b. b -> MathContext
ctx (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Title -> PrintLaTeX Doc
spec Title
s
    t' :: PrintLaTeX Doc
t' = (MathContext -> MathContext) -> PrintLaTeX Doc -> PrintLaTeX Doc
switch MathContext -> MathContext
forall b. b -> MathContext
ctx (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Title -> PrintLaTeX Doc
spec Title
t
spec (E ex :: Expr
ex) = PrintLaTeX Doc -> PrintLaTeX Doc
toMath (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Expr -> PrintLaTeX Doc
pExpr Expr
ex
spec (S s :: String
s)  = (String -> PrintLaTeX Doc)
-> (String -> PrintLaTeX Doc)
-> Either String String
-> PrintLaTeX Doc
forall a c b. (a -> c) -> (b -> c) -> Either a b -> c
either String -> PrintLaTeX Doc
forall a. HasCallStack => String -> a
error (Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc)
-> (String -> Doc) -> String -> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> Doc
text (String -> Doc) -> (String -> String) -> String -> Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Char -> String) -> String -> String
forall (t :: * -> *) a b. Foldable t => (a -> [b]) -> t a -> [b]
concatMap Char -> String
escapeChars) (Either String String -> PrintLaTeX Doc)
-> Either String String -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> String -> Either String String
L.checkValidStr String
s String
invalid
  where
    invalid :: String
invalid = ['&', '#', '$', '%', '&', '~', '^', '\\', '{', '}']
    escapeChars :: Char -> String
escapeChars '_' = "\\_"
    escapeChars '&' = "\\&"
    escapeChars c :: Char
c = [Char
c]
spec (Sp s :: Special
s) = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text (String -> Doc) -> String -> Doc
forall a b. (a -> b) -> a -> b
$ Latex -> String
unPL (Latex -> String) -> Latex -> String
forall a b. (a -> b) -> a -> b
$ Special -> Latex
forall r. RenderSpecial r => Special -> r
L.special Special
s
spec HARDNL = String -> PrintLaTeX Doc
command0 "newline"
spec (Ref Internal r :: String
r sn :: Title
sn) = String -> PrintLaTeX Doc -> PrintLaTeX Doc
snref String
r (Title -> PrintLaTeX Doc
spec Title
sn)
spec (Ref (Cite2 n :: Title
n) r :: String
r _) = String -> Maybe (PrintLaTeX Doc) -> PrintLaTeX Doc
cite String
r (Title -> Maybe (PrintLaTeX Doc)
info Title
n)
  where
    info :: Title -> Maybe (PrintLaTeX Doc)
info EmptyS = Maybe (PrintLaTeX Doc)
forall a. Maybe a
Nothing
    info x :: Title
x      = PrintLaTeX Doc -> Maybe (PrintLaTeX Doc)
forall a. a -> Maybe a
Just (Title -> PrintLaTeX Doc
spec Title
x)
spec (Ref External r :: String
r sn :: Title
sn) = String -> PrintLaTeX Doc -> PrintLaTeX Doc
externalref String
r (Title -> PrintLaTeX Doc
spec Title
sn)
spec EmptyS              = PrintLaTeX Doc
empty
spec (Quote q :: Title
q)           = PrintLaTeX Doc -> PrintLaTeX Doc
quote (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Title -> PrintLaTeX Doc
spec Title
q

-- | Determines the needed context of a symbol.
symbolNeeds :: LD.Symbol -> MathContext
symbolNeeds :: Symbol -> MathContext
symbolNeeds (LD.Variable   _) = MathContext
Text
symbolNeeds (LD.Label      _) = MathContext
Text
symbolNeeds (LD.Integ      _) = MathContext
Math
symbolNeeds (LD.Special    _) = MathContext
Math
symbolNeeds (LD.Concat    []) = MathContext
Math
symbolNeeds (LD.Concat (s :: Symbol
s:_)) = Symbol -> MathContext
symbolNeeds Symbol
s
symbolNeeds LD.Corners{}      = MathContext
Math
symbolNeeds (LD.Atop     _ _) = MathContext
Math
symbolNeeds LD.Empty          = MathContext
Curr

-- | Prints units.
pUnit :: L.USymb -> D
pUnit :: USymb -> PrintLaTeX Doc
pUnit (L.US ls :: [(Symbol, Integer)]
ls) = [(Symbol, Integer)] -> [(Symbol, Integer)] -> PrintLaTeX Doc
formatu [(Symbol, Integer)]
t [(Symbol, Integer)]
b
  where
    (t :: [(Symbol, Integer)]
t,b :: [(Symbol, Integer)]
b) = ((Symbol, Integer) -> Bool)
-> [(Symbol, Integer)]
-> ([(Symbol, Integer)], [(Symbol, Integer)])
forall a. (a -> Bool) -> [a] -> ([a], [a])
partition ((Integer -> Integer -> Bool
forall a. Ord a => a -> a -> Bool
> 0) (Integer -> Bool)
-> ((Symbol, Integer) -> Integer) -> (Symbol, Integer) -> Bool
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Symbol, Integer) -> Integer
forall a b. (a, b) -> b
snd) [(Symbol, Integer)]
ls
    formatu :: [(L.Symbol,Integer)] -> [(L.Symbol,Integer)] -> D
    formatu :: [(Symbol, Integer)] -> [(Symbol, Integer)] -> PrintLaTeX Doc
formatu [] l :: [(Symbol, Integer)]
l = [(Symbol, Integer)] -> PrintLaTeX Doc
line [(Symbol, Integer)]
l
    formatu l :: [(Symbol, Integer)]
l [] = ((Symbol, Integer) -> PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> [(Symbol, Integer)] -> PrintLaTeX Doc
forall (t :: * -> *) a b.
Foldable t =>
(a -> b -> b) -> b -> t a -> b
foldr (PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
(<>) (PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc)
-> ((Symbol, Integer) -> PrintLaTeX Doc)
-> (Symbol, Integer)
-> PrintLaTeX Doc
-> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Symbol, Integer) -> PrintLaTeX Doc
pow) PrintLaTeX Doc
empty [(Symbol, Integer)]
l
    formatu nu :: [(Symbol, Integer)]
nu de :: [(Symbol, Integer)]
de = PrintLaTeX Doc -> PrintLaTeX Doc
toMath (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
fraction ([(Symbol, Integer)] -> PrintLaTeX Doc
line [(Symbol, Integer)]
nu) (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ [(Symbol, Integer)] -> PrintLaTeX Doc
line ([(Symbol, Integer)] -> PrintLaTeX Doc)
-> [(Symbol, Integer)] -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ ((Symbol, Integer) -> (Symbol, Integer))
-> [(Symbol, Integer)] -> [(Symbol, Integer)]
forall a b. (a -> b) -> [a] -> [b]
map ((Integer -> Integer) -> (Symbol, Integer) -> (Symbol, Integer)
forall (a :: * -> * -> *) b c d.
Arrow a =>
a b c -> a (d, b) (d, c)
second Integer -> Integer
forall a. Num a => a -> a
negate) [(Symbol, Integer)]
de
    line :: [(L.Symbol,Integer)] -> D
    line :: [(Symbol, Integer)] -> PrintLaTeX Doc
line []  = PrintLaTeX Doc
empty
    line [n :: (Symbol, Integer)
n] = (Symbol, Integer) -> PrintLaTeX Doc
pow (Symbol, Integer)
n
    line l :: [(Symbol, Integer)]
l   = PrintLaTeX Doc -> PrintLaTeX Doc
parens (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ ((Symbol, Integer) -> PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> [(Symbol, Integer)] -> PrintLaTeX Doc
forall (t :: * -> *) a b.
Foldable t =>
(a -> b -> b) -> b -> t a -> b
foldr (PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
(<>) (PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc)
-> ((Symbol, Integer) -> PrintLaTeX Doc)
-> (Symbol, Integer)
-> PrintLaTeX Doc
-> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Symbol, Integer) -> PrintLaTeX Doc
pow) PrintLaTeX Doc
empty [(Symbol, Integer)]
l
    pow :: (L.Symbol,Integer) -> D
    pow :: (Symbol, Integer) -> PrintLaTeX Doc
pow (n :: Symbol
n,1) = Symbol -> PrintLaTeX Doc
p_symb Symbol
n
    pow (n :: Symbol
n,p :: Integer
p) = PrintLaTeX Doc -> PrintLaTeX Doc
toMath (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
superscript (Symbol -> PrintLaTeX Doc
p_symb Symbol
n) (Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text (String -> Doc) -> String -> Doc
forall a b. (a -> b) -> a -> b
$ Integer -> String
forall a. Show a => a -> String
show Integer
p)
    -- printing of unit symbols is done weirdly... FIXME?
    p_symb :: Symbol -> PrintLaTeX Doc
p_symb (LD.Concat s :: [Symbol]
s) = (PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> [PrintLaTeX Doc] -> PrintLaTeX Doc
forall (t :: * -> *) b a.
Foldable t =>
(b -> a -> b) -> b -> t a -> b
foldl PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
(<>) PrintLaTeX Doc
empty ([PrintLaTeX Doc] -> PrintLaTeX Doc)
-> [PrintLaTeX Doc] -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ (Symbol -> PrintLaTeX Doc) -> [Symbol] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map Symbol -> PrintLaTeX Doc
p_symb [Symbol]
s
    p_symb n :: Symbol
n = let cn :: MathContext
cn = Symbol -> MathContext
symbolNeeds Symbol
n in (MathContext -> MathContext) -> PrintLaTeX Doc -> PrintLaTeX Doc
switch (MathContext -> MathContext -> MathContext
forall a b. a -> b -> a
const MathContext
cn) (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Expr -> PrintLaTeX Doc
pExpr (Expr -> PrintLaTeX Doc) -> Expr -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Symbol -> Expr
I.symbol Symbol
n

-----------------------------------------------------------------
------------------ DATA DEFINITION PRINTING-----------------
-----------------------------------------------------------------

-- | Prints a (data) definition.
makeDefn :: PrintingInformation -> [(String,[LayoutObj])] -> D -> D
makeDefn :: PrintingInformation
-> [(String, [LayoutObj])] -> PrintLaTeX Doc -> PrintLaTeX Doc
makeDefn _  [] _ = String -> PrintLaTeX Doc
forall a. HasCallStack => String -> a
error "Empty definition"
makeDefn sm :: PrintingInformation
sm ps :: [(String, [LayoutObj])]
ps l :: PrintLaTeX Doc
l = PrintLaTeX Doc -> PrintLaTeX Doc
mkMinipage (PrintingInformation
-> [(String, [LayoutObj])] -> PrintLaTeX Doc -> PrintLaTeX Doc
makeDefTable PrintingInformation
sm [(String, [LayoutObj])]
ps PrintLaTeX Doc
l)

-- | Helper that creates the definition and associated table.
makeDefTable :: PrintingInformation -> [(String,[LayoutObj])] -> D -> D
makeDefTable :: PrintingInformation
-> [(String, [LayoutObj])] -> PrintLaTeX Doc -> PrintLaTeX Doc
makeDefTable _ [] _ = String -> PrintLaTeX Doc
forall a. HasCallStack => String -> a
error "Trying to make empty Data Defn"
makeDefTable sm :: PrintingInformation
sm ps :: [(String, [LayoutObj])]
ps l :: PrintLaTeX Doc
l = String -> String -> PrintLaTeX Doc -> PrintLaTeX Doc
mkEnvArgBr "tabular" (String -> Double -> String
forall a. Show a => String -> a -> String
col String
rr Double
colAwidth String -> String -> String
forall a. [a] -> [a] -> [a]
++ String -> Double -> String
forall a. Show a => String -> a -> String
col (String
rr String -> String -> String
forall a. [a] -> [a] -> [a]
++ "\\arraybackslash") Double
colBwidth) (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ [PrintLaTeX Doc] -> PrintLaTeX Doc
vcat [
  String -> PrintLaTeX Doc
command0 "toprule " PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> PrintLaTeX Doc -> PrintLaTeX Doc
bold (Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text "Refname") PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text " & ") PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> PrintLaTeX Doc -> PrintLaTeX Doc
bold PrintLaTeX Doc
l, --shortname instead of refname?
  String -> PrintLaTeX Doc
command0 "phantomsection ", PrintLaTeX Doc -> PrintLaTeX Doc
label PrintLaTeX Doc
l,
  PrintingInformation -> [(String, [LayoutObj])] -> PrintLaTeX Doc
makeDRows PrintingInformation
sm [(String, [LayoutObj])]
ps,
  Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Doc
dbs Doc -> Doc -> Doc
<+> String -> Doc
text "\\bottomrule"
  ]
  where
    col :: String -> a -> String
col s :: String
s x :: a
x = ">" String -> String -> String
forall a. [a] -> [a] -> [a]
++ String -> String
brace String
s String -> String -> String
forall a. [a] -> [a] -> [a]
++ "p" String -> String -> String
forall a. [a] -> [a] -> [a]
++ String -> String
brace (a -> String
forall a. Show a => a -> String
show a
x String -> String -> String
forall a. [a] -> [a] -> [a]
++ String
tw)
    rr :: String
rr = "\\raggedright"
    tw :: String
tw = "\\textwidth"

-- | Helper that makes the rows of a definition table.
makeDRows :: PrintingInformation -> [(String,[LayoutObj])] -> D
makeDRows :: PrintingInformation -> [(String, [LayoutObj])] -> PrintLaTeX Doc
makeDRows _  []         = String -> PrintLaTeX Doc
forall a. HasCallStack => String -> a
error "No fields to create Defn table"
makeDRows sm :: PrintingInformation
sm ls :: [(String, [LayoutObj])]
ls    = (PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc)
-> [PrintLaTeX Doc] -> PrintLaTeX Doc
forall (t :: * -> *) a. Foldable t => (a -> a -> a) -> t a -> a
foldl1 PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
(%%) ([PrintLaTeX Doc] -> PrintLaTeX Doc)
-> [PrintLaTeX Doc] -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ ((String, [LayoutObj]) -> PrintLaTeX Doc)
-> [(String, [LayoutObj])] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map (\(f :: String
f, d :: [LayoutObj]
d) -> PrintLaTeX Doc
dBoilerplate PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%%  Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text (String
f String -> String -> String
forall a. [a] -> [a] -> [a]
++ " & ")) PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> PrintingInformation -> [LayoutObj] -> PrintLaTeX Doc
print PrintingInformation
sm [LayoutObj]
d) [(String, [LayoutObj])]
ls
  where dBoilerplate :: PrintLaTeX Doc
dBoilerplate = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Doc
dbs Doc -> Doc -> Doc
<+> String -> Doc
text "\\midrule" Doc -> Doc -> Doc
<+> Doc
dbs

-----------------------------------------------------------------
------------------ EQUATION PRINTING------------------------
-----------------------------------------------------------------

-- | Prints an equation.
makeEquation :: Spec -> D
makeEquation :: Title -> PrintLaTeX Doc
makeEquation contents :: Title
contents = PrintLaTeX Doc -> PrintLaTeX Doc
toEqn (Title -> PrintLaTeX Doc
spec Title
contents)

  --TODO: Add auto-generated labels -> Need to be able to ensure labeling based
  --  on chunk (i.e. "eq:h_g" for h_g = ...

-----------------------------------------------------------------
------------------ LIST PRINTING----------------------------
-----------------------------------------------------------------

-- latex doesn't like empty lists, so don't put anything out for them.
-- empty lists here isn't quite wrong (though there should probably be
-- a warning higher up), so don't generate bad latex.
-- | Prints a list. LaTeX doesn't like empty lists, so those are rendered as 'empty'.
makeList :: ListType -> D
makeList :: ListType -> PrintLaTeX Doc
makeList (Simple []   )      = PrintLaTeX Doc
empty
makeList (Desc []   )        = PrintLaTeX Doc
empty
makeList (Unordered []   )   = PrintLaTeX Doc
empty
makeList (Ordered []   )     = PrintLaTeX Doc
empty
makeList (Definitions []   ) = PrintLaTeX Doc
empty
makeList (Simple items :: [(Title, ItemType, Maybe Title)]
items)      = PrintLaTeX Doc -> PrintLaTeX Doc
itemize     (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ [PrintLaTeX Doc] -> PrintLaTeX Doc
vcat ([PrintLaTeX Doc] -> PrintLaTeX Doc)
-> [PrintLaTeX Doc] -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ [(Title, ItemType, Maybe Title)] -> [PrintLaTeX Doc]
simItem [(Title, ItemType, Maybe Title)]
items
makeList (Desc items :: [(Title, ItemType, Maybe Title)]
items)        = PrintLaTeX Doc -> PrintLaTeX Doc
description (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ [PrintLaTeX Doc] -> PrintLaTeX Doc
vcat ([PrintLaTeX Doc] -> PrintLaTeX Doc)
-> [PrintLaTeX Doc] -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ [(Title, ItemType, Maybe Title)] -> [PrintLaTeX Doc]
simItem [(Title, ItemType, Maybe Title)]
items
makeList (Unordered items :: [(ItemType, Maybe Title)]
items)   = PrintLaTeX Doc -> PrintLaTeX Doc
itemize     (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ [PrintLaTeX Doc] -> PrintLaTeX Doc
vcat ([PrintLaTeX Doc] -> PrintLaTeX Doc)
-> [PrintLaTeX Doc] -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ ((ItemType, Maybe Title) -> PrintLaTeX Doc)
-> [(ItemType, Maybe Title)] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map (ItemType, Maybe Title) -> PrintLaTeX Doc
plItem [(ItemType, Maybe Title)]
items
makeList (Ordered items :: [(ItemType, Maybe Title)]
items)     = PrintLaTeX Doc -> PrintLaTeX Doc
enumerate   (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ [PrintLaTeX Doc] -> PrintLaTeX Doc
vcat ([PrintLaTeX Doc] -> PrintLaTeX Doc)
-> [PrintLaTeX Doc] -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ ((ItemType, Maybe Title) -> PrintLaTeX Doc)
-> [(ItemType, Maybe Title)] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map (ItemType, Maybe Title) -> PrintLaTeX Doc
plItem [(ItemType, Maybe Title)]
items
makeList (Definitions items :: [(Title, ItemType, Maybe Title)]
items) = PrintLaTeX Doc -> PrintLaTeX Doc
symbDescription (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ [PrintLaTeX Doc] -> PrintLaTeX Doc
vcat ([PrintLaTeX Doc] -> PrintLaTeX Doc)
-> [PrintLaTeX Doc] -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ [(Title, ItemType, Maybe Title)] -> [PrintLaTeX Doc]
defItem [(Title, ItemType, Maybe Title)]
items

-- | Helper that renders items in 'makeList'.
plItem :: (ItemType,Maybe Label) -> D
plItem :: (ItemType, Maybe Title) -> PrintLaTeX Doc
plItem (i :: ItemType
i, l :: Maybe Title
l) = Maybe Title -> PrintLaTeX Doc
mlref Maybe Title
l PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> ItemType -> PrintLaTeX Doc
pItem ItemType
i

-- | Helper that renders the 'Spec' part of labels in 'mlref'.
lspec :: Spec -> D  -- FIXME: Should be option rolled in to spec
lspec :: Title -> PrintLaTeX Doc
lspec (S s :: String
s) = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text String
s
lspec r :: Title
r = Title -> PrintLaTeX Doc
spec Title
r

-- | Helper that renders labels in 'plItem'. 
mlref :: Maybe Label -> D
mlref :: Maybe Title -> PrintLaTeX Doc
mlref = PrintLaTeX Doc
-> (Title -> PrintLaTeX Doc) -> Maybe Title -> PrintLaTeX Doc
forall b a. b -> (a -> b) -> Maybe a -> b
maybe PrintLaTeX Doc
empty ((Title -> PrintLaTeX Doc) -> Maybe Title -> PrintLaTeX Doc)
-> (Title -> PrintLaTeX Doc) -> Maybe Title -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
(<>) (String -> PrintLaTeX Doc
command0 "phantomsection") (PrintLaTeX Doc -> PrintLaTeX Doc)
-> (Title -> PrintLaTeX Doc) -> Title -> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PrintLaTeX Doc -> PrintLaTeX Doc
label (PrintLaTeX Doc -> PrintLaTeX Doc)
-> (Title -> PrintLaTeX Doc) -> Title -> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Title -> PrintLaTeX Doc
lspec

-- | Helper that renders items in 'plItem'.
pItem :: ItemType -> D
pItem :: ItemType -> PrintLaTeX Doc
pItem (Flat s :: Title
s) = PrintLaTeX Doc -> PrintLaTeX Doc
item (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Title -> PrintLaTeX Doc
spec Title
s
pItem (Nested t :: Title
t s :: ListType
s) = [PrintLaTeX Doc] -> PrintLaTeX Doc
vcat [PrintLaTeX Doc -> PrintLaTeX Doc
item (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Title -> PrintLaTeX Doc
spec Title
t, ListType -> PrintLaTeX Doc
makeList ListType
s]

-- | Helper that renders simple and descriptive items in 'makeList'.
simItem :: [(Spec,ItemType,Maybe Label)] -> [D]
simItem :: [(Title, ItemType, Maybe Title)] -> [PrintLaTeX Doc]
simItem = ((Title, ItemType, Maybe Title) -> PrintLaTeX Doc)
-> [(Title, ItemType, Maybe Title)] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map (\(x :: Title
x,y :: ItemType
y,l :: Maybe Title
l) -> PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
item' (Title -> PrintLaTeX Doc
spec (Title
x Title -> Title -> Title
:+: String -> Title
S ":") PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> Maybe Title -> PrintLaTeX Doc
mlref Maybe Title
l) (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ ItemType -> PrintLaTeX Doc
sp_item ItemType
y)
  where sp_item :: ItemType -> PrintLaTeX Doc
sp_item (Flat s :: Title
s) = Title -> PrintLaTeX Doc
spec Title
s
        sp_item (Nested t :: Title
t s :: ListType
s) = [PrintLaTeX Doc] -> PrintLaTeX Doc
vcat [Title -> PrintLaTeX Doc
spec Title
t, ListType -> PrintLaTeX Doc
makeList ListType
s]

-- | Helper that renders definitions in 'makeList'.
defItem :: [(Spec, ItemType,Maybe Label)] -> [D]
defItem :: [(Title, ItemType, Maybe Title)] -> [PrintLaTeX Doc]
defItem = ((Title, ItemType, Maybe Title) -> PrintLaTeX Doc)
-> [(Title, ItemType, Maybe Title)] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map (\(x :: Title
x,y :: ItemType
y,l :: Maybe Title
l) -> PrintLaTeX Doc -> PrintLaTeX Doc
item (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Maybe Title -> PrintLaTeX Doc
mlref Maybe Title
l PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> Title -> PrintLaTeX Doc
spec (Title
x Title -> Title -> Title
:+: String -> Title
S " is the " Title -> Title -> Title
:+: ItemType -> Title
d_item ItemType
y))
  where d_item :: ItemType -> Title
d_item (Flat s :: Title
s) = Title
s
        d_item (Nested _ _) = String -> Title
forall a. HasCallStack => String -> a
error "Cannot use sublists in definitions"
-----------------------------------------------------------------
------------------ FIGURE PRINTING--------------------------
-----------------------------------------------------------------

-- | Prints figures. Takes in a label and caption along with information for 'includegraphics'.
makeFigure :: D -> D -> String -> L.MaxWidthPercent -> D
makeFigure :: PrintLaTeX Doc
-> PrintLaTeX Doc -> String -> MaxWidthPercent -> PrintLaTeX Doc
makeFigure r :: PrintLaTeX Doc
r c :: PrintLaTeX Doc
c f :: String
f wp :: MaxWidthPercent
wp =
  PrintLaTeX Doc -> PrintLaTeX Doc
figure (PrintLaTeX Doc -> PrintLaTeX Doc
center (
  [PrintLaTeX Doc] -> PrintLaTeX Doc
vcat [
    MaxWidthPercent -> String -> PrintLaTeX Doc
includegraphics MaxWidthPercent
wp String
f,
    PrintLaTeX Doc -> PrintLaTeX Doc
caption PrintLaTeX Doc
c,
    PrintLaTeX Doc -> PrintLaTeX Doc
label PrintLaTeX Doc
r
  ] ) )

-----------------------------------------------------------------
------------------ MODULE PRINTING----------------------------
-----------------------------------------------------------------

-- | Prints graphs.
makeGraph :: [(D,D)] -> D -> D -> D -> D -> D
makeGraph :: [(PrintLaTeX Doc, PrintLaTeX Doc)]
-> PrintLaTeX Doc
-> PrintLaTeX Doc
-> PrintLaTeX Doc
-> PrintLaTeX Doc
-> PrintLaTeX Doc
makeGraph ps :: [(PrintLaTeX Doc, PrintLaTeX Doc)]
ps w :: PrintLaTeX Doc
w h :: PrintLaTeX Doc
h c :: PrintLaTeX Doc
c l :: PrintLaTeX Doc
l =
  String -> PrintLaTeX Doc -> PrintLaTeX Doc
mkEnv "figure" (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ PrintLaTeX Doc
centering PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%%
  String -> String -> PrintLaTeX Doc -> PrintLaTeX Doc
mkEnvArgBr "adjustbox" "max width=\\textwidth" (
  String -> String -> PrintLaTeX Doc -> PrintLaTeX Doc
mkEnvArgSq "tikzpicture" ">=latex,line join=bevel" (
  [PrintLaTeX Doc] -> PrintLaTeX Doc
vcat [String -> String -> PrintLaTeX Doc
command "tikzstyle" "n" PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text " = ") PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> PrintLaTeX Doc -> PrintLaTeX Doc
sq (
          Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text "draw, shape=rectangle, ") PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> PrintLaTeX Doc
w PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> PrintLaTeX Doc
h PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<>
          Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text "font=\\Large, align=center]")),
        String -> String -> PrintLaTeX Doc -> PrintLaTeX Doc
mkEnvArgSq "dot2tex" "dot, codeonly, options=-t raw" (
        Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text "digraph G ") PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> PrintLaTeX Doc -> PrintLaTeX Doc
br ( [PrintLaTeX Doc] -> PrintLaTeX Doc
vcat (
         Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text "graph [sep = 0. esep = 0, nodesep = 0.1, ranksep = 2];") PrintLaTeX Doc -> [PrintLaTeX Doc] -> [PrintLaTeX Doc]
forall a. a -> [a] -> [a]
:
         Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text "node [style = \"n\"];") PrintLaTeX Doc -> [PrintLaTeX Doc] -> [PrintLaTeX Doc]
forall a. a -> [a] -> [a]
:
         ((PrintLaTeX Doc, PrintLaTeX Doc) -> PrintLaTeX Doc)
-> [(PrintLaTeX Doc, PrintLaTeX Doc)] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map (\(a :: PrintLaTeX Doc
a,b :: PrintLaTeX Doc
b) -> PrintLaTeX Doc -> PrintLaTeX Doc
forall (f :: * -> *).
(Semigroup (f Doc), Applicative f) =>
f Doc -> f Doc
q PrintLaTeX Doc
a PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text " -> ") PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> PrintLaTeX Doc -> PrintLaTeX Doc
forall (f :: * -> *).
(Semigroup (f Doc), Applicative f) =>
f Doc -> f Doc
q PrintLaTeX Doc
b PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text ";")) [(PrintLaTeX Doc, PrintLaTeX Doc)]
ps)
        ))
       ])) PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% PrintLaTeX Doc -> PrintLaTeX Doc
caption PrintLaTeX Doc
c PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% PrintLaTeX Doc -> PrintLaTeX Doc
label PrintLaTeX Doc
l
  where q :: f Doc -> f Doc
q x :: f Doc
x = Doc -> f Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text "\"") f Doc -> f Doc -> f Doc
forall a. Semigroup a => a -> a -> a
<> f Doc
x f Doc -> f Doc -> f Doc
forall a. Semigroup a => a -> a -> a
<> Doc -> f Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text "\"")

---------------------------
-- Bibliography Printing --
---------------------------
-- **THE MAIN FUNCTION** --
-- | Prints a bibliography.
makeBib :: PrintingInformation -> BibRef -> D
makeBib :: PrintingInformation -> BibRef -> PrintLaTeX Doc
makeBib sm :: PrintingInformation
sm bib :: BibRef
bib = String -> String -> PrintLaTeX Doc -> PrintLaTeX Doc
mkEnvArgBr "filecontents*" (String
bibFname String -> String -> String
forall a. [a] -> [a] -> [a]
++ ".bib") (PrintingInformation -> BibRef -> PrintLaTeX Doc
mkBibRef PrintingInformation
sm BibRef
bib) PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%%
  String -> String -> PrintLaTeX Doc
command "nocite" "*" PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%% String -> String -> PrintLaTeX Doc
command "bibstyle" String
bibStyleT PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
%%
  String -> PrintLaTeX Doc
command0 "printbibliography" PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> PrintLaTeX Doc -> PrintLaTeX Doc
sq (Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (Doc -> PrintLaTeX Doc) -> Doc -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ String -> Doc
text "heading=none")

-- | Renders a bibliographical reference.
mkBibRef :: PrintingInformation -> BibRef -> D
mkBibRef :: PrintingInformation -> BibRef -> PrintLaTeX Doc
mkBibRef sm :: PrintingInformation
sm = [PrintLaTeX Doc] -> PrintLaTeX Doc
forall a. Monoid a => [a] -> a
mconcat ([PrintLaTeX Doc] -> PrintLaTeX Doc)
-> (BibRef -> [PrintLaTeX Doc]) -> BibRef -> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Citation -> PrintLaTeX Doc) -> BibRef -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map (PrintingInformation -> Citation -> PrintLaTeX Doc
renderF PrintingInformation
sm)

-- | Helper that renders a citation.
renderF :: PrintingInformation -> Citation -> D
renderF :: PrintingInformation -> Citation -> PrintLaTeX Doc
renderF sm :: PrintingInformation
sm (Cite cid :: String
cid refType :: CitationKind
refType fields :: [CiteField]
fields) = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text (CitationKind -> String
showT CitationKind
refType)) PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<>
  PrintLaTeX Doc -> PrintLaTeX Doc
br (Doc -> [PrintLaTeX Doc] -> PrintLaTeX Doc
hpunctuate (String -> Doc
text ",\n") ([PrintLaTeX Doc] -> PrintLaTeX Doc)
-> [PrintLaTeX Doc] -> PrintLaTeX Doc
forall a b. (a -> b) -> a -> b
$ Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text String
cid) PrintLaTeX Doc -> [PrintLaTeX Doc] -> [PrintLaTeX Doc]
forall a. a -> [a] -> [a]
: (CiteField -> PrintLaTeX Doc) -> [CiteField] -> [PrintLaTeX Doc]
forall a b. (a -> b) -> [a] -> [b]
map (PrintingInformation -> CiteField -> PrintLaTeX Doc
showBibTeX PrintingInformation
sm) [CiteField]
fields)

-- | Renders different kinds of citation mediums.
showT :: L.CitationKind -> String
showT :: CitationKind -> String
showT L.Article       = "@article"
showT L.Book          = "@book"
showT L.Booklet       = "@booklet"
showT L.InBook        = "@inbook"
showT L.InCollection  = "@incollection"
showT L.InProceedings = "@inproceedings"
showT L.Manual        = "@manual"
showT L.MThesis       = "@mastersthesis"
showT L.Misc          = "@misc"
showT L.PhDThesis     = "@phdthesis"
showT L.Proceedings   = "@proceedings"
showT L.TechReport    = "@techreport"
showT L.Unpublished   = "@unpublished"

-- | Renders different citation fields.
showBibTeX :: PrintingInformation -> CiteField -> D
showBibTeX :: PrintingInformation -> CiteField -> PrintLaTeX Doc
showBibTeX  _ (Address      s :: Title
s) = String -> Title -> PrintLaTeX Doc
showField "address" Title
s
showBibTeX sm :: PrintingInformation
sm (Author       p :: People
p) = String -> Title -> PrintLaTeX Doc
showField "author" (PrintingInformation -> People -> Title
rendPeople PrintingInformation
sm People
p)
showBibTeX  _ (BookTitle    b :: Title
b) = String -> Title -> PrintLaTeX Doc
showField "booktitle" Title
b
showBibTeX  _ (Chapter      c :: Depth
c) = String -> Title -> PrintLaTeX Doc
showField "chapter" (Depth -> Title
forall a. Show a => a -> Title
wrapS Depth
c)
showBibTeX  _ (Edition      e :: Depth
e) = String -> Title -> PrintLaTeX Doc
showField "edition" (Depth -> Title
forall a. Show a => a -> Title
wrapS Depth
e)
showBibTeX sm :: PrintingInformation
sm (Editor       e :: People
e) = String -> Title -> PrintLaTeX Doc
showField "editor" (PrintingInformation -> People -> Title
rendPeople PrintingInformation
sm People
e)
showBibTeX  _ (Institution  i :: Title
i) = String -> Title -> PrintLaTeX Doc
showField "institution" Title
i
showBibTeX  _ (Journal      j :: Title
j) = String -> Title -> PrintLaTeX Doc
showField "journal" Title
j
showBibTeX  _ (Month        m :: Month
m) = String -> Title -> PrintLaTeX Doc
showFieldRaw "month" (Month -> Title
bibTeXMonth Month
m)
showBibTeX  _ (Note         n :: Title
n) = String -> Title -> PrintLaTeX Doc
showField "note" Title
n
showBibTeX  _ (Number       n :: Depth
n) = String -> Title -> PrintLaTeX Doc
showField "number" (Depth -> Title
forall a. Show a => a -> Title
wrapS Depth
n)
showBibTeX  _ (Organization o :: Title
o) = String -> Title -> PrintLaTeX Doc
showField "organization" Title
o
showBibTeX sm :: PrintingInformation
sm (Pages        p :: [Depth]
p) = String -> Title -> PrintLaTeX Doc
showField "pages" (PrintingInformation -> Sentence -> Title
I.spec PrintingInformation
sm (Sentence -> Title) -> Sentence -> Title
forall a b. (a -> b) -> a -> b
$ String -> [Depth] -> Sentence
L.foldNums "--" [Depth]
p)
showBibTeX  _ (Publisher    p :: Title
p) = String -> Title -> PrintLaTeX Doc
showField "publisher" Title
p
showBibTeX  _ (School       s :: Title
s) = String -> Title -> PrintLaTeX Doc
showField "school" Title
s
showBibTeX  _ (Series       s :: Title
s) = String -> Title -> PrintLaTeX Doc
showField "series" Title
s
showBibTeX  _ (Title        t :: Title
t) = String -> Title -> PrintLaTeX Doc
showField "title" Title
t
showBibTeX  _ (Type         t :: Title
t) = String -> Title -> PrintLaTeX Doc
showField "type" Title
t
showBibTeX  _ (Volume       v :: Depth
v) = String -> Title -> PrintLaTeX Doc
showField "volume" (Depth -> Title
forall a. Show a => a -> Title
wrapS Depth
v)
showBibTeX  _ (Year         y :: Depth
y) = String -> Title -> PrintLaTeX Doc
showField "year" (Depth -> Title
forall a. Show a => a -> Title
wrapS Depth
y)
showBibTeX  _ (HowPublished (URL  u :: Title
u)) = String -> String -> Title -> PrintLaTeX Doc
showFieldCom "url" "howpublished" Title
u
showBibTeX  _ (HowPublished (Verb v :: Title
v)) = String -> Title -> PrintLaTeX Doc
showField "howpublished" Title
v

--showBibTeX sm (Author p@(Person {_convention=Mono}:_)) = showField "author"
  -- (LS.spec sm (rendPeople p)) :+: S ",\n" :+:
  -- showField "sortkey" (LS.spec sm (rendPeople p))
-- showBibTeX sm (Author    p) = showField "author" $ LS.spec sm (rendPeople p)

-- | Citation fields may be wrapped with braces, nothing, or a command.
data FieldWrap = Braces | NoDelimiters | Command String

-- | Helper that renders citation fields with a wrapper.
wrapField :: FieldWrap -> String -> Spec -> D
wrapField :: FieldWrap -> String -> Title -> PrintLaTeX Doc
wrapField fw :: FieldWrap
fw f :: String
f s :: Title
s = Doc -> PrintLaTeX Doc
forall (f :: * -> *) a. Applicative f => a -> f a
pure (String -> Doc
text (String
f String -> String -> String
forall a. [a] -> [a] -> [a]
++ "=")) PrintLaTeX Doc -> PrintLaTeX Doc -> PrintLaTeX Doc
forall a. Semigroup a => a -> a -> a
<> FieldWrap -> PrintLaTeX Doc -> PrintLaTeX Doc
resolve FieldWrap
fw (Title -> PrintLaTeX Doc
spec Title
s)
  where
    resolve :: FieldWrap -> PrintLaTeX Doc -> PrintLaTeX Doc
resolve Braces       = PrintLaTeX Doc -> PrintLaTeX Doc
br
    resolve NoDelimiters = PrintLaTeX Doc -> PrintLaTeX Doc
forall a. a -> a
id
    resolve (Command st :: String
st) = PrintLaTeX Doc -> PrintLaTeX Doc
br (PrintLaTeX Doc -> PrintLaTeX Doc)
-> (PrintLaTeX Doc -> PrintLaTeX Doc)
-> PrintLaTeX Doc
-> PrintLaTeX Doc
forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> PrintLaTeX Doc -> PrintLaTeX Doc
commandD String
st

showField, showFieldRaw :: String -> Spec -> D
-- | Helper that renders citation fields wrapped with braces.
showField :: String -> Title -> PrintLaTeX Doc
showField    = FieldWrap -> String -> Title -> PrintLaTeX Doc
wrapField FieldWrap
Braces
-- | Helper that renders citation fields with no delimiters.
showFieldRaw :: String -> Title -> PrintLaTeX Doc
showFieldRaw = FieldWrap -> String -> Title -> PrintLaTeX Doc
wrapField FieldWrap
NoDelimiters

-- | Helper that renders citation fields with a command.
showFieldCom   :: String -> String -> Spec -> D
showFieldCom :: String -> String -> Title -> PrintLaTeX Doc
showFieldCom s :: String
s = FieldWrap -> String -> Title -> PrintLaTeX Doc
wrapField (String -> FieldWrap
Command String
s)

-- | Helper that renders people for citations.
rendPeople :: PrintingInformation -> L.People -> Spec
rendPeople :: PrintingInformation -> People -> Title
rendPeople _ []  = String -> Title
S "N.a." -- "No authors given"
rendPeople sm :: PrintingInformation
sm people :: People
people = PrintingInformation -> Sentence -> Title
I.spec PrintingInformation
sm (Sentence -> Title) -> Sentence -> Title
forall a b. (a -> b) -> a -> b
$
  (Sentence -> Sentence -> Sentence) -> [Sentence] -> Sentence
forall (t :: * -> *) a. Foldable t => (a -> a -> a) -> t a -> a
foldl1 (\x :: Sentence
x y :: Sentence
y -> Sentence
x Sentence -> Sentence -> Sentence
L.+:+ String -> Sentence
L.S "and" Sentence -> Sentence -> Sentence
L.+:+ Sentence
y) ([Sentence] -> Sentence) -> [Sentence] -> Sentence
forall a b. (a -> b) -> a -> b
$ (Person -> Sentence) -> People -> [Sentence]
forall a b. (a -> b) -> [a] -> [b]
map (String -> Sentence
L.S (String -> Sentence) -> (Person -> String) -> Person -> Sentence
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Person -> String
L.rendPersLFM) People
people

-- | Helper that renders months for citations.
bibTeXMonth :: L.Month -> Spec
bibTeXMonth :: Month -> Title
bibTeXMonth L.Jan = String -> Title
S "jan"
bibTeXMonth L.Feb = String -> Title
S "feb"
bibTeXMonth L.Mar = String -> Title
S "mar"
bibTeXMonth L.Apr = String -> Title
S "apr"
bibTeXMonth L.May = String -> Title
S "may"
bibTeXMonth L.Jun = String -> Title
S "jun"
bibTeXMonth L.Jul = String -> Title
S "jul"
bibTeXMonth L.Aug = String -> Title
S "aug"
bibTeXMonth L.Sep = String -> Title
S "sep"
bibTeXMonth L.Oct = String -> Title
S "oct"
bibTeXMonth L.Nov = String -> Title
S "nov"
bibTeXMonth L.Dec = String -> Title
S "dec"

-- | Helper that lifts something showable into a 'Spec'.
wrapS :: Show a => a -> Spec
wrapS :: a -> Title
wrapS = String -> Title
S (String -> Title) -> (a -> String) -> a -> Title
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> String
forall a. Show a => a -> String
show