# Poetry Scansion with LaTeX - Text Alignment

I'm looking for a good solution to print poetry with a separate line for accents, stresses and such (scansion). Normally this is done by taking a monospaced font like \texttt and then just add the accents where you need them in the upper line. But that includes loads of spaces to align things, which is neither easy to do in LaTeX nor elegant. Any ideas how this could be done in a better way?

Examples how it should look like can be found here: https://en.wikipedia.org/wiki/Scansion#Elements

\texttt{~~/~~~x~~~x~~/~~x~~~~x~~~~/~[x]/~x~~~~~/}\\
\texttt{When to the sessions of sweet silent thought}


What I need is to be able to align scansion symbols which are normally either letters or slashes and underscores to align to an exact position within a syllable (first vowel) of the text in the following line. I hope that makes sense. Traditionally this is solved as described above by using monospaced font and just adding as many spaces as needed inbetween the symbols.

• Please make your question self-contained: external links may vanish in a year or two rendering your question meaningless. It would also be extremely helpful if you succinctly described exactly what features you want rather than relying on a long wikipedia post. In addition, please give a minimal working example to show what you have tried and gives some example "poetry" for people to work with. Giving people compilable code to start from makes it much easier for people to help you and hence much more likely that some one will. – Andrew Nov 9 '17 at 9:51
• I typed out one of the examples given, but as said this is certainly no good way to do it and very unsuitable to LaTeX. So I don't know how much use that example will be except to show how not to do it but since I have no idea how to do it in a better way I can only provide this.. I hope it is clearer like this. – Cinna Nov 9 '17 at 10:11

You can use commands for stressed and unstressed vowels.

\documentclass{article}

\newcommand{\sni}[1]{\scansion{\smallertimes}{#1}}
\newcommand{\sbi}[1]{\scansion{\smallerbrackettimes}{#1}}
\newcommand{\si}[1]{\scansion{\smallerslash}{#1}}

\newcommand{\scansion}[2]{%
\begingroup
\renewcommand{\arraystretch}{0}%
\begin{tabular}[b]{@{}c@{}}
\makebox[0pt]{#1}\\[0.5ex]
\vphantom{T}#2
\end{tabular}%
\endgroup
}
\newcommand{\smallertimes}{$\scriptstyle\times\mathstrut$}
\newcommand{\smallerbrackettimes}{$\scriptstyle[{\times}]$}
\newcommand{\smallerslash}{$\scriptstyle/$}

\begin{document}

\noindent
\texttt{~~/~~~x~~~x~~/~~x~~~~x~~~~/~[x]/~x~~~~~/}\\
\texttt{When to the sessions of sweet silent thought}

\bigskip

\noindent
Wh\si{e}n t\sni{o} th\sni{e} s\si{e}ss\sni{i}ons
\sni{o}f sw\si{e}et\sbi{ }s\si{i}l\sni{e}nt th\si{o}ught

\end{document}


This could be done with my package metrix.

For example

\metrics{_    u  u  _   _  _  | _    _  u  u   _  _   _   }
{flos ve-te-ris vi-ni | meis na-ri-bus ob-iec-tust}


gives

As you see it uses letters for the input but symbols for the output as I believe the use of letters to denote accent symbol is just a workaround from users how don’t know how to add special symbols.

Pleas take a look at the manual for more examples and information.

• With v1.4 of metric it is now possible to use p (primary) and s (secondary) as symbols to add stresses. – Tobi May 5 '19 at 11:14

This is based on some code I used in the distant past for choral rehearsals, trying to get the proper stresses put in the proper places. The use of tikz is recent and simplifies the placement of the stress marks.

The approach implemented here is based on the observation that syllables are generally distributed evenly within most words. In the second example ("Succulent..."), I indicate how an atypical distribution of syllable lengths might be handled.

I prefer to avoid markup as much as I can. The principle here is to precede the word with the stress pattern with the command \sn and using / for stressed and * for unstressed syllables. So, logarithm would be given as sn/*/* logarithm and would look like this:

\documentclass{article}
\usepackage{tikz}

\newbox\wordbox
\newbox\stressbox

\def\mymacron{%
\tikz[baseline] \draw (0,0) -- (0.5ex,0);%
}

\def\mybreve{%
\tikz[baseline] \draw[yshift=0.15ex] (0,0) arc (180:360:0.25ex);%
}

\def\mb{% for [macron]breve
{\tikz[baseline]
{%
\draw (0.1ex,-0.3ex) -| (-0.2ex,0.35ex) -- (0.1ex,0.35ex);% left brace
\draw (0,0) -- (0.5ex,0);% breve
\draw (0.4ex,-0.3ex) -| (0.7ex,0.35ex) -- (0.4ex,0.35ex);% right brace
\draw (0.8ex,-0.3ex) -- (1ex,0.35ex);% slash
\draw[yshift=0.15ex] (1.1ex,0) arc (180:360:0.25ex);% breve
}}%
}

\def\bm{% for [breve]macron
{\tikz[baseline]
{%
\draw (0.1ex,-0.3ex) -| (-0.2ex,0.35ex) -- (0.1ex,0.35ex);% left bracket
\draw[yshift=0.15ex] (0,0) arc (180:360:0.25ex);% breve
\draw (0.4ex,-0.3ex) -| (0.7ex,0.35ex) -- (0.4ex,0.35ex);% right bracket
\draw (0.8ex,-0.3ex) -- (1ex,0.35ex);% slash
\draw (1ex,0) -- (1.5ex,0);% macron
}}%
}

\if#1/%
\mymacron% Change to suit
\else
\if#1*%
\mybreve
\else
#1%
\fi
\fi
\hss
}

\def\fifo#1{\ifx\ofif#1\ofif\fi% first in first out
\process#1\fifo}%

\def\ofif#1\fifo{\fi}

\def\sn#1 #2 {% for *s*cansio*n*
\setbox\wordbox\hbox{#2}%
\setbox\stressbox\hbox to\wd\wordbox{\Large\hss\fifo#1\ofif}% Change \Large to alter mark size
\ooalign{\raisebox{1em}{\box\stressbox}\cr#2\cr}% change the dimension to suit
\space
}

\begin{document}

\sn/ When \sn* to \sn* the \sn/* sessions \sn* of \sn/ sweet \sn\mb* silent \sn/ thought

\bigskip

%% Note that anything other than /, *, \mb and \bm should be wrapped in braces.
\sn/** Succulent \sn/* berries \sn*{\enskip}/{\quad} abound

\end{document}


The OP's [x]/ x I assume means that the syllable could be either stressed or unstressed. The macros \bm and \mb can be used to replicate this.

Clearly, there is room for improvement so comments are welcome.

## Later

For my own sake, I have decided to essay something closer to the OP's request and attempt to put the stress marks on the appropriate vowels while, again, trying to keep markup at a minimum. The source looks a bit cryptic (a little like xy) but the entry is simple enough: The four special characters -- |, >, / and * -- each take an argument (letter) without the need for {...} and adds, respectively a macron, breve, [macron]breve and **[breve]macron**.

\documentclass[12pt]{article}
\usepackage{tikz}
\usepackage{calc}

\newlength\correction

\def\mymacron{%
\tikz[baseline] \draw (0ex,0) -- (0.5ex,0);%
}

\def\mybreve{%
\tikz[baseline] \draw[yshift=0.15ex] (0,0) arc (180:360:0.25ex);%
}

\def\mb{% for [macron]breve
{\tikz[baseline]
{%
\draw (0.1ex,-0.3ex) -| (-0.2ex,0.35ex) -- (0.1ex,0.35ex);% left brace
\draw (0,0) -- (0.5ex,0);% breve
\draw (0.4ex,-0.3ex) -| (0.7ex,0.35ex) -- (0.4ex,0.35ex);% right brace
\draw (0.8ex,-0.3ex) -- (1ex,0.35ex);% slash
\draw[yshift=0.15ex] (1.1ex,0) arc (180:360:0.25ex);% breve
}}%
}

\def\bm{% for [breve]macron
{\tikz[baseline]
{%
\draw (0.1ex,-0.3ex) -| (-0.2ex,0.35ex) -- (0.1ex,0.35ex);% left bracket
\draw[yshift=0.15ex] (0,0) arc (180:360:0.25ex);% breve
\draw (0.4ex,-0.3ex) -| (0.7ex,0.35ex) -- (0.4ex,0.35ex);% right bracket
\draw (0.8ex,-0.3ex) -- (1ex,0.35ex);% slash
\draw (1ex,0) -- (1.5ex,0);% macron
}}%
}

\setlength{\correction}{0.4em}% Change to suit; probably font-dependent
\begingroup
\catcode|=\active
\catcode>=\active
\catcode/=\active
\catcode*=\active
\gdef\beginscan{%
\begingroup
\def|##1{\ooalign{\raisebox{1em}{\hbox to 0pt{\Large\hspace{\correction}\hss\mymacron\hss}}\cr##1\cr}}%
\def>##1{\ooalign{\raisebox{1em}{\hbox to 0pt{\Large\hspace{\correction}\hss\mybreve\hss}}\cr##1\cr}}%
\def/##1{\ooalign{\raisebox{1em}{\hbox to 0pt{\Large\hspace{\correction}\hss\mb\hss}}\cr##1\cr}}%
\def*##1{\ooalign{\raisebox{1em}{\hbox to 0pt{\Large\hspace{\correction}\hss\bm\hss}}\cr##1\cr}}%
\catcode|=\active % macron
\catcode>=\active % breve
\catcode/=\active % [macron]breve
\catcode*=\active % [breve]macron
}
\endgroup

\def\endscan{%
\endgroup
}

\begin{document}

\beginscan
Wh|en t>o th>e s|ess>ions >of sw|eet /sil>ent th|ought

\bigskip

S|ucc>ul>ent b|err>ies >ab|ound

\bigskip

l|og>ar|ith>m
\endscan

\end{document}