I came across PLT Scribble which appears to be the best tool available today for writing documentation. You write text with some Scheme in it, it generates HTML and LaTeX. Without much ado, I could use PLT Racket to define a lexer for F# that pretty-prints code blocks. It worked beautifully for HTML, but in LaTeX I hit a problem – how do I define a macro that typesets its argument with preserved whitespace and mono-space font, while keeping other commands as-is?
Note, verbatim does not work – it types inner commands verbatim, instead of applying them to, say, make keywords blue. There is alltt and fancyvrb but they do not work either: somehow they change the reader too much. Scribble generated commands of the form “\char’146” that LaTeX accepts in default mode but fails to accept inside alltt or Verbatim from fancyvrb.
I knew then I had no choice but to roll my own..
Enter 1970-s text processing technology. Without proper documentation either, because I do not currently have a copy of the TeX book handy. Anyhow, here is what I got after more time than I care to admit:
% ``\Listing{...}'' command typesets its argument as a code block - | |
% with monospace font and whitespace preserved. It is an | |
% environment-like command accepting multiple paragraphs. | |
\def\Listing{\bigskip\begingroup% | |
\setlength{\parskip}{0pc}\addtolength{\parindent}{1pc}% | |
\tt\scriptsize\obeylines\obeyspaces\PreserveWhitespace\ListingBody} | |
% ``\ListingBody'' is an auxillary command need to make Listing work. | |
% It inserts the argument and closes the group opened by Listing. | |
\long\def\ListingBody#1{#1\endgroup\smallskip} | |
% \PreserveWhitespace makes leading spaces appear as-is. To make | |
% leading spaces appear, we have to set space to be an active | |
% character that exands to a non-breakable space. The command for | |
% this is ``\let =\ ``, but unfortunately lifting this command to a | |
% macro does not quite work because space is not active during the | |
% definition of the macro - it needs to be made active using | |
% ``\catcode''. Therefore we define our macro in a little block of | |
% code where space is made active: | |
\begingroup | |
\catcode32=\active | |
\gdef\PreserveWhitespace{\catcode32=\active\let =\ } | |
\endgroup |