1

This question is a refinement of ConTeXt: avoid enumeration items across pages.

Given an itemgroup, each \item contains one or more paragraphs or itemgroups, possibly mixed. I only want pagebreaks between paragraphs or itemgroups, with several exceptions:

  • Never page break after the first paragraph, as it is somewhat of a heading
  • Only break a paragraph or itemgroup (into pieces) if it is longer than some arbitrary number X.
  • When breaking a paragraph or itemgroup, ensure that each the length of each portion Y is Y>X/Z for some arbitrary number Z. The idea is to minimize orphans and widows especially for the second paragraph which is the main paragraph.

The example below demonstrates the types of paragraphs I'm dealing with.

  • Rirst paragraph is always a single line.
  • Other paragraphs or nested items are short, 1-5(+?) lines.
  • Few paragraphs per item or items per nested itemgroups.

My last two points I considered to be more like guidelines. These are the problems I've been fighting:

  • Page break after the first paragraph.
  • Poor breaking of the second paragraph. If it's four lines then it is broken 2-2. I don't know if it could be broken 1-3/3-1 and 3-line paragraphs broken 1-2/2-1, or if the widow and club penalties prevent this. I'm not even sure I'd be comfortable having a 5-6 line paragraph broken up at all either. But yeah there's some arbitrary point (8?) were I would want paragraphs split, because horrible page breaks are horrible (and footer spill infinitely worse). When I say second I mean all remaining paragraphs... and that I care about the appearance of the second paragraph more than others. I've been fortunate to not have page breaks across itemgroups, but same guidelines should apply.
  • Not comfortable with setting \widowpenalty or \clubpenalty for the entire document.
\setupwhitespace[medium]

\starttext
    \startitemize
    \sym{>}\bold{Heading One}\hfill1

        \samplefile{ward}

    \sym{>}\bold{Heading Two}\hfill2

        \samplefile{ward}

        \samplefile{ward}

    \sym{>}\bold{Heading Three}\hfill3

        \samplefile{knuth}

    \sym{>}\bold{Heading Four}\hfill4

        \startitemize[joinedup,nowhite,after]
            \item Some important point.
            \item \samplefile{jojomayer}
            \item Hmm shouldn't there be whitespace below?
        \stopitemize

        \samplefile{ward}

    \sym{>}\bold{Heading Five}\hfill5

        \samplefile{ward}

        \startitemize[joinedup,nowhite,after]
            \item Some important point.
            \item \samplefile{jojomayer}
            \item Hmm shouldn't there be whitespace below?
        \stopitemize

    \stopitemize
\stoptext

(page breaks may occur anywhere)

3
  • Regarding the source question's answer, I'm under the impression that a \vbox would prevent the second paragraph from breaking even when necessary - assuming you could vbox each individual paragraph or itemgroup. And that \keeplinestogether doesn't prevent a break after the first paragraph, and can cause nasty orphans/widows when a break is necessary.
    – user19087
    Commented Dec 5, 2018 at 22:10
  • 1
    Can you maybe give a real world example of what you are trying to achieve? For (1) \starthead{<first par>} <other pars> \stophead comes to my mind but that does not prevent pagebreaks within <first par>. It could be modified though. For (2), what if the remaining space on the page is less than X? You will either get a horrible page break or spilling into the footer. For (3) this is a lot of work to implement. Basically you'd reimplement TeX's paragraph builder. To minimize widows and orphans it's easier to tune \widowpenalty and \clubpenalty. Commented Dec 6, 2018 at 10:52
  • 2
    In general, forcing or preventing pagebreaks will result in a page that looks torn apart, with enourmos gaps between paragraphs. Commented Dec 6, 2018 at 10:54

1 Answer 1

5

For the first point you can use \start...\stophead with the setup afterhead={\blank[disable]} to prevent a page break at this point. The other points are more complicated and I can only offer a partial solution which requires macro support. I wrote the macro \keeptogether{<n>}{<content>} where <n> is the number of lines you want to protect from ever breaking. The macro simply records <content> into a box and splits it after <n> lines. Unfortunately, this might discard \parskip within \vsplit (see here), so no \setupwhitespace[medium], unless you don't care about inconsistent paragraph spacing.

\definesymbol[chevron][>]

\setupitemize
  [headstyle=bold,
   afterhead={\blank[disable]}]

\setupitemize
  [1]
  [symbol=chevron]

\define[1]\keeptogether{%
  \dowithnextbox{%
    \setbox\scratchbox=\vsplit\nextbox to #1\lineheight
    \setbox\scratchbox=\vbox{\unvbox\scratchbox}
    \ifdim\dp\scratchbox<\strutdepth
      \dp\scratchbox=\strutdepth
    \fi
    \box\scratchbox
    \unvbox\nextbox
  }\vbox
}

\starttext

\startitemize
  \starthead{Heading One\hfill\normal{1}}

    \samplefile{ward}

  \stophead

  \starthead{Heading Two\hfill\normal{2}}

    \samplefile{ward}

    \samplefile{ward}

  \stophead

  \starthead{Heading Three\hfill\normal{3}}

    \samplefile{knuth}

  \stophead

  \starthead{Heading Four\hfill\normal{4}}

    \startitemize[joinedup,nowhite,after]
    \item Some important point.
    \item \samplefile{jojomayer}
    \item Hmm shouldn't there be whitespace below?
    \stopitemize

    \keeptogether{3}{\samplefile{knuth}}

  \stophead

  \starthead{Heading Five\hfill\normal{5}}

    \samplefile{ward}

    \startitemize[joinedup,nowhite,after]
    \item Some important point.
    \item \samplefile{jojomayer}
    \item Hmm shouldn't there be whitespace below?
    \stopitemize
  \stophead

\stopitemize
\stoptext
1
  • I really like where this is going, especially the linked question. Instead of placing the \vbox it might be better to specify interline penalties within the box only, then unboxing before placement. This would play better with widow and orphan penalties and the builtin paragraph builder.
    – user19087
    Commented Dec 11, 2018 at 2:54

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .