I'm unsure how to present the question, so I'll just go with something and edit if it is deemed necessary.
The PDF extensions currently extend the basic TeX macros with at least the following three macros
\pdfsavepos
,\pdflastxpos
and\pdflastypos
,
which allow the user to extract the current page positioning at shipout. This is discussed in some detail in the TUG article here: https://www.tug.org/TUGboat/tb30-1/tb94zyka.pdf
I'm trying to sort a counter, based on \pdfsavepos
. The idea is that I have a few macros, say, \csname macro-1-savedposition\endcsname
all the way up to, say, \csname macro-4-savedposition\endcsname
(in the case of four instances of the macro), and the expanded values hold \the\pdflastypos
. I then wish to sort these macros so that another macro, say \csname macro-3\endcsname
, expands correctly based on the value of the savedposition instance.
As a concrete example, say I have four macros (the value after the arrow is the (once) expanded definition of the macro):
\csname macro-1-savedposition\endcsname -> 12345
\csname macro-2-savedposition\endcsname -> 1234
\csname macro-3-savedposition\endcsname -> 123456
\csname macro-4-savedposition\endcsname -> 1234567
Since page positioning happens from the bottom to the top, I wish to sort them with order "largest first", so in this case the order should be 4-3-1-2
. The corresponding macros should then have the expanded values of \csname macro-4\endcsname=1
, \csname macro-3\endcsname=2
, \csname macro-1\endcsname=3
and \csname macro-2\endcsname=4
.
I've been pondering how to get this done for a while now and I feel like I'm stuck. In the simplest case I could simply extract the absolute page positioning at macro callout rather than at page shipout, but clearly the mechanism isn't coded this way and I'm unsure whether such functionality is even supported.
Digging deeper, this means that identifiers corresponding to the saved positions have to be added in retro-actively, since (to my knowledge) counters are generally not incremented at page shipout. This asynchronous handling of the positioning calculations and the counter values makes life much harder. One option would be to produce chains of these positioning commands, a method I also used in my other question: Reflowing marginpars typeset using pdfsavepos, but I have not found anything to loop over these chains in this website or on foreign websites concerning the TeX language.
Moving forward to the sorting part, a preliminary implementation of (alpha)numeric sorting that I found useful but could not adapt to this use case was presented here: How to sort an alphanumeric list (I may have messed up expansion control in this respect.)
The below example shows the issue quite nicely:
\documentclass{article}
\usepackage{lipsum}
\makeatletter
\def\@oddfoot{\hskip\textwidth\smash{\raise\footskip\vbox to .9\textheight{\hsize\marginparwidth%
\hrule\@height\z@%
\box123
\vskip\z@\@plus\textheight}}}
\def\mymacroX{\setbox123\hbox{Here is my macro X \mymacro}}
\def\saveposition#1{%
\pdfsavepos\write\@auxout{%
\noexpand\savedpos%
{#1}{\the\c@page}{\the\pdflastxpos}{\the\pdflastypos}}}
\def\savedpos#1#2#3#4{%
\begingroup
\let\@positions\relax
\expandafter\xdef\csname sp@#1-#2\endcsname{%
\expandafter\ifx\csname sp@#1-#2\endcsname\relax
\else
\csname sp@#1-#2\endcsname
\fi
\@positions{#3}{#4}}%
\endgroup}%
\newcount\mymacrocounter
\newcount\mymacrohelper
\def\mymacro{%
\saveposition{mymacro}
}
\makeatother
\begin{document}
\lipsum[1]
\mymacro
\mymacroX
\lipsum[1]
\mymacro
\lipsum[1]
\mymacro
\lipsum[1]
\mymacro
\end{document}
If we look at the aux
file, we see that the fourth instance, created by \mymacroX
, has a higher value of \pdflastypos
than the previous instance, even though it was called second and typeset last.
I'll add in more examples when I finally manage to compile one.
EDIT The most concrete example I can think of is the actual use case. The code can be found at gist.github.com/TobiasBouma/de4fa02c4e7fa12141ca and gist.github.com/TobiasBouma/798444f698dd637cafa2, which shows why I'm asking for a position-based solution spefically. (Just for completeness, I'm not recommending the usage of that code as an MWE.)