# How do PostScript interpreters know the meanings of PGF-specific operators, such as 'pgfe' and 'pgfstr'?

A TikZ node "lives" in a TeX box. With latex as the TeX engine these boxes are converted to PostScript directives. Use \showbox to see how a box like this is implemented by following these steps.

1. Open the TikZ source file <tex installation directory>/tex/generic/pgf/frontendlayer/tikz/tikz.code.tex and add the instruction

\showbox\tikz@figbox%


just after the comment

% Step 13: Add labels and nodes

2. Create the following LaTeX manuscript:

\documentclass{article}
\usepackage{tikz}
\begin{document}
\tikz \path (0,0) node[draw] {};
\end{document}

3. Compile the manuscript with latex. The compilation will halt with a question mark:

l.4 \tikz \path (0,0) node[draw] {};

?


Entering q<RET> will end the session and flush the log buffer to the log file.

4. Open the log file. The raw box will be found near the end of the file:

> \box33=
\hbox(0.0+0.0)x0.0
.\hbox(0.0+0.0)x0.0
..\special{ps:: save }
..\glue 0.0

...

..\glue 0.0
..\special{ps:: 6.64113 6.64113 -3.32056 -3.32056 pgfe }
..\special{ps:: pgfstr }
..\glue 0.0

...

..\glue 0.0
..\special{ps:: save }
..\special{ps:: [1.0 0.0 0.0 1.0 0.0 0.0 ] concat }
..\special{ps:: pgfs}
..\special{ps::[end]}
..\hbox(0.0+0.0)x0.0
...\special{ps:: 0 setgray }
..\glue 0.0
..\special{ps::[begin]}
..\special{ps:: pgfr}
..\special{ps:: restore }
..\special{ps:: restore }

! OK.


As can be seen, the PostScript operators used to render the box include save, pgfe, pgfstr, and concat. Now, save and concat are official operators documented in the PostScript manual, but pgfe, pgfstr and the other pgf... operators are, I believe, PGF-specific and are not part of the PostScript language. How do PostScript interpreters, such as dvi viewers and utilities such as dvipdf, know what to make of these operators and how to interpret them?

The PostScript definitions for pgf/TikZ can be found in the files

pgfsys-common-postscript.def and pgfsys-dvips.def in the TeX directory tree under

texmf-dist/generic/pgf/systemlayer


/pgfstr is defined in pgfsys-dvips.def (as well as again for the vtex version)

/pgfe is defined in pgfsys-common-postscript.def

Definitions for the other output 'engines' like .pdf etc. can be found there as well within files of similar names.

• Perhaps worth noting that almost all real PostScript files include similar shortcut definitions. – Joseph Wright Aug 6 '17 at 16:12
• With TeX generated PS files, but not almost all ... – user2478 Aug 6 '17 at 16:32
• @Herbert Other tools I use to make EPS files always have some shortcuts in the prologue, e.g. /m {moveto} def /l {lineto} def /r {rmoveto} def . Of course this depends on the tool one uses. – Joseph Wright Aug 6 '17 at 16:44
• I think the other part of the answer, probably the main part, is explaining how these definitions from the .def files get put into the .ps files. – ShreevatsaR Aug 6 '17 at 18:03
• @EvanAad I don't think I know the answer :-) But what I could figure out just now, by running dvitype on the dvi file, is that the definitions are already inserted as specials into the dvi file, so that when dvips (for an example PostScript driver) is used, it simply puts those specials into the .ps file to be read by the PostScript interpreter. – ShreevatsaR Aug 7 '17 at 6:13

Here is a PostScript function which defines all pgf functions:

/pgffunctions {
/pgfsc{}bind def% stroke color is empty by default
/pgffc{}bind def% fill color is empty by default
/pgfstr{stroke}bind def
/pgffill{fill}bind def
/pgfeofill{eofill}bind def
/pgfe{a dup 0 rlineto exch 0 exch rlineto neg 0 rlineto closepath}bind def% rectangle
/pgfw{setlinewidth}bind def% setlinewidth
/pgfs{save pgfpd 72 Resolution div 72 VResolution div neg scale
magscale{1 DVImag div dup scale}if
pgfx neg pgfy neg translate pgffoa .setopacityalpha}bind def% save
/pgfr{pgfsd restore}bind def %restore
userdict begin
/pgfo{pgfsd /pgfx currentpoint /pgfy exch def def @beginspecial}bind def %open
/pgfc{newpath @endspecial pgfpd}bind def %close
/pgfsd{globaldict /pgfdelta /delta where {pop delta} {0} ifelse put}bind def% save delta
/pgfpd{/delta globaldict /pgfdelta get def}bind def % put delta
/.setopacityalpha where {pop} {/.setopacityalpha{pop}def} ifelse % install .setopacityalpha
/.pgfsetfillopacityalpha{/pgffoa exch def
/pgffill{gsave pgffoa .setopacityalpha fill 1 .setopacityalpha newpath fill grestore newpath}bind def
/pgfeofill{gsave pgffoa .setopacityalpha eofill 1 .setopacityalpha newpath eofill grestore newpath}bind def}bind def
/.pgfsetstrokeopacityalpha{/pgfsoa exch def /pgfstr{gsave pgfsoa .setopacityalpha stroke grestore newpath}bind def}bind def
/pgffoa 1 def
/pgfsoa 1 def
end
} def

• Can you add context on what this is? Is this code you wrote yourself? (If so it can't be relevant to the question I guess…) Is this code that exists in some file used by the TeX engine? (If so, how is it used, and how does this code end up in the PostScript file?) – ShreevatsaR Aug 6 '17 at 22:00
• As I already wrote: that are all functions which are defined by pgf! They are all extracted from the relevant pgf files and I use it together with PSTricks. – user2478 Aug 7 '17 at 6:47
• It wasn't clear to me from the words in the answer ("Here is a PostScript function which defines all pgf functions") that these definitions were in pgf. Now it is clear. But what is the answer to the question? How do these functions, that are defined by pgf, wind through TeX and end up being available to the PostScript interpreters? – ShreevatsaR Aug 7 '17 at 14:51