Skip to content

Instantly share code, notes, and snippets.

@gusbrs
Last active April 30, 2018 15:27
Show Gist options
  • Save gusbrs/876746b4bbc503ea7f3e33c0a15dd569 to your computer and use it in GitHub Desktop.
Save gusbrs/876746b4bbc503ea7f3e33c0a15dd569 to your computer and use it in GitHub Desktop.
\documentclass[12pt]{scrartcl}
\usepackage{soulutf8}
\usepackage{atbegshi}
\usepackage{etoolbox}
% \usepackage{calc}
\usepackage{tikz}
\usetikzlibrary{tikzmark,calc}
\makeatletter
\newlength{\txtdec@depth}
\setlength{\txtdec@depth}{.35ex}
\newcounter{txtdec@hyphmark}
\newcounter{txtdec@decormark}
\newcounter{txtdec@hyphdraw}
\setcounter{txtdec@hyphdraw}{1}
\newcounter{txtdec@decordraw}
\setcounter{txtdec@decordraw}{1}
\newcounter{txtdec@thenextpage}
\newtoggle{txtdec@unfinisheddecor}
\newtoggle{txtdec@stayonpage}
\newtoggle{txtdec@stayondecor}
\newtoggle{txtdec@stayonline}
% from https://tex.stackexchange.com/a/33765/105447
\newcommand{\gettikzxy}[3]{%
\tikz@scan@one@point\pgfutil@firstofone#1\relax
\edef#2{\the\pgf@x}%
\edef#3{\the\pgf@y}%
}
% the drawing macros
\newcommand{\txtdec@draw@all}{%
\draw[blue] ($(\Xbegin,\Ybegin)-(0,\txtdec@depth)$) -- ($(\Xend,\Yend)-(0,\txtdec@depth)$) ;
}
\newcommand{\txtdec@draw@begin}{%
\draw[blue] ($(\Xlinebegin,\Ylinebegin)-(0,\txtdec@depth)$) -- ($(\Xlineend,\Ylineend)-(0,\txtdec@depth)$) ;
}
\newcommand{\txtdec@draw@middle}{%
\draw[green] ($(\Xlinebegin,\Ylinebegin)-(0,\txtdec@depth)$) -- ($(\Xlineend,\Ylineend)-(0,\txtdec@depth)$) ;
}
\newcommand{\txtdec@draw@end}{%
\draw[red] ($(\Xlinebegin,\Ylinebegin)-(0,\txtdec@depth)$) -- ($(\Xend,\Yend)-(0,\txtdec@depth)$) ;
}
% using soul to set tikzmarks
\def\SOUL@tdleaders{%
\stepcounter{txtdec@hyphmark}\tikzmark{p\thepage.d\arabic{txtdec@decormark}.\arabic{txtdec@hyphmark}}%
\leaders\hrule\@depth\z@\@height\z@\relax
}
\def\SOUL@tdunderline#1{{%
\setbox\z@\hbox{#1}%
\dimen@=\wd\z@
\dimen@i=\SOUL@uloverlap
\advance\dimen@2\dimen@i
\rlap{%
\null
\kern-\dimen@i
\SOUL@ulcolor{\SOUL@tdleaders\hskip\dimen@}%
\hskip\dimen@
}%
\unhcopy\z@
}}
\def\SOUL@tdpreamble{%
\spaceskip\SOUL@spaceskip
\stepcounter{txtdec@decormark}%
\setcounter{txtdec@hyphmark}{0}%
\tikzmark{p\thepage.d\arabic{txtdec@decormark}.begin}%
}
\def\SOUL@tdeverysyllable{%
\SOUL@tdunderline{%
\the\SOUL@syllable
\SOUL@setkern\SOUL@charkern
}%
\stepcounter{txtdec@hyphmark}\tikzmark{p\thepage.d\arabic{txtdec@decormark}.\arabic{txtdec@hyphmark}}%
}
\def\SOUL@tdeveryhyphen{%
\discretionary{%
\unkern
\SOUL@tdunderline{%
\SOUL@setkern\SOUL@hyphkern
\SOUL@sethyphenchar
}%
\stepcounter{txtdec@hyphmark}\tikzmark{p\thepage.d\arabic{txtdec@decormark}.\arabic{txtdec@hyphmark}}%
}{}{}%
}
\def\SOUL@tdeveryexhyphen#1{%
\SOUL@setkern\SOUL@hyphkern
\SOUL@tdunderline{#1}%
\discretionary{}{}{%
\SOUL@setkern\SOUL@charkern
}%
\stepcounter{txtdec@hyphmark}\tikzmark{p\thepage.d\arabic{txtdec@decormark}.\arabic{txtdec@hyphmark}}%
}
\def\SOUL@tdpostamble{%
% create an extra mark, vertically displaced, to create an exit condition for the last line
\stepcounter{txtdec@hyphmark}\raisebox{-5pt}{\tikzmark{p\thepage.d\arabic{txtdec@decormark}.\arabic{txtdec@hyphmark}}}%
\tikzmark{p\thepage.d\arabic{txtdec@decormark}.end}%
}
\def\SOUL@tdsetup{%
\SOUL@setup
\let\SOUL@preamble\SOUL@tdpreamble
\let\SOUL@everysyllable\SOUL@tdeverysyllable
\let\SOUL@everyhyphen\SOUL@tdeveryhyphen
\let\SOUL@everyexhyphen\SOUL@tdeveryexhyphen
\let\SOUL@postamble\SOUL@tdpostamble
}
\DeclareRobustCommand*\textdecor{\SOUL@tdsetup\SOUL@}
% get the drawing done AtBeginShipout
\AtBeginShipout{%
\AtBeginShipoutUpperLeft{%
% getting the number of the next page
\setcounter{txtdec@thenextpage}{\thepage}%
\stepcounter{txtdec@thenextpage}%
% if the current decoration occurs on this page, stay on it
\iftikzmark{p\thepage.d\arabic{txtdec@decordraw}.\arabic{txtdec@hyphdraw}}{%
\toggletrue{txtdec@stayonpage}}{}%
\whileboolexpr{togl {txtdec@stayonpage}}{%
\begin{tikzpicture}[remember picture, overlay]
\iftikzmark{p\thepage.d\arabic{txtdec@decordraw}.begin}{%
% if current decor begins in current page, get coordinates
\gettikzxy{(pic cs:p\thepage.d\arabic{txtdec@decordraw}.begin)}{\Xbegin}{\Ybegin}}{%
% if current decor begins in previous page, set to top left of the page
\gettikzxy{(current page.north west)}{\Xbegin}{\Ybegin}}%
\iftikzmark{p\thepage.d\arabic{txtdec@decordraw}.end}{%
% if current decor ends in current page, get coordinates
\gettikzxy{(pic cs:p\thepage.d\arabic{txtdec@decordraw}.end)}{\Xend}{\Yend}}{%
% if current decor ends in future page, set to bottom right of the page
\gettikzxy{(current page.south east)}{\Xend}{\Yend}}%
\ifdim\Ybegin=\Yend % the simplest case, a single line
\txtdec@draw@all
\stepcounter{txtdec@decordraw}%
\else % current textdecor has a line break
\toggletrue{txtdec@stayondecor}%
\whileboolexpr{togl {txtdec@stayondecor}}{%
\gettikzxy{(pic cs:p\thepage.d\arabic{txtdec@decordraw}.\arabic{txtdec@hyphdraw})}{\Xlinebegin}{\Ylinebegin}%
\edef\Xcurrent{\Xlinebegin}%
\edef\Ycurrent{\Ylinebegin}%
\edef\Xnext{\Xcurrent}%
\edef\Ynext{\Ycurrent}%
\toggletrue{txtdec@stayonline}%
\whileboolexpr{togl {txtdec@stayonline}}{%
\ifdim\Ycurrent=\Ynext
\stepcounter{txtdec@hyphdraw}%
% if the following tikzmark exists, we are at a page break
\iftikzmark{p\arabic{txtdec@thenextpage}.d\arabic{txtdec@decordraw}.\arabic{txtdec@hyphdraw}}{%
\edef\Xcurrent{\Xnext}%
\edef\Ycurrent{\Ynext}%
\gettikzxy{(current page.south east)}{\Xnext}{\Ynext}
\togglefalse{txtdec@stayondecor}%
}{% else, we remain on the same page
\iftikzmark{p\thepage.d\arabic{txtdec@decordraw}.\arabic{txtdec@hyphdraw}}{%
\edef\Xcurrent{\Xnext}%
\edef\Ycurrent{\Ynext}%
\gettikzxy{(pic cs:p\thepage.d\arabic{txtdec@decordraw}.\arabic{txtdec@hyphdraw})}{\Xnext}{\Ynext}}{}%
}%
\else
\edef\Xlineend{\Xcurrent}%
\edef\Ylineend{\Ycurrent}%
\ifdim\Ylinebegin=\Ybegin
\txtdec@draw@begin
\else
\ifdim\Ycurrent=\Yend
\txtdec@draw@end
\stepcounter{txtdec@decordraw}%
\setcounter{txtdec@hyphdraw}{1}%
\togglefalse{txtdec@stayondecor}%
\else
\txtdec@draw@middle
\fi
\fi
\togglefalse{txtdec@stayonline}%
\fi
}%
}%
\fi
\end{tikzpicture}%
% if the beginning of the next decor does not exist in this page, leave this page
\iftikzmark{p\thepage.d\arabic{txtdec@decordraw}.begin}{}{%
\togglefalse{txtdec@stayonpage}}%
% if the continuation of the current decor exists in the next page, leave this page
\iftikzmark{p\arabic{txtdec@thenextpage}.d\arabic{txtdec@decordraw}.\arabic{txtdec@hyphdraw}}{%
\togglefalse{txtdec@stayonpage}}{}%
}%
}%
}
\makeatother
\begin{document}
\vspace*{15cm}
Lorem ipsum \textdecor{dolor sit amet, consectetuer adipiscing}
elit. Ut purus elit, vestibulum ut, placerat ac, adipiscing vitae,
felis. Curabitur dictum gravida mauris. Nam arcu libero, nonummy eget,
consectetuer id, vulputate a, magna. \textdecor{Donec vehicula augue
eu neque. Pellentesque habitant morbi tristi-que senectus et netus
et malesuada fames ac -- turpis --- egestas. Mauris ut leo. Cras
viverra metus rhoncus sem. Nulla et lectus vestibulum urna fringilla
ultrices.} Phasellus eu tellus sit amet tortor gravida
placerat. Integer sapien est, iaculis in, pretium quis, viverra ac,
nunc. Praesent eget sem vel leo ultrices bibendum. Aenean
faucibus. Morbi dolor nulla, malesuada eu, pulvinar at, mollis ac,
nulla. Curabitur auctor semper nulla. Donec varius orci eget
risus. \textdecor{Duis nibh mi, congue eu, accumsan eleifend, sagittis
quis, diam. Duis eget orci sit amet orci dignissim rutrum. Nam dui
ligula, fringilla a, euismod sodales, sollicitudin vel, wisi. Morbi
auctor lorem non justo. Nam lacus libero, pretium at, lobortis
vitae, ultricies et, tellus. Donec aliquet, tortor sed accumsan
bibendum, erat ligula aliquet magna, vitae ornare odio metus a mi.
Morbi ac orci et nisl hendrerit mollis. Suspendisse ut massa. Cras
nec ante. Pellentesque a nulla.} Cum sociis natoque penatibus et
magnis dis parturient montes, nascetur ridiculus mus. Aliquam
tincidunt urna. Nulla ullamcorper vestibulum turpis. Pellentesque
cursus luctus mauris.
\clearpage
Lorem ipsum \textdecor{dolor sit amet, consectetuer adipiscing}
elit. Ut purus elit, vestibulum ut, placerat ac, adipiscing vitae,
felis. Curabitur dictum gravida mauris. Nam arcu libero, nonummy eget,
consectetuer id, vulputate a, magna. \textdecor{Donec vehicula augue
eu neque. Pellentesque habitant morbi tristi-que senectus et netus
et malesuada fames ac -- turpis --- egestas. Mauris ut leo. Cras
viverra metus rhoncus sem. Nulla et lectus vestibulum urna fringilla
ultrices.} Phasellus eu tellus sit amet tortor gravida
placerat. Integer sapien est, iaculis in, pretium quis, viverra ac,
nunc. Praesent eget sem vel leo ultrices bibendum. Aenean
faucibus. Morbi dolor nulla, malesuada eu, pulvinar at, mollis ac,
nulla. Curabitur auctor semper nulla. Donec varius orci eget
risus. \textdecor{Duis nibh mi, congue eu, accumsan eleifend, sagittis
quis, diam. Duis eget orci sit amet orci dignissim rutrum. Nam dui
ligula, fringilla a, euismod sodales, sollicitudin vel, wisi. Morbi
auctor lorem non justo. Nam lacus libero, pretium at, lobortis
vitae, ultricies et, tellus. Donec aliquet, tortor sed accumsan
bibendum, erat ligula aliquet magna, vitae ornare odio metus a mi.
Morbi ac orci et nisl hendrerit mollis. Suspendisse ut massa. Cras
nec ante. Pellentesque a nulla.} Cum sociis natoque penatibus et
magnis dis parturient montes, nascetur ridiculus mus. Aliquam
tincidunt urna. Nulla ullamcorper vestibulum turpis. Pellentesque
cursus luctus mauris.
\end{document}
%%% Local Variables:
%%% mode: latex
%%% TeX-master: t
%%% End:
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment