# Preformatted text using ConTeXt's \startlines

This is a follow-up question to

I am using the results of pdf text extraction to generate source files for reproducing a (poublic domain) book from its pdf, while trying to retain as much of the original layout as possible, especially linebreaks. Latex has worked fine for this so far, but I'm looking into ConTeXt as an alternative, partly out of curiousity.

So far I've manually inserted \linebreak (in LaTeX) or \break (in ConTeXt) to force the line-breaking algorithm to adhere to the original line breaks, but reading through the documentation I've come across \startlines which suggest I don't have to litter the text with so much cruft.

The documentation describes the inbetween argument as:

command that is expanded and then placed between each line and the next


But the following MWE doesn't behave as expected:

\starttext
\setuplines[inbetween=\break]

\startlines
First line --- should be fully justified
Secondline --- should be fully justified
\stoplines

\stoptext


In fact, substituting some marker test as the inbetween argument suggests that the inbetween code is inserted only on paragraph breaks:

\starttext
\setuplines[inbetween=FOO]

\startlines
First line

Secondline
\stoplines

\stoptext


An additional concern is that the contents may contain multiple paragraphs, so that a blank line (now appended with a \break) should not force a new page.

Edit 1: Ideally I should be able to use something like:

\setupindenting[yes,0.1in]
\startX
first line of first paragraph, whose end becomes a tex linebreak
second line of first paragraph, whose end becomes a tex linebreak
third line, left unjustified.

% parbreak
first line of second paragraph...
\stopX


Similar to the way HTML's <pre> tag works.

As explained in Metafox's answer to your previous question, you can use the paragraph alignment to achieve this effect. For example,

\showframe % to visualize the page
\starttext
\setuplines[align=paragraph]

\startlines
First line --- should be fully justified
Secondline --- should be fully justified
\stoplines

\stoptext


gives

Edit Here is one way to get \startlines to obey \parindent (rather fake \parindent).

\setuppapersize[A5]

\definemeasure[indent][20pt]

\setupindenting[\measure{indent},yes]

\define\ResetIndent
{\let\Indent\FirstIndent}

\define\FirstIndent
{\hskip\measure{indent}%
\let\Indent\relax}

\let\Indent\FirstIndent

\setuplines
[
align=paragraph,
command={\Indent},
inbetween={\blank\ResetIndent},
option=packed,
]

\starttext
\input knuth

\startlines
Thus, I came to the conclusion that the designer of a
new system must not only be the implementer and first
large--scale user; the designer should also write the first
user manual. \crlf

The separation of any of these four components would
have hurt TEX significantly. If I had not participated fully
in all these activities, literally hundreds of improvements
would never have been made, because I would never have
thought of them or perceived why they were important. \crlf

But a system cannot be successful if it is too strongly
influenced by a single person. Once the initial design is
complete and fairly robust, the real test begins as people
with many different viewpoints undertake their own exper-
iments. \crlf
\stoplines

\stoptext


• I use \definemeasure and \measure{..} to use the same value for both setting indentation and using indentation in the lines environment.

• option=packed ensures that there is no page break inside the lines environment. So you will have to Add each page in a separate lines environment.

• I have manually added \crlf on the last line of each paragraph. If you don't want to manually add \crlf at the end of each paragraph, then one option is to capture the content of the environment as a buffer, and algorithmically add \crlf at the end of each paragraph. See, for example, this example in the wiki.

• Is it possible to leave the last line in a paragraph unjustified? and honor empty lines as paragraph breaks? this is also undocumented afaict. – Jared Kulik Jul 19 '15 at 23:07
• @JaredKulik: To leave the last line in the "paragraph" unjustified, you could end the paragraph with \crlf. (It should be possible to do this in an automated manner, but I'll need to search for that). I don't understand what you mean by honor empty lines as paragraph breaks. – Aditya Jul 20 '15 at 0:08
• The goal is to recreate a paragraph's appearence from a pdf in ConTeXt, with minimal added markup. Is there a way to make \startlines to obey \parindent? – Jared Kulik Jul 20 '15 at 0:35
• @JaredKulik: See edited answer. – Aditya Jul 20 '15 at 1:31
• Excellent. Where are you getting all this from? paragraph, command=, option=, I can't find any documentation for any of this. Also, isn't inbetween misdocumented in the page linked in the OP? – Jared Kulik Jul 20 '15 at 2:15

Following up on @Aditya LuaTeX reference, here is an alternative solution based on lua:

\setuppapersize[A5]
\setupindenting[0.2in,yes]

% Create an environment that stores everything
% between \startpreformatted and \stoppreformatted
% in a buffer named 'preformatted'.
\def\startpreformatted
{\dostartbuffer
[preformatted]
[startpreformatted]
[stoppreformatted]}

% On closing the preformatted environment, call the LuaTeX
% function preformatted(), and pass it the contents of
% the buffer called 'preformatted'
\def\stoppreformatted
{\ctxlua
{userdata.preformatted(buffers.getcontent('preformatted'))}}

\startluacode
userdata = userdata or {}

function userdata.isemptyline(line)
return nil ~= string.find(line,'^ *\$' )
end

function userdata.preformatted(content)
local lines    = string.splitlines(content)
for i=1,#lines do
if i < #lines then
if (not userdata.isemptyline(lines[i+1])) and (not userdata.isemptyline(lines[i])) then
lines[i] = lines[i]  .. "\\break"
end
-- else do something special for last line
end
end

content = table.concat(lines,'\n')
context(content)
end
\stopluacode

\starttext
\startpreformatted
Thus, I came to the conclusion that the designer of a
new system must not only be the implementer and first
large--scale user; the designer should also write the first
user manual.

The separation of any of these four components would
have hurt TEX significantly. If I had not participated fully
in all these activities, literally hundreds of improvements
would never have been made, because I would never have
thought of them or perceived why they were important.
\stoppreformatted

\stoptext


Result: