38

I create a lot of theorem-like environments, and I'm usually happy to employ a package (such as ntheorem, amsthm, etc) to do the work for me.

After studying the ntheorem documentation, and reading many answers here on TeX exchange, it seems that most theorems, and more interestingly, a lot of the 'standard' environments (such as the center environment, for example) are defined in terms of trivlists

I'm interested in experimenting with my own environments using trivlists, but would like to know all the parameters that can be tweaked- so far I haven't been able to find a definitive guide, hence this question :)

So, can someone provide details of all of the parameters that can be tweaked in order to customize a trivlist?

Here's a MWE that can be played with

\documentclass{article}
\usepackage[showframe=true]{geometry}
\usepackage{lipsum}

\setlength{\parskip}{5mm}

\newenvironment{problem}{%
\begin{trivlist}%
\item[{\bfseries Problem}]%
\item%
}{\end{trivlist}}

\begin{document}

\begin{problem}
    \lipsum[1]
\end{problem}

\end{document}

Interestingly, there's no trivlist tag, so feel free to re-tag as you see appropriate.

3
  • 2
    Perhaps the definitions of \trivlist, \@trivlist (and related commands) in source2e could give you a starting point. Commented Mar 8, 2012 at 2:01
  • @GonzaloMedina yes indeed, section 56.1 looks very helpful- thanks
    – cmhughes
    Commented Mar 8, 2012 at 2:12
  • Also check out tex-tipografia.com/enumitem.html
    – HansBKK
    Commented Mar 18, 2012 at 2:02

2 Answers 2

20

I cannot say this answer is a definitive guide, but the definitive statement one can make about trivlists are that they are plain vanilla  lists.

\begin{trivlist}
  \item $\varepsilon$-\TeX
  \item[test] a line to test
  \item Ghostscript, version $\ge8.31$
  \item dvipdfmx, version $\ge20080607$ for DVI to PDF conversion
  \item Adobe Reader or another viewer
\end{trivlist}

In simple terms the trivlist environment turns each item into a paragraph and thus it is easier to apply formatting information to a list of paragraphs or items if you want to think of them this way. As it carries common information to all lists, it is used to build up more complicated structures. All LaTeX's lists use parshape to shape the paragraph and the source is not easy to follow.

The definite guide of course is File A: ltlists.dtx in source2e.

A good use of trivlists is to simplify the writing of table heads and produce semantic table environments:

\documentclass{article}
\begin{document}
\newenvironment{name}
  {\trivlist\item
   \tabular{@{}ll@{}}}
  {\endtabular\endtrivlist}
\begin{name}
   First    & Mary  \\
   Second   & Jones \\
   Nickname & --- \\
\end{name}
\end{document}
3
  • +1 (and accepted): source2e is very clear- I also studied the changepage package which uses list environments at its heart. I might post an answer giving some examples, but yours sent me to the right place- thanks!
    – cmhughes
    Commented Mar 9, 2012 at 21:05
  • @cmhughes Thanks. Good idea to post some examples.
    – yannisl
    Commented Mar 9, 2012 at 21:08
  • 3
    Why is the \trivlist needed in the name environment at all? Simply excising it and its \endtrivlist pair seems to result in almost identical output. Commented Feb 9, 2019 at 2:53
17

Yiannis provided the details of where to find the definitive guide:

texdoc source2e

Section 56 is very detailed, and provides all of the parameters that can be tweaked. I thought I'd provide a small example for future reference- perhaps it will help others creating environments. (I don't claim this answer is the definitive guide, but merely an introductory experiment that may help others.)

Motivation

Firstly though, the reason I am interested in lists and trivlists is to create theorem-like environments. In particular, I wanted to emulate the break style from the ntheorem package, which produces something like

enter image description here

Initially I thought that a trivlist would be appropriate, but referencing @egreg's comment to this answer

This works provided that no list based environment appears within this trivlist. \begin{list}{}{\leftmargin=2cm}...\end{list} wouldn't have this problem (and is the approach taken by adjustwidth).

So, I then decided to use the list environment instead of the trivlist, and studied the changepage documentation too.

The list environment

The list environment has the form

\begin{list}{<label>}{options}
\item ...
\end{list}

A complete set of options is detailed in source2e, but I'll only go into a few of them here. For my particular application, I don't need a <label>, so this argument will always be empty.

  • the default settings of the list environment (without any options)

        \begin{list}{}{}
          \item {\bfseries Problem}
          \item \lipsum[1]
        \end{list}
    

    give the following output

enter image description here

  • note that the list is indented, and the separation between Problem and the next item is not ideal

  • we can tweak a few options

      \begin{list}{}{% options
            \setlength{\leftmargin}{0mm}%     leftmargin
            \parsep\parskip%                  space between paragraphs within an item
            \setlength{\itemsep}{-\parsep}%   space between items
       }
       \item {\bfseries Problem}
       \item \lipsum[1]
       \end{list}
    
  • I don't want any space between my items, so I pull them together using -\parsep, and this gives the desired result

enter image description here

Of course, this can be all be done in the pre-amble to make a \newenvironment

\newenvironment{problem}{\begin{list}{}{%
              \setlength{\leftmargin}{0mm}%
              \setlength{\rightmargin}{0mm}%
              \setlength{\topsep}{0mm}%
              \setlength{\partopsep}{0mm}%
              \parsep\parskip%
              \setlength{\itemsep}{-\parsep}%
              }\needspace{\baselineskip}\item {\bfseries Problem}
              \item}{\end{list}}

I've used the needspace package which provides the command \needspace{<space>} to stop page breaks happening between Problem and the body of the environment.


EDIT

Thanks to Philippe Goutet for pointing out that the needspace approach is actually quite flawed; in particular, if the problem environment immediately follows an occurrence of \section{} then it could potentially widow the section heading, and start a new page- very bad! So, he proposed that I copy the definitions of \item and \@item (from ltlists.dtx) into some new commands called \nobreakitem and \@nobreakitem and change the \addpenalty\@itempenalty to \addpenalty\@M.

A complete MWE follows that demonstrates this in action, and in particular, demonstrates that we don't get any lonely orphaned section headings- hoorah!

\documentclass{article}
\usepackage[showframe=true]{geometry}
\usepackage{lipsum}

\makeatletter
% copied from ltlists.dtx
\def\nobreakitem{%
  \@inmatherr\nobreakitem
  \@ifnextchar [\@nobreakitem{\@noitemargtrue \@nobreakitem[\@itemlabel]}}
\def\@nobreakitem[#1]{%
  \if@noparitem
    \@donoparitem
  \else
    \if@inlabel
      \indent \par
    \fi
    \ifhmode
      \unskip\unskip \par
    \fi
    \if@newlist
      \if@nobreak
        \@nbitem
      \else
        \addpenalty\@beginparpenalty
        \addvspace\@topsep
        \addvspace{-\parskip}%
      \fi
    \else
      \addpenalty\@M%only new bit!
      \addvspace\itemsep
    \fi
    \global\@inlabeltrue
  \fi
  \everypar{%
    \@minipagefalse
    \global\@newlistfalse
    \if@inlabel
      \global\@inlabelfalse
      {\setbox\z@\lastbox
       \ifvoid\z@
         \kern-\itemindent
       \fi}%
      \box\@labels
      \penalty\z@
    \fi
    \if@nobreak
      \@nobreakfalse
      \clubpenalty \@M
    \else
      \clubpenalty \@clubpenalty
      \everypar{}%
    \fi}%
  \if@noitemarg
    \@noitemargfalse
    \if@nmbrlist
      \refstepcounter\@listctr
    \fi
  \fi
  \sbox\@tempboxa{\makelabel{#1}}%
  \global\setbox\@labels\hbox{%
    \unhbox\@labels
    \hskip \itemindent
    \hskip -\labelwidth 
    \hskip -\labelsep
    \ifdim \wd\@tempboxa >\labelwidth
      \box\@tempboxa
    \else
      \hbox to\labelwidth {\unhbox\@tempboxa}%
    \fi
    \hskip \labelsep}%
  \ignorespaces}
\makeatother

\newenvironment{problem}{\begin{list}{}{%
            \parsep\parskip%
            \setlength{\itemsep}{-\parsep}%
            }\item {\bfseries Problem}
            \nobreakitem}{\end{list}}

\begin{document}

\lipsum[1]
\vspace{13.55cm} % just to simulate potential page breaks
\section{no page breaks here!}
\begin{problem}
\lipsum[1]

\lipsum[1]
\end{problem}
\end{document}
3
  • Nice write up. I also added a simple example of trivlists above.
    – yannisl
    Commented Mar 11, 2012 at 2:55
  • 3
    @cmhughes: The \needspace may avoid breaks between the two items, but it also introduces an unwanted break point at the start of the environment so if you use {problem} just after a \section{...} you can have your section title at the bottom of the page and your problem beginning on the top of the following page. To avoid this, you need to copy the definition of \item and \@item and make new commands \nobreakitem and \@nobreakitem in which you change \addpenalty\@itempenalty to \addpenalty\@M and then use \nobreakitem for your second \item (without the \needspace). Commented Mar 11, 2012 at 7:48
  • This tutorial was very helpful. Good work!
    – Sveinung
    Commented Mar 18, 2012 at 10:58

You must log in to answer this question.

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