Работа в системе LaTeX

Модификация стандартных классов

Разбить на страницы
Показывать лекцию целиком

Мне кажется, гиппопотама

Зовут так длинно для того,

Чтоб сторож из глубокой ямы

Пореже вызывал его.

С.Я.Маршак

Эта лекция предназначена для тех, кого не удовлетворяет оформление, предлагаемое стандартными классами LaTeX'а. Возможно, вам даже захочется создать свой собственный класс документов вместо стандартных article, proc, report или book. Задача эта выполнимая, но для этого надо в деталях знать, во-первых, книгу [2], а во-вторых — исходные тексты LaTeX'а (они доступны). У читателя настоящей книги таких познаний не предполагается, так что мы предлагаем нечто более скромное: научиться модифицировать оформление одного конкретного документа.

Прежде чем двигаться дальше — два предупреждения. В этой лекции мы расскажем вам, как можно довольно сильно изменить стандартное LaTeX'овское оформление: вы научитесь менять по своему усмотрению шрифты в заголовках, интервалы, отделяющие заголовки от текста, и много других подобных вещей. Но вот первое предупреждение: если вы не являетесь профессиональным полиграфистом, применяйте эти познания с осторожностью. Не пытайтесь менять сразу много разных элементов оформления или резко изменять какие-то параметры: лучше осторожно менять только то, что вам действительно нужно. Учтите: когда дилетант берется за оформление книги, в девяти случаях из десяти результат бывает достоин сожаления.

Второе предупреждение: стиль оформления записан в специальных " стилевых" или "классовых" файлах, входящих в комплект поставки LaTeX'а. Ни в коем случае не меняйте ничего в этих файлах: все изменения в стиле оформления надо записывать в собственном стилевом пакете, как объяснено ниже.

С чего начать

Кое-какие изменения в оформлении документа вы делать уже умеете: например, в лекции 4 рассказывалось, как можно, присвоив в преамбуле новые значения нескольким параметрам, изменить размер полей или текста. Однако для более серьезной модификации оформления приходится иметь дело со специальными командами LaTeX'а, содержащими в своем имени символ @. Поскольку @ — не буква, просто так до этих команд не добратьсяЕсли просто написать \@addtoreset (скоро вы узнаете, что это значит), то TeX воспримет это как команду \@ (имя — из одной не-буквы!), за которой следует текст addtoreset.. Поэтому действовать нужно следующим образом.

Если вы хотите серьезно менять стандартное оформление, нужно создать свой собственный стилевой пакет. Пусть вы решили, что он будет называться {mystyle}. Тогда надо создать файл под названием mystyle.sty и начать документ так (подразумевается, что вы хотите печатать шрифтом кегля 11 и отталкиваетесь от класса book; в других случаях — c очевидными изменениями):

\documentclass[11pt]{book}
\usepackage{mystyle}

После \usepackage можно писать сразу \begin{document}; все установки параметров, определения макросов, и т.п. лучше делать уже не в преамбуле, а непосредественно в файле mystyle.sty (чтобы не запутаться, устанавливая один и тот же параметр по-разному в двух разных местах).

Для оформления документа вам, скорее всего, понадобятся какие-нибудь уже существующие стилевые пакеты (если в тексте много формул, то вы захотите подключить пакет {amsmath}, если есть таблицы, то пакет {array},...). Начать свой личный стилевой пакет надо с того, что подключить эти пакеты. При этом нужно использовать команду \RequirePackage (вместо знакомой вам \usepackage ), например, так:

\RequirePackage{array,longtable}
\RequirePackage[noamsfonts]{amsmath}

(необязательный аргумент команды \RequirePackage означает то же самое и используется так же, как у команды \usepackage ).

На крайний случай, если вам понадобилось использовать команду с символом @ в имени не в стилевом пакете, а прямо в тексте документа, предусмотрены команды \makeatletter и \makeatother. Первая из них делает @ буквой, а вторая восстанавливает status quo. Если вы использовали в тексте \makeatletter, не забудьте написать и \makeatother сразу после текста, в котором использовалась @ в имени команд.

Итак, стандартные стилевые пакеты загружены. После этого надо записать в свой стилевой пакет ваши личные команды для модификации оформления. Начнем.

Снова о счетчиках

Для начала расскажем о некоторых манипуляциях со счетчиками, которые иногда бывают полезны. До сих пор мы обходили их молчанием, поскольку команды, используемые для этих манипуляций, содержат @ в своих именах.

Как подчинить один счетчик другому

Первый из приемов, о которых пойдет речь, связан с отношением подчинения между счетчиками. Мы знаем, что при создании счетчика с помощью команды \newcounter можно задать и счетчик, которому он будет "подчинен". Но как быть, если уже существует никому не подчиненный счетчик, а мы хотим его кому-то подчинить? Например, за нумерацию сносок отвечает счетчик footnote ; в стиле article этот счетчик определяется как никому не подчиненный, благодаря чему нумерация сносок выходит сплошной в пределах всего документа. Если мы хотим, чтоб нумерация сносок начиналась заново в каждом разделе, то можно в стилевом пакете написать так:

\@addtoreset{footnote}{section}

Первый аргумент команды \@addtoreset — имя подчиняемого счетчика, второй — имя подчиняющего.

Разумеется, для того чтобы осмысленно применять описанную команду, надо знать, какие счетчики определены в стандартных стилях и кому они подчинены (или не подчинены). Эта информация содержится в конце раздела.

При ознакомлении с командой \@addtoreset может возникнуть искушение написать

\@addtoreset{footnote}{page}

чтобы сноски нумеровались заново на каждой странице. К сожалению, по TeXническим причинам это может не дать желаемого результата: если сноски оказываются на нескольких страницах подряд, то может случиться так, что на второй из этих страниц нумерация сносок начнется не с $$1$$.

Типичный случай использования команды \@addtoreset возникает, если класс документа — article. В этом случае часто пишут

\@addtoreset{equation}{section}

чтобы нумерация уравнений была не сплошной, как предусмотрено стандартом, а начиналась заново в каждом разделе. Разумеется, в этом случае надо будет переопределить команду \theequation.

Если вы подключили пакет {amsmath}, то эту операцию можно осуществить и попросту в преамбуле документа: команда \numberwithin, принимающая в точности те же аргументы, что и \@addtoreset, осуществляет подчинение счетчика и к тому же переопределяет соответствующим образом the-команду.

Ссылочный префикс

Вторая тонкость, о которой пойдет речь, связана с автоматическими ссылками и the-командами. Предположим, что перед исполнением команды \label{metka} последним счетчиком, подвергшимся увеличению с помощью \refstepcounter, был abcd. В лекции 7 мы говорили, что при этом команда \ref{metka} представит на печати значение этого счетчика "в соответствии с командой \theabcd ". Настало время сознаться, что это полуправда. На самом деле команда \ref напечатает перед \theabcd еще и так называемый "ссылочный префикс" счетчика. Содержимое ссылочного префикса к счетчику abcd записано в команде \p@abcd (буква p, конечно, латинская). В момент создания счетчика эта команда определяется как макрос с "пустым" замещающим текстом, так что у таких счетчиков, как chapter или section в стандартных классах, ее следов не видно. Можно, однако, переопределить эту команду, чтобы ссылочный префикс реально печатался. Вот пример работы со ссылочным префиксом.

В классе book вид номера главы и номера раздела определяется следующим образом: команда \thechapter определена стандартным образом как \arabic{chapter} (такое определение, как мы помним, автоматически производится при создании счетчика), а внешний вид номера раздела определен как

\renewcommand{\thesection}{\thechapter.\arabic{section}}

Из-за этого номер третьего раздела второй главы печатается в заголовке как 2.3. Пусть мы хотим, чтобы номера разделов в заголовках не содержали номера главы; тогда можно написать

\renewcommand{\thesection}{\arabic{section}}

но при этом возникнет другая неприятность. Автоматические ссылки на номер раздела, генерируемые командой \ref, теперь дадут на печати одно и то же число 3 как для третьего раздела второй главы, так и для третьего раздела четвертой главы: ведь из команды \thesection информация о номере главы ушла! Чтобы справиться с этой неприятностью, поместим утерянную информацию в ссылочный префикс счетчика section:

\renewcommand{\p@section}{\thechapter.}

Теперь будет печататься 2.3 при ссылке на третий раздел второй главы и 4.3 при ссылке на третий раздел четвертой главы: хотя \thesection в обоих случаях дает просто 3, печатающийся перед ним \p@section обеспечивает печать номера главы и точки. Кстати говоря, именно такой прием применен при подготовке книги, которую вы читаете.

Русский аналог \alph

В лекции 7 мы отмечали, что было бы желательно иметь команду, аналогичную \alph или \Alph, печатающую русскую букву с номером, равным значению счетчика. Сейчас мы расскажем, как вы ее можете определить в своем стилевом пакете. К сожалению, в этом определении используются не рассматривавшиеся нами средства TeX'а, так что рецепт вам придется воспринять сугубо догматически.

Итак, пусть вам нужна команда \ralph, принимающая в качестве аргумента имя счетчика и дающая на печати русскую букву, чей номер в алфавите совпадает со значением счетчика; если этот номер неположителен или превышает число букв в алфавите, команда будет (как и команда \alph в аналогичном случае) выдавать сообщение об ошибке. Определить эту команду (в вашем стилевом пакете) можно так:

\newcommand*{\ralph}[1]{\@ralph{\@nameuse{c@#1}}}
\newcommand*{\@ralph}[1]%
{\ifcase #1\or а\or б\or в\or г\or д\or е\or ж\or з\or и\or
к\or л\or м\or н\or о\or п\or р\or с\or т\or у\or
ф\or х\or ц\or ч\or ш\or щ\or э\or ю\or
я\else\@ctrerr \fi}

(как иногда делают, мы пропускаем буквы ё, й, ъ, ы, ь). Аналогичным образом можно определить команду \Ralph, печатающую прописную букву (в этом случае "вспомогательную команду" с символом @ в имени надо тоже назвать как-нибудь по-другому, скажем, \@Ralph ). Если вы будете модифицировать это определение, не сделайте в нем пробела между буквой и \or или \else (конец строки — это тоже пробел), иначе ваша команда будет печатать лишний пробел.

Кто кому подчинен в стандарте

Нам осталось выполнить свое обещание и рассказать, какие счетчики определены в LaTeX'овском стандарте и каковы отношения подчинения между ними.

В классах article и proc счетчик section определен как

\newcounter{section}

в то время как в классах report и book, в которых существуют еще и главы, определяется никому не подчиненный счетчик chapter для глав, а счетчик section определяется как подчиненный счетчику chapter:

\newcounter{chapter}
\newcounter{section}[chapter]

Остальные счетчики номеров разделов определяются во всех четырех стандартных классах одинаково:

\newcounter{part}
\newcounter{subsection}[section]
\newcounter{subsubsection}[subsection]
\newcounter{paragraph}[subsubsection]
\newcounter{subparagraph}[paragraph]

Соответствующие этим счетчикам the-команды определены в классах article и proc так:

\renewcommand{\thepart}{\Roman{part}}
\renewcommand{\thesection}{\arabic{section}}
\renewcommand{\thesubsection}{\thesection.\arabic{subsection}}
\renewcommand{\thesubsubsection}%
{\thesubsection.\arabic{subsubsection}}
\renewcommand{\theparagraph}%
{\thesubsubsection.\arabic{paragraph}}
\renewcommand{\thesubparagraph}%
{\theparagraph.\arabic{subparagraph}}

(мы пишем \renewcommand, поскольку все эти the-команды уже получили какое-то определение при создании счетчиков).

В классах report и book, кроме того, определена the-команда для счетчика chapter и по-другому определена \thesection:

\renewcommand{\thechapter}{\arabic{chapter}}
\renewcommand{\thesection}%
{\thechapter.\arabic{section}}

За нумерацию сносок отвечает счетчик footnote. В классах article } и proc этот счетчик определяется как никому не подчиненный:

\newcounter{footnote}

В классах же report и book этот счетчик подчинен счетчику chapter, так как в них присутствует еще и команда

\@addtoreset{footnote}{chapter}

В таком же положении, как счетчик footnote, находится и отвечающий за нумерацию формул счетчик equation: в классах article и proc он определен как никому не подчиненный, а в классах report и book он подчинен счетчику chapter. Однако же в классах report и book переопределяется \theequation:

\renewcommand{\theequation}{\thechapter.\arabic{equation}}

Наконец, счетчики figure и table, отвечающие за нумерацию плавающих иллюстраций и таблиц соответственно, устроены точно так же, как счетчик equation: в классах article и proc они никому не подчинены, а в двух других стандартных классах они подчинены счетчику chapter и соответствующие the-команды определены как

\renewcommand{\thefigure}%
{\thechapter.\arabic{figure}}

(аналогично для table).

Остались еще счетчики, связанные с нумерованными перечнями. Как объяснялось в лекции 7, эти счетчики, в зависимости от уровня вложенности enumerate, называются enumi, enumii, enumiii и enumiv. Все эти счетчики, естественно, последовательно подчинены друг другу, а их ссылочные префиксы определены так (это — единственный случай, когда в стандарте используются нетривиальные ссылочные префиксы):

\renewcommand{\p@enumii}{\theenumi}
\renewcommand{\p@enumiii}{\theenumi(\theenumii)}
\renewcommand{\p@enumiv}{\p@enumiii\theenumiii}

Рубрикация

Здесь мы расскажем о том, как менять оформление разделов документа, предписываемое LaTeX'овским стандартом.

Что нумеровать и что включать в оглавление

Будет ли раздел документа иметь номер, зависит от двух вещей: "уровня вложенности" раздела и значения счетчика secnumdepth. Раздел документа получает номер, если уровень его вложенности меньше или равен значению secnumdepth (разумеется, все сказанное относится к случаю, когда LaTeX'овская команда для раздела документа дана без звездочки — иначе нумерации не будет заведомо). Уровни вложенности в стандартных стилях приведены в табл. 9.1

Уровни вложенности разделов документа
Название разделаУровень
\section 1
\subsection 2
\subsubsection 3
\paragraph 4
\subparagraph 5

Стало быть, если мы хотим, чтобы самый мелкий из нумеруемых разделов был \subsection, то надо написать в преамбуле документа команду

\setcounter{secnumdepth}{2}

Что касается команд \chapter и \part, то соответствующие разделы документа будут нумероваться тогда и только тогда, когда значение secnumdepth является неотрицательным числом.

Какие разделы включать в оглавление, определяется другим счетчиком, а именно tocdepth: информация о разделе документа вносится в оглавление в том и только том случае, если уровень вложенности раздела меньше или равен значения этого счетчика (и раздел вводится командой без звездочки).

Модификация команд, задающих разделы

Теперь рассмотрим, что надо делать, чтобы более серьезным образом изменить оформление разделов. Для этого надо переопределить команды \section, \subsection и т.п., а чтобы научиться их должным образом переопределять, надо узнать, как эти команды определены в стандартных LaTeX'овских классах.

Почти все команды для создания разделов документа определяются в классовых файлах через команду \@startsection. Например, команда \section определяется (не буквально, а по существу) так:

\newcommand{\section}{\@startsection{section}{1}{0pt}%
{-3.5ex plus -1ex minus -.2ex}{2.3ex plus.2ex}%
{\normalfont\Large\bfseries}}

В этом определении у команды \@startsection указаны шесть аргументов, в которых закодированы различные параметры оформления раздела. Разберем последовательно, что эти аргументы означают.

Первый из аргументов (в нашем случае section) — это " внутреннее имя", под которым LaTeX будет узнавать определяемый тип разделов документа. Если вы решили использовать команду \@startsection с "нестандартным" первым аргументом (скажем, abcd), то заодно придется определить счетчик с именем abcd, который будет отвечать за нумерацию разделов, а также команду \l@abcd, которая будет отвечать за сбор материала для оглавления, и команду \abcdmark, отвечающую за передачу информации для колонтитулов,так что без надобности командой \@startsection с нестандартным первым аргументом лучше не пользоваться.

Второй аргумент (в нашем случае 1) — это тот самый " уровень вложенности" раздела, о котором шла речь выше.

Третий аргумент задает отступ заголовка от левого поля (в нашем случае этот отступ равен нулю).

Четвертый аргумент команды \@startsection (в нашем случае это -3.5ex plus -1ex minus -.2ex) задает величину вертикального отступа, оставляемого перед заголовком. Точнее говоря, вертикальному отступу равен не сам четвертый аргумент, а его абсолютная величина (при определении отступа знаки - отбрасываются), а знак - означает, что первый абзац нашего раздела будет печататься без абзацного отступа, как и оформляются разделы в стандартных LaTeX'овских стилях. Если задать эти расстояния как положительные числа, то абзацный отступ в первом абзаце подавляться не будет. Тот факт, что отступ перед началом раздела имеет plus- и minus-компоненты, означает, как водится, что этот пробел обладает растяжимостью и сжимаемостью.

Пятый аргумент (в нашем случае 2.3ex plus .2ex) задает величину вертикального отступа после заголовка раздела, а тот факт, что он положителен, означает, что заголовок раздела печатается на отдельной строке (или строках, если в строку он не умещается). Если он будет отрицательным, то заголовок раздела будет печататься не на отдельной строке, а в подбор; значение пятого аргумента \@startsection будет означать при этом (после отбрасывания знака минус, естественно) величину дополнительного горизонтального отступа между заголовком раздела и продолжающим его текстом из первого абзаца раздела.

Пятый аргумент \@startsection тоже, как видите, может содержать plus- и/или minus-компоненту.

Наконец, шестой аргумент команды \@startsection задает стиль оформления заголовка. Точнее говоря, в этом аргументе записан текст и/или команды, которые будут вставлены перед заголовком раздела. В нашем случае этот аргумент содержит только команды

\normalfont\Large\bfseries

задающие шрифт, которым заголовок будет напечатан (на последующий текст эта смена шрифта не повлияет, поскольку команды, указанные в шестом аргументе \@startsection, будут выполняться внутри группы).

Приведем пример того, как можно изменить стандартное оформление. Пусть нам хочется, чтобы команда \section порождала раздел документа, оформленный таким образом:

  • номера разделов печатаются римскими цифрами;
  • перед номером раздела стоит знак $$\S$$ ;
  • номер раздела и его заглавие печатаются прямым светлым шрифтом размера \Large ;
  • абзацный отступ в первом абзаце не подавляется.
  • Как этого добиться? Для начала переопределим команду \thesection, определяющую, в каком виде будет представлен на печати номер раздела:

    \renewcommand{\thesection}{\Roman{section}}

    А теперь переопределим и саму команду \section следующим образом:

    \renewcommand{\section}{\@startsection{section}{1}%
    {\parindent}{3.5ex plus 1ex minus .2ex}%
    {2.3ex plus.2ex}{\normalfont\Large\S}}

    Мы воспользовались \renewcommand, поскольку команда \section ранее уже была определена. В четвертом аргументе мы убрали знаки -, чтобы не подавлять абзацный отступ, а в третьем — задали отступ заголовка от левого поля, равный абзацному отступу (причина этого не программистская, а эстетическая: некрасиво, когда первый абзац раздела идет с отступом, а заголовок начинается вплотную к левому полю). Прочие параметры, задающие размеры отступов, мы оставили такими же, как в стандартной LaTeX'овской команде: они достаточно разумны, и незачем их трогать, если на то нет особых причин.

    Как видите, для того, чтобы модифицировать оформление разделов, надо знать размеры стандартных LaTeX'овских параметров оформления, наподобие отступа перед или после заголовком. Для команды \section

    Стандартное оформление разделов
    Отступ ПередПосле
    \subsection 0pt -3.25ex plus -1ex minus-.2ex 1.5ex plus.2ex
    \subsubsection 0pt -3.25ex plus -1ex minus-.2ex 1.5ex plus.2ex
    \paragraph 0pt 3.25ex plus 1ex minus.2ex -1em
    \subparagraph \parindent 3.25ex plus 1ex minus.2ex -1em

    мы привели их выше, а для остальных стандартных команд рубрикации они собраны в табл.9.2. В ней " отступ" означает отступ заголовка от левого поля, "перед" — отступ перед заголовком (если этот отступ отрицательный, то абзацный отступ в первом абзаце будет подавлен), "после" — отступ после заголовка (если это отрицательное число, то заголовок печатается в подбор). Уровни вложенности разделов см. в табл. 9.1 , а что до "внутреннего имени" раздела (первый аргумент команды \@startsection ), то оно у всех стандартных команд рубрикации совпадает с их именем section для команды \section и т.п.). Шестой аргумент команды \@startsection содержит в стандартных определениях только команды переключения шрифта; при необходимости заинтересованный читатель воспроизведет его самостоятельно.

    Шестой аргумент команды \@startsection позволяет автоматически добавлять текст перед номером раздела. К сожалению, не так простоНо возможно: это сделано, например, в пакете {russcorr}, использованном при подготовке данной книги. См. приложения E и Ж. заставить LaTeX автоматически добавлять текст после номера, хотя такая потребность порой возникает (например, хочется, чтобы в заголовках разделов после номеров стояли точки, чего стандартное LaTeX'овское оформление не предусматривает).

    Можно заставить LaTeX ставить точки после номеров, написав

    \renewcommand{\thesection}{\arabic{section}.}

    но после этого автоматические ссылки на раздел, сгенерированные с помощью команды \ref, также будут заканчиваться точками, что нелепо.

    Оформление глав отличается от оформления остальных разделов тем, что слово "Глава" и номер главы печатаются на отдельной строке. С помощью команды \@startsection определить такой раздел нельзя, поэтому главы определяются в LaTeX'овских классах иначе. Не будем вдаваться в подробности, как именно, а вместо этого рассмотрим единственно важный для нас вопрос: как можно менять оформление глав.

    Большая часть оформления главы задается в определении команды \@makechapterhead, так что для модификации оформления именно ее и надо переопределять. Рассмотрим, как \@makechapterhead определяется в стандарте. Этой команде передается один аргумент — заголовок главы. В переводе с TeX'а на LaTeX определение выглядит так (не забудьте, что #1 — это аргумент, т. е. текст заголовка):

    \newcommand{\@makechapterhead}[1]{% Начало макроопределения
      \vspace*{50 pt}% Пустое место вверху страницы
      {\parindent=0pt
       \raggedright \normalfont\huge\bfseries
       \@chapapp{} % \@chapapp печатает слово "Глава" (см. ниже)
        \thechapter \par % номер главы - в отдельной строке
        \vspace{20 pt} % между словом "Глава" и ее заголовком
        \normalfont\Huge\bfseries #1\par % заголовок главы
        \nopagebreak     % чтоб не оторвать заголовок от текста
        \vspace{40 pt}   % между заголовком и текстом
      }% конец группы.
    }% конец макроопределения

    Разберем эту "программу". Первая команда \vspace* оставляет пустое место вверху страницы (поскольку главы начинаются с новой страницы). Далее печатается слово "Глава", ее номер и заголовок главы; поскольку заголовок может не поместиться в строку, надо предусмотреть, какие будут при этом параметры верстки абзаца. Как видите, устанавливается нулевое значение абзацного отступа и отсутствие выравнивания по правому краю; чтобы такой режим не распространился на дальнейший текст, соответствующие команды даны внутри группы. Внутри этой же группы определен шрифт, которым будет печататься заголовок.

    Команда \@chapapp печатает слово " Chapter", "Глава",... — одним словом, то, как в вашем документе называются главы. Точнее говоря, по умолчанию эта команда работает так же, как \chaptername, а после команды \appendix (если таковая есть в вашем файле) начинает работать как \appendixname. Если в вашем тексте все главы называются одинаково, то при переопределении \@makechapterhead можно не мудрить, а прямо заменить \@chapapp на "Глава". Не забудьте только оставить пробел между этим словом и номером главы (выше это было сделано с помощью обычного трюка с парой фигурных скобок).

    Остальное в приведенном выше определении разъяснений, надо думать, не требует. Скорее всего, вы захотите в этой команде изменить шрифт, которым печатается заголовок главы, или же интервалы, отделяющие заголовок от остального текста. Чтобы изменить вид, в котором представляется на печати номер главы, надо, как водится, переопределить команду \thechapter. Можно при желании задать и какое-нибудь более сложное оформление заголовка с помощью блоков и линеек — все зависит от вашей фантазии и вкуса!

    Надо еще сказать, что мы немного обманули читателя: на самом деле в стандартных классах команда \@makechapterhead определена таким образом, что если значение счетчика secnumdepth отрицательно, то команды, записанные в строках с пятой по седьмую, не исполняются (и номер главы не печатается). В нашем определении эти команды будут исполняться всегда, вне зависимости от значения secnumdepth; если вы переопределяете \@makechapterhead и не хотите, чтобы главы нумеровались, просто удалите соответствующие строки из определения.

    Кроме того, если в классе book вы переопределите \@makechapterhead, отталкиваясь от этого определения, то главы, заданные как \chapter без звездочки, будут нумероваться, невзирая на команды \frontmatter и \backmatter (но вы ведь сможете поставить две-три звездочки самостоятельно?).

    За оформление заголовка главы, определенной командой \chapter со звездочкой, отвечает команда \@makeschapterhead. Ее определение в стандарте аналогично определению \@makechapterhead, с тем отличием, что из него удален фрагмент, отвечающий за печать номера:

    \newcommand{\@makeschapterhead}[1]{%
      \vspace*{50 pt}%
      {\parindent=0pt \raggedright
        \normalfont\Huge\bfseries #1\par
        \nopagebreak
        \vspace{40 pt}}}

    Кроме оформления заголовка, с оформлением глав можно делать еще две вещи. Во-первых, главы начинаются либо просто с новой страницы (как в классе report ), либо с новой нечетной страницы (как в классе book ); чтобы повлиять на этот выбор, не надо ничего делать в личном стилевом пакете, достаточно просто указать классовую опцию openright или openany (в необязательном аргументе команды \documentclass ). Во-вторых, по умолчанию абзацный отступ в первом абзаце главы подавляется; вы можете захотеть сделать так, чтобы он не подавлялся. Чтобы решить эту проблему, надо переопределять уже саму команду \chapter, а для этого надо знать, как она определяется в стандарте. Вот соответствующее определение, опять в переводе на LaTeX с TeX'а, в классе book:

    \newcommand{\chapter}{\cleardoublepage
       \thispagestyle{plain}%
       \global\@topnum=0
       \@afterindentfalse
       \secdef\@chapter\@schapter}

    Разбирать это определение мы не будем, чтобы не запутаться в некоторых слишком хитрых TeX'овских и LaTeX'овских конструкциях, а просто скажем две вещи:

  • чтобы не подавлялся абзацный отступ в первом абзаце главы, замените \@afterindentfalse на \@afterindenttrue ;
  • если вы не хотите, чтобы на странице с заглавием главы печаталась колонцифра (номер страницы), замените аргумент команды \thispagestyle с plain на empty.
  • Что касается команды \part (" часть"), то она отличается тем, что заголовок части занимает отдельную страницу. Если вы решили изменить стандартное оформление таких "частей", то проще всего оформить соответствующие две--три страницы вручную.

    Оглавление, список иллюстраций и прочее

    Автоматическая сборка оглавления — многоэтапный процесс. Сначала материал для оглавления (заглавия разделов и номера соответствующих страниц) записывается в специальный файл с тем же именем, что и у основного файла, и расширением toc (в нормальных условиях эта запись обеспечивается командами \chapter, \section и т.д.); при следующем запуске LaTeX'а этот toc-файл считывается (с помощью команды \input ), команды, записанные в него, исполняются, и в результате происходит фактическая печать оглавления. Аналогичным образом составляются список иллюстраций и список таблиц (при этом информация записывается в файлы с расширениями lof или lot соответственно). Давайте научимся влиять на этот процесс.

    Сначала расскажем, как составлять оглавление полностью вручную, игнорируя его автоматическую сборку, обеспечиваемую командами типа \section. Итак, предположим, что все команды \section, \chapter и т.п. даны в исходном тексте в варианте со звездочкой, и посмотрим, как можно самому создать оглавление.

    Команда \addtocontents служит для записи в toc- (соответственно,lof - или lot-)- файл любого текста и любых TeX'овских команд. У этой команды два обязательных аргумента. Первый из них должен быть toc, lof или lot, в соответствии с тем, в какой из файлов с оглавлениями вы пишете свой текст. Второй аргумент — то, что вы хотите записать в файл. Если, например, вам взбрело в голову внести в оглавление к вашей книге текст "У попа была собака" (не будем спрашивать, зачем), то можете написать

    \addtocontents{toc}{У попа была собака\par}

    ( \par поставить необходимо, так как до и после выполнения каждой команды, записанной в оглавлении, TeX должен находиться в вертикальном режиме). Если после этого запустить LaTeX два раза, то вы увидите в оглавлении свой текст (после первого раза он только попадет в toc-файл, а при втором запуске toc-файл с этим текстом будет обработан).

    С помощью команды \addtocontents можно записывать в оглавление не только всякие глупости. Если, например, вы хотите в каком-то месте оглавления провести горизонтальную линейку шириной во всю страницу, то можно написать

    \addtocontents{toc}{\hrule}

    и в оглавлении появится линейка. Имейте только в виду, что в аргументе \addtocontents необходимо защищать хрупкие команды с помощью команды \protect. В случае с \hrule мы обошлись без \protect, так как эта команда не хрупка, но если есть сомнения, то лучше команду защитить. Напомним, что \protect действует только на непосредственно следующую команду и что команды для смены шрифта или установки пробелов в защите с помощью \protect не нуждаются. Приведем пример более разумного применения \addtocontents, в котором требуется \protect. Пусть вы не хотите, чтобы какая-то из строк в оглавлении начинала новую страницу. Тогда надо перед командой, порождающей эту строку оглавления (обычно таковой будет команда наподобие \section ), написать в своем файле вот что:

    \addtocontents{toc}{\protect\nopagebreak}

    В результате в toc-файл запишется команда \nopagebreak, и нежелательный разрыв страницы в оглавлении будет предотвращен. Если опустить \protect, то получится весьма непонятное сообщение об ошибке.

    При совместном использовании команд \addtocontents возникает следующий неприятный эффект. Пусть ваш файл имеет вид, скажем,

    \documentclass{book}
    \usepackage{mystyle}
    \begin{document}
    \tableofcontents
    \include{ch1}
    \addtocontents{\hrule}
    \include{ch2}
    \end{document}

    Тогда, вопреки всем ожиданиям, в оглавлении линейка окажется не между записями, отвечающими файлам ch1.tex и ch2.tex, а после записей, отвечающих файлу ch2.tex. Чтобы этого избежать, запишите команду \addtocontents в начало файла ch2.tex (самой первой строчкой).

    Чтобы составить полноценное оглавление, надо иметь возможность записать в toc - (соответственно, lof- или lot-) файл не только текст, но и номер той страницы, к которой этот текст относится. Это делается с помощью команды \addcontentsline, имеющей такой синтаксис:

    \addcontentsline{тип\_файла}{тип\_записи}{текст}

    Здесь тип_файла — это toc, lof или lot, текст — тот текст, который будет записан в оглавление (например, команда \section в стандартном стиле article в качестве этого текста передает название раздела и его номер; подробности см. ниже). Наконец, тип_записи определяет, каким образом будет обрабатываться этот текст при чтении файла с оглавлением. Именно, если второй аргумент в команде \addcontentsline был abcd, то, когда при следующем запуске LaTeX'а будет читаться toc- (соответственно, lof- или lot-) файл, будет исполнена команда \l@abcd с двумя аргументами, первый из которых - текст, записанный в третьем аргументе команды \addcontentsline, а второй - номер страницы, на которую попала ваша команда \addcontentsline. Например, если в файле было написано

    \leavevmode
    \hbox to\hsize{\verb"\addcontentsline{toc}{abcd}{О слонах}"\hfill
    $\displaystyle(*)$

    и если эта команда попала на страницу $$95$$, то при следующем запуске LaTeX'а в процессе чтения toc-файла будет исполняться команда

    \l@abcd{О слонах}{95}

    Разумеется, чтобы при этом не получилось сообщения об ошибке, надо, чтобы команда \l@abcd была определена. Стало быть, в стилевом пакете должно присутствовать ее определение. Если мы хотим, чтобы запись $$(*)$$ в исходном файле порождала в оглавлении строку

    О слонах................................ 95

    то в преамбуле надо написать вот что:

    \newcommand{\l@abcd}[2]{\hbox to\textwidth{#1\dotfill #2}}

    Чтобы при этом страница в оглавлении была указана верно, необходимо команду \addcontentsline разместить непосредственно после команды \section* (иначе есть опасность, что они попадут на разные страницы).

    Если в третьем аргументе команды \addcontentsline присутствуют "хрупкие" команды, то их следует, как водится, защитить командой \protect, если, с другой стороны, в нем записана \the -команда, соответствующая какому-то счетчику, то в toc-файл будет записано печатное представление значения этого счетчика по состоянию на тот момент, когда выполнялась \addcontentsline. Таким способом можно, например, записать в оглавление номер текущего раздела документа: достаточно сказать

    \addcontentsline{toc}{abcd}{\thesection. О слонах}

    Теперь рассмотрим, как именно собирают оглавление стандартные команды наподобие \chapter или \section. Делают они это также с помощью \addcontentsline, при этом ее второй аргумент (" тип записи") будет section для команды \section, subsection для команды \subsection, — одним словом, " внутреннее имя", под которым LaTeX знает тип разделов документа (напомним, что внутреннее имя передается в качестве первого аргумента команде \@startsection ). Стало быть, для модификации стиля оформления строк оглавления, соответствующих \section, надо переопределять команду \l@section, для модификации строк оглавления, соответствующих \subsection, надо переопределять \l@subsection и т.д. Чтобы было понятно, как их переопределять, рассмотрим, как они определены в стандарте.

    В классе book команда \l@section определена так:

    \newcommand{\l@section}{\@dottedtocline{1}{1.5em}{2.3em}}

    Смысл трех выражений, стоящих в фигурных скобках после команды \@dottedtocline, таков. Первое выражение — "уровень вложенности" элемента оглавления. Если этот уровень превышает значение счетчика tocdepth, то команда \@dottedtocline ничего в оглавлении не печатает. Второе выражение — отступ строки оглавления от левого поля. Третье выражение определяет, сколько места в строке оглавления TeX отведет на номер раздела. Результат выглядит на печати так: после отступа, указанного во втором выражении, печатается номер раздела, затем, отступя от начала этого номера столько, сколько сказано в третьем выражении, печатается заглавие раздела. Это сделано для того, чтобы заглавия всех разделов печатались в оглавлении одно под другим. После заглавия идут "лидеры" — ряд точек до завершающего строку номера страницы. Если заглавие в строку не укладывается, то оно обычным образом будет перенесено на следующую строку (если есть какие-то неясности, загляните в оглавление к этой книге). Из сказанного следует, что слишком длинный номер раздела может в оглавлении наложиться на заглавие. Средство борьбы с этим — переопределить команду \l@section (или \l@subsection...), увеличив должным образом второй аргумент команды \@dottedtocline.

    Параметры оформления элемента оглавления, задаваемого командами, определенными через \@dottedtocline, можно менять. Именно, размер места, отводимого на номер страницы, задается значением команды \@pnumwidth, которую можно переопределить. В классе book эта команда определена как

    \newcommand{\@pnumwidth}{1.55em}

    и соответственно на номер страницы отводится 1.55em места. Если мы хотим, чтобы на номер страницы отводилось \2em, надо написать

    \renewcommand{\@pnumwidth}{2em}

    Еще одна команда, значение которой отвечает за оформление оглавления, — это \@tocrmarg. Если запись в оглавлении занимает более одной строки, то значение этой команды задает отступ от правого поля, который будет у всех строк, кроме той последней, что завершается номером страницы. Если вы хотите, чтобы размер этого отступа равнялся 3em, напишите так:

    \renewcommand{\@tocrmarg}{3em}

    Хотя \@pnumwidth и \@tocrmarg используются для задания размеров, они не являются параметрами со значением длины; запись наподобие \@tocrmarg=4em приведет к ошибке!

    Наконец, регулировать густоту точек-" лидеров" можно, если переопределить команду \@dotsep. В классе book она определена как

    \newcommand{\@dotsep}{4.5}

    Если вы хотите, чтобы точки шли погуще, попробуйте переопределить ее, заменив 4.5 на число поменьше (число может быть дробным, в нем можно использовать как десятичную запятую, так и десятичную точку):

    \renewcommand{\@dotsep}{3,9}

    Напрашивающаяся запись \@dotsep=3,9 приведет к ошибке.

    Команды \l@subsection и "более мелкие" определяются в классе book так же, как \l@section, отличаются только аргументы команды \@dottedtocline. Мы собрали значения этих параметров в табл. 9.3

    Стандартные определения l@-команд
    Три аргумента \@dottedtocline
    \l@subsection 2 3.8em 3.2em
    \l@subsubsection 3 7.0em 4.1em
    \l@paragraph 4 10em 5em
    \l@subparagraph 5 12em 6em

    Теперь рассмотрим, как в стандарте определяются записи в оглавлении, соответствующие самым крупным разделам ( \chapter в классах book и report, \section в двух других классах). Вот (в адаптированном виде, как водится) определение команды \l@chapter из стандартного класса book. Чтобы было понятно, о чем идет речь, напомним, что в этом определении на место #1 подставляется информация о номере (если главы нумеруются) и названии главы, а на место #2 — номер страницы.

    \newcommand{\l@chapter}[2]%
    {\pagebreak[3]
     \vspace{1em plus 1pt}% отбивка перед строкой оглавления
       \@tempdima=1.5em % место для номера главы
       {% Дальнейшее происходит внутри группы...
         \rightskip=\@pnumwidth % см. ниже
         \parfillskip=-\@pnumwidth
         \noindent\bfseries % Начать абзац, установить шрифт
         \addtolength{\leftskip}{\@tempdima}% см. ниже
         \hspace{-\leftskip}#1\nolinebreak
         \hfil\nolinebreak
         \hbox to \@pnumwidth {\hss #2}\par
         \nopagebreak[3] % лучше бы здесь не рвать страницу...
       }% конец этой группы
    }% конец определения

    Определение, как видите, длинное и сложное, к тому же автору не удалось полностью изгнать из него не упоминавшиеся ранее TeX'овские конструкции. Приведено оно здесь не для того, чтобы вы самостоятельно создавали подобные определения "с нуля", но чтобы вы при необходимости смогли в нем кое-что осторожно изменить. Разберем определение по порядку. В начале встречаются не рассматривавшиеся нами параметры \rightskip и \leftskip. Эти параметры со значением длины (по умолчанию они равны нулю) имеют следующий смысл: все строки абзаца начинаются с отступом \leftskip от левого поля и кончаются с отступом \rightskip от правого поля (если речь идет о последней строке, то в дополнение к отступу \parfillskip ). У нас \rightskip устанавливается равным длине, записанной в определении команды \@pnumwidth (именно столько места будет отведено на номер страницы), а \leftskip устанавливается равным значению переменной \@tempdima, определяющей, сколько места будет отведено на номер главы. С другой стороны, параметр \parfillskip устанавливается равным отрицательной величине - \@pnumwidth. Тем самым, если название главы длинное и не поместится в одну строку оглавления, произойдет следующее: все строки, кроме последней, будут заканчиваться на расстоянии \@pnumwidth от правого края, а последняя строка, содержащая номер страницы, закончится на расстоянии

    \leftskip + \parfillskip =  @pnumwidth - \@pnumwidth =0,

    от края, так что номер страницы будет все-таки прижат вправо.

    Между \@pnumwidth и \@tempdima есть существенная разница. Команда \@pnumwidth всегда определяет только место, отводимое на номер страницы, и эту команду можно переопределять в стилевом пакете. С другой стороны, параметр \@tempdima используется LaTeX'ом для самых разных целей (в основном — для временного хранения различных длин в процессе каких-то вычислений), и он может измениться в процессе выполнения очень многих LaTeX'овских команд, так что присваивать ему какое-то значение в стилевом пакете совершенно бессмысленно — все равно после этого оно сто раз изменится. Как мог заметить читатель, значение этому параметру присваивается в начале исполнения команды \l@chapter, и именно это значение принимается в расчет в дальнейшем. Поэтому, если вы захотите отводить на номер главы, скажем, 2em вместо 1.5em, то вам придется переопределить команду \l@chapter, заменив третью строку на

    \@tempdima=2em

    Нужда в таком переопределении \l@chapter возникает, например, если мы переопределяем команду \thechapter, чтобы номер печатался римскими цифрами (как в книге, которую вы читаете). Далее, #1 - это, как уже было сказано, номер и заглавие главы. Точнее говоря, на месте #1 печатается такой текст (будем считать, что глава называется "Все о слонах"):

    \makebox[\@tempdima][l]{\thechapter}Все о слонах

    Таким образом, величина отступа от левого поля до названия главы всегда равна \@tempdima ; если номер занимает больше места, чем \@tempdima, то он наложится на название.

    Команда \hfil в двенадцатой строке обеспечивает пробел между названием главы и номером страницы. Если вы хотите заполнить этот пробел лидерами, можете в определении \l@chapter заменить \hfil на, скажем,

    \leaders\hbox to .5em{\hss.\hss}\hfil

    (автор не гарантирует, что именно при таком выборе параметров лидеры будут выглядеть красиво).

    Наконец, команды \pagebreak[3] в начале и \nopagebreak[3] в конце играют следующую роль: первая из них призывает LaTeX не печатать, по возможности, строку оглавления, соответствующую главе, внизу страницы, а вторая — не разрывать страницу сразу после строки, посвященной главе (опять же по возможности).

    Имейте также в виду, что мы удалили из нашего упрощенного определения \l@chapter проверку значения счетчика tocdepth, так что если вы в какой-то момент решите не включать главы в оглавление, эту команду надо будет переопределить на "ничего не делать" так:

    \renewcommand{\l@chapter}[2]{}

    Команды, определяющие вид записей в списке иллюстраций (соответствующих плавающим иллюстрациям) и списке таблиц (соответствующих плавающим таблицам) называются \l@figure и \l@table соответственно и определяются в стандарте с помощью \@dottedtocline.

    До сих пор речь шла о сборке материала для оглавления, списка иллюстраций и т.п. Однако же и у самого оглавления есть заголовок, и его оформление тоже можно менять. Чтобы было понятно, как это делать, опишем, как определена команда \tableofcontents стандартное определение} в стандартном стиле article:

    \newcommand{\tableofcontents}%
    {\section*{\contentsname}\@starttoc{toc}}

    Здесь \contentsname — это уже знакомая нам команда, которую при работе с русскими текстами приходится переопределять. Как видите, заголовок оглавления оформляется просто как заголовок ненумерованного раздела. Вы можете вместо этого оформить заголовок, скажем, с помощью \subsection, или еще каким-либо образом. Новой для вас будет команда \@starttoc. У этой команды предусмотрен один обязательный аргумент. Этим аргументом должен быть toc (для оглавления), либо lot или lof (для списка таблиц или иллюстраций соответственно). Команда \@starttoc читает toc- (соответственно, lot- или lof-) файл и создает оглавление как таковое.

    На самом деле в определении \tableofcontents присутствует еще команда, позволяющая задать текст для включения в колонтитулы (вспомним, что \section* сама по себе никакой информации для колонтитулов не дает). Мы не будем здесь вдаваться в скучные подробности. Когда вы научитесь задавать такие команды, вы сможете соответствующим образом переопределить и \tableofcontents.

    Перечни общего вида

    В этом разделе мы завершим рассказ о том, как менять стиль оформления перечней. В лекции 3 мы назвали перечнями окружения {itemize}, {enumerate} и {description} ; помимо этого, к перечням в LaTeX'овском смысле относятся {flushleft}, {flushright}, {center}, {quote}, {quotation}, {verse}, а также окружения, создаваемые с помощью \newtheorem ; как мы увидим в лекции 5, все эти окружения — частные случаи одной LaTeX'овской конструкции. Поэтому многие параметры оформления этих окружений устанавливаются и модифицируются по единой схеме.

    Отбивки в перечнях

    Начнем с важного предупреждения. Чтобы изменить отбивки, с помощью которых оформляются перечни, необходимо, естественно, изменить значение каких-то из перечисляемых в этом разделе параметров. Однако же, если попросту присвоить этим параметрам новые значения в преамбуле или в стилевом пакете, то в большинстве случаев действия это не возымеет. Средства, которые надо применить, чтобы эти изменения подействовали, описаны в следующем подразделе.

    Теперь договоримся о терминологии. Каждый перечень LaTeX рассматривает как состоящий из элементов (каждый элемент вводится, как мы помним, командой \item ). В свою очередь, каждый элемент перечня может состоять из одного или нескольких абзацев. Наконец, у каждого элемента перечня есть свой заголовок — " горошина" на первом уровне окружения {itemize}, заданный вами заголовок в окружении {description} и т.п. (У некоторых перечней — например, таковы "теоремы" — перечень состоит из одного-единственного элемента; у таких перечней, как {quote} или {verse}, кроме того, заголовок к этому единственному элементу всегда пуст.)

    Вооружившись этими терминами и имея в виду предупреждение, приступим к утомительному перечислению параметров. Все они — параметры со значением длины. Во-первых, параметры \leftmargin и \rightmargin задают, с каким отступом от левого (правого) поля начинается (заканчивается) текст элементов перечня (полиграфист сказал бы: насколько втянуты элементы перечня). Если перечень вложен в другой перечень, то \leftmargin и \rightmargin обозначают величину втяжки по отношению к объемлющему перечню.

    Следующие два параметра влияют на размещение заголовков в перечне. Параметр \labelsep задает расстояние между правым краем заголовка и началом текста в элементе перечня, к которому относится этот заголовок, а параметр \labelwidth задает место по горизонтали, которое по умолчанию занимает заголовок. Точный смысл этих параметров следующий. При обработке перечня LaTeX сначала пытается поместить заголовок в блок шириной \labelwidth. Если места хватает, то именно в такой блок он и помещается, причем выключенным вправо: правый край блока при этом находится на расстоянии \labelsep от начала текста, составляющего элемент перечня (так что его левый край будет на расстоянии

    \leftmargin - \labelwidth - \labelsep

    от левой границы основного текста или объемлющего перечня). Если же ширина заголовка больше, чем \labelwidth, то заголовок печатается как есть. Такое, например, регулярно случается при пользовании окружением {description}.

    Мы не сказали еще об одном параметре, влияющем на размещение заголовков. Именно, если параметр \itemindent отличен от нуля, то каждый заголовок перечня будет дополнительно сдвинут на это расстояние вправо. Соответственно, при определении, на каком расстоянии начинается заголовок элемента перечня, надо будет прибавить значение \itemindent к тому, что получается по формуле $$(*)$$. По умолчанию значение этого параметра равно нулю.

    Если элемент перечня состоит из нескольких абзацев, то по умолчанию во всех этих абзацах абзацный отступ будет отсутствовать. Можно, однако, при желании задать такой режим, что во всех, кроме первого, абзацах каждого элемента перечня будет присутствовать абзацный отступ. Для этого надо задать ненулевую величину этого отступа в параметре \listparindent. Кстати, значение этого параметра может быть и отрицательным (в этом случае эффект будет похож на тот, что достигается в обычном тексте установкой параметров \hangindent и \hangafter ).

    Параметры, о которых шла речь до сих пор, относились к размещению материала по горизонтали. Теперь займемся "вертикальными" параметрами. Сразу отметим, что все эти параметры являются " растяжимыми" длинами, т.е. у них можно задавать plus- и minus -компоненты.

    Первый (и основной) из этих параметров называется \topsep. Это величина дополнительного вертикального интервала, который делается перед перечнем и после него (в дополнение к \parskip ).

    Если перед перечнем оставлена пустая строка (или имеется команда \par ), то перед и после перечня устанавливается еще и вертикальный отступ, равный \partopsep (в дополнение к отступам, заданным параметрами \parskip и \topsep ).

    Далее, вертикальный отступ между абзацами внутри одного элемента задается параметром \parsep (а не \parskip, как в обычном тексте). Между различными же элементами перечня, в дополнение к \parsep, оставляется еще и вертикальный отступ \itemsep. Таким образом, если \itemsep отличен от нуля, как это и сделано в стандартных классах, то различные элементы перечня будут более отделены друг от друга, чем абзацы внутри одного элемента перечня.

    Изменение отбивок в перечнях

    Теперь настало время объяснить, как именно можно менять вышеописанные параметры. При "входе" в перечень LaTeX в первую очередь вычисляет уровень вложенности перечней: если перечень не вложен ни в какой другой, то этот уровень равен 1, для перечня, вложенного в перечень, уровень равен 2 и т. д. После этого исполняется команда \@listI, если уровень равен 1, \@listii, если уровень равен 2, и т.д.: имя команды — слово @list, к которому добавлен уровень вложенности, записанный римскими цифрами (если уровень вложенности равен 1, то римская цифра записывается прописной буквой I, в остальных случаях римские цифры записываются строчными латинскими буквами). В стандартных классах команды \@listI, \@listii и т.п. определены таким образом, что они в момент входа в перечень устанавливают значение параметров оформления перечня на соответствующем уровне. Именно поэтому переустановка (некоторых из) параметров перечня в стилевом пакете может ничего не дать.

    Итак, чтобы менять отбивки в перечнях, надо переопределять команды \@listI, \@listii, ..., \@listvi. Видимо, самое практичное — переопределить в своем стилевом пакете команды \@listI, \@listii, ..., \@listvi (или не все из них — в зависимости от того, какова реальная максимальная глубина вложенности перечней в вашем документе), присвоив всем перечисленным в предыдущем разделе десяти параметрам явные значения. Например, можно написать что-нибудь в таком роде:

    \renewcommand{\@listI}{%
    \leftmargin=25pt
    \rightmargin=0pt
    \labelsep=5pt
    \labelwidth=20pt
    \itemindent=0pt
    \listparindent=0pt
    \topsep=8pt plus 2pt minus 4pt
    \partopsep=2pt plus 1pt minus 1pt
    \parsep=0pt plus 1pt
    \itemsep=\parsep}

    Здесь всем параметрам оставлены стандартные значения, за исключением \parsep и \itemsep: в отличие от положительных значений, задаваемых в стандарте, мы устанавливаем их такими же, как обычная вертикальная отбивка между абзацами (как вы помните, она обозначается \parskip и обладает нулевым естественным размером и растяжимостью 1pt). На взгляд автора, такие перечни смотрятся лучше.

    Если какой-то из параметров (например, \labelsep ) одинаков в перечнях всех уровней, то достаточно прописать его установку только в определении \@listI: при входе в перечень верхнего уровня этот параметр будет установлен командой \@listI, и LaTeX будет его помнить, пока не выйдет из " наружного" перечня.

    Окружения list и trivlist

    Все LaTeX'овские перечни являются на самом деле частными случаями одной общей конструкции — окружения list. Рассмотрим, как это окружение работает.

    Окружение list имеет два обязательных аргумента. Общий вид этого окружения в исходном тексте будет такой:

    \begin{list}{заголовок\_по\_умолчанию}{команды}
    ...
    \end{list}

    Аргументы окружения list означают следующее. "Заголовок по умолчанию" — это заголовок элемента перечня, печатающийся в том случае, когда этот элемент перечня вводится командой \item без аргумента. Пример:

    $$\begin{list}{И какой-то}{ \leftmargin=20pt \rightmargin=40pt \labelsep=5pt \labelwidth=0pt \itemindent=0pt %\listparindent=0pt \topsep=8pt plus 2pt minus 4pt \partopsep=2pt plus 1pt minus 1pt %\parsep=0pt plus 1pt \itemsep=\parsep %\itemsep=0pt } \item малыш пока\-зал ему шиш. \item бар\-бос укусил его в нос. Нехороший бар\-бос, невоспитанный! \end{list}$$
    \begin{list}{И какой-то}{}
    \item малыш показал ему шиш.
    \item барбос укусил его в нос.
    Нехороший барбос, 
    невоспитанный!
    \end{list}

    Аргумент команды окружения list содержит те команды, которые будут исполнены после входа в перечень. Поэтому в нем можно задать команды, присваивающие новые значения параметрам оформления перечня (в частности, отбивкам, описанным в лекции 5: эти команды будут выполнены после команды \@list..., выполняющейся при входе в перечень). Кроме этого, во втором аргументе окружения list можно поместить команду \usecounter. Эта последняя требует одного обязательного аргумента — имени счетчика (счетчик должен быть определен). Если \usecounter присутствует во втором аргументе окружения list, то при входе в окружение значение счетчика, являющегося аргументом \usecounter, будет установлено в нуль, а каждая команда \item без аргумента будет увеличивать его на единицу с помощью \refstepcounter (так что на значения этого счетчика можно будет ссылаться с помощью \label и \ref ). Вот пример c \usecounter (подразумевается, что у нас определен счетчик tmp):

    $$Вот как выглядят первые буквы латинского алфавита: \begin{list}{\Alph{tmp}:}% {\usecounter{tmp}} \item Выглядит так же, как соответствующая русская буква, и читается так же. \item Читается не так, как похожая на нее русская буква. \item И с ней та же история. \end{list}$$
    Вот как выглядят первые 
    буквы латинского алфавита:
    \begin{list}{\Alph{tmp}:}%
    {\usecounter{tmp}}
    \item Выглядит так же, как
    соответствующая русская
    буква, и читается так же.
    \item Читается не так,
    как похожая на нее
    русская буква.
    \item И с ней та же 
    история. \end{list}

    Чтобы заголовки элементов перечня выравнивались по левому краю, а не по правому, можно завершить "заголовок по умолчанию" командой \hfill ; чтобы по левому краю выравнивались заголовки, заданные в явном виде в необязательном аргументе команд \item, нужно завершить командой \hfill этот необязательный аргумент.

    Окружением list разумно пользоваться не непосредственно, как в приведенных примерах, а для определения нового окружения с помощью \newenvironment. Вот, например, как в стандарте определяется окружение {quote}:

    \newenvironment{\quote}%
    {\begin{list}{}{\rightmargin=\leftmargin}\item[]}}%
    {\end{list}}

    Команда \item с пустым аргументом необходима, поскольку до команды \item в перечне не должно быть никакого текста.

    Наряду с окружением list в LaTeX'е определен его важный частный случай — окружение trivlist. Его отличия от list таковы:

  • это окружение не требует аргументов (так же, как и все окружения для создания перечней, с которыми мы имели дело раньше);
  • \leftmargin, \labelwidth и \itemindent для него всегда равны нулю (стало быть, текст печатается без втяжки); \parsep равно \parskip ;
  • команда \item, употребленная внутри этого окружения, обязана иметь аргумент (хотя бы пустой).
  • Как видите, многие возможности перечней в этом окружении не работают, но сохраняются такие важные черты, как \topsep (дополнительный интервал перед и после) плюс обычное свойство первой строки после перечня: она делается без абзацного отступа тогда и только тогда, когда после окружения в исходном тексте не оставлено пустой строки. Окружение trivlist также применяют обычно не само по себе, а для определения новых окружений; при этом в "открывающие команды" \newenvironment добавляют команду \item[], а внутри окружения \item вообще не используют. Иногда используют и \item с аргументом (пример тому вы увидите ниже, в лекции 8).

    Окружения list можно вкладывать друг в друга; максимальная глубина вложенности равна шести. В окружениях наподобие {itemize} предусмотрен "ограничитель", снижающий эту макимальную глубину до четырех. В личном стилевом файле, не рассчитанном на общее пользование, предусматривать такой ограничитель большого смысла нет: просто следите за тем, чтобы не вкладывать слишком много list'ов друг в друга.

    Колонтитулы

    Страницу документа, подготовленного с помощью LaTeX'а, можно рассматривать как состоящую из трех частей: тела страницы, верхнего колонтитула и нижнего колонтитулаЭта терминология не совпадает с традиционной, но удобна для наших целей... Мы знаем, что с помощью команды \pagestyle на оформление колонтитулов можно в какой-то мере влиять. Возможностей для этого, однако же, не слишком много. Сейчас мы увидим, как можно радикально менять вид колонтитулов.

    За оформление верхних колонтитулов отвечают команды \@oddhead и \@evenhead. Точнее говоря, если стиль оформления документа "двусторонний", то команда \@oddhead задает верхний колонтитул на страницах с нечетными номерами, а команда \@evenhead — на страницах с четными номерами. Если же стиль оформления документа " односторонний", то \@oddhead задает все верхние колонтитулы, а команда \@evenhead на оформление документа вообще не влияет. Аналогично обстоит дело с \@oddfoot и \@evenfoot, отвечающими за нижние колонтитулы. Все четыре названные команды получают некоторое определение в LaTeX'овском стандарте, так что переопределять их надо с помощью \renewcommand.

    Теперь обсудим, как вышеназванные команды влияют на оформление колонтитулов. Основной принцип таков. При оформлении страницы верхний колонтитул получается в результате исполнения команды

    \hbox to\textwidth{\@evenhead}

    (мы предположили, что стиль двусторонний и страница четная; в других случаях — с очевидными изменениями). Можно сказать, что в каждой из команд \@evenhead и ей подобных записан текст и TeX'овские команды, которые при верстке страницы будут подставлены в \hbox to \textwidth.

    Пусть, например, мы готовим к изданию роман Л.Н.Толстого " Война и мир"; стиль документа выберем двусторонний. Предположим, что мы выбрали такое оформление:

  • на левой странице разворота в верхнем колонтитуле написано имя автора, прижатое (выключенное) вправо;
  • на правой странице разворота в верхнем колонтитуле написано название романа, прижатое (выключенное) влево;
  • В нижних колонтитулах по центру расположен номер страницы, окруженный тире.
  • Тогда надо переопределить команды для колонтитулов так:

    \renewcommand{\@evenhead}{\hfil Л.Н.ТОЛСТОЙ}
    \renewcommand{\@oddhead}{ВОЙНА И МИР\hfil}
    \renewcommand{\@evenfoot}{\hfil --- \thepage ---\hfil}
    \renewcommand{\@oddfoot}{\hfil --- \thepage ---\hfil}

    Если мы хотим, чтобы каких-то колонтитулов вообще не было, то надо переопределить соответствующую команду на "ничего не делать", например, так:

    \renewcommand{\@oddfoot}{}

    Итак, мы научились менять оформление колонтитулов, переопределяя команду \@evenhead и ей подобные. А теперь — важное предупреждение: команда \pagestyle также переопределяет команды типа \@evenhead ; если вы проведете переопределения в своем стилевом пакете, то первой же командой \pagestyle ваши переопределения будут отменены. Стало быть, если уж вы переопределяете команды наподобие \@evenhead, то после этого переопределения командой \pagestyle в документе пользоваться не надо ( \thispagestyle можно).

    Прежде чем перейти к более сложным вещам, скажем еще о трех стилевых параметрах. Во-первых, интервалы между колонтитулами и текстом регулируются параметрами со значением длины \headsep, задающим интервал между верхним колонтитулом и текстом, и \footskip, задающим расстояние между базисной линией последней строки в теле страницы и базисной линией нижнего колонтитула. Во-вторых, существует параметр \headheight, задающий высоту верхних колонтитулов. Если сумма высоты и глубины заданного вами колонтитула будет превышать \headheight, то при трансляции вы получите сообщение

    Overfull \vbox occurred while \output was active.

    Приведем пример, когда надо учитывать \headheight. Пусть мы хотим в том же издании "Войны и мира" отделять верхние колонтитулы от текста линейками. Разумный способ это сделать — передать в \hbox to \textwidth уже готовый блок шириной \textwidth, содержащий как текст колонтитула, так и линейку. Так как линейку под текстом удобно проводить в вертикальном режиме с помощью команды \hrule, в голову приходит вот что (здесь и далее мы для краткости приводим только определение \@evenhead ):

    \renewcommand{\@evenhead}%
    {\vbox{\hbox to\textwidth{\hfil Л.Н.ТОЛСТОЙ}\hrule}}

    У такого определения есть, однако, два недостатка. Во-первых, так как линейки в вертикальном режиме добавляются "впритык" к предшествующему блоку, у нас нет гарантии, что линейка не подойдет к тексту слишком близко; если бы к тому же текст в колонтитулах на разных страницах варьировался, как в дальнейших примерах, то может случиться и так, что две соседние линейки на развороте окажутся на разной высоте (из-за того, что в колонтитуле на одной странице будет буквы вроде у, опускающиеся ниже базисной линии, а на другой — нет). Средство от этого недостатка — добавить \strut в наш блок:

    \renewcommand{\@evenhead}%
    {\vbox{\hbox to\textwidth{\hfil \strut
    Л.Н.ТОЛСТОЙ}\hrule}}

    Второй недостаток — это то, что к размеру блока с текстом добавится ширина линейки, в результате чего этот размер превысит \headheight и мы будем получать уйму сообщений об overfull'е. Чтобы уйти от этого, надо еще чуть-чуть схитрить:

    \renewcommand{\@evenhead}%
    {\raisebox{0pt}[\headheight][0pt]{% начало блока
    \vbox{\hbox to\textwidth{\hfil \strut
    Л.Н.ТОЛСТОЙ}\hrule}}% конец блока
    }% конец макроопределения

    Понятно ли, что происходит? С помощью \raisebox мы заставляем TeX считать, что блок имеет высоту \headheight (нам даже незачем вникать, чему она фактически равна) и нулевую глубину (чтобы в сумме получилось то, что надо). Теперь ни о каких переполнениях речи не будет; пробел между колонтитулом и текстом можно при желании изменить, изменив значение \headsep.

    Для нижних колонтитулов параметра, аналогичного \headheight, нет, так что смело делайте их любой высоты.

    Кстати говоря, команду \@evenhead в этом примере можно было бы переопределить более простым образом, без \vbox, с использованием команды \underline. Наш способ, однако, более гибок: например, мы можем регулировать толщину линейки, чего с \underline не добьешься.

    Итак, мы научились создавать собственные колонтитулы. Однако в LaTeX'овском стандарте в колонтитулы обычно помещается не только номер страницы, но и, например, номер и заглавие текущего раздела. Давайте научимся делать и это.

    Чтобы передать в колонтитул какую-то информацию из текста, в LaTeX'е используются команды \markboth и \markright. Разберем, как они работают. Команда \markboth, требующая двух обязательных аргументов, запоминает пару " пометок" — два фрагмента текста (возможно, с TeX'овскими командами). Например, если мы скажем (где-нибудь между абзацами)

    \markboth{Кот}{Пес}

    то поместим между этими абзацами пару пометок: "левую пометку" Кот и "правую пометку" Пес. Сами по себе эти пометки никак не отражаются на печати. Однако же в определениях команд \@oddhead и ей подобных мы можем на эти пометки ссылаться. Именно, в этих определениях команда \leftmark дает левую пометку, а команда \rightmark — правую пометку. Например, если мы переопределим верхние колонтитулы как

    \renewcommand{\@evenhead}{\leftmark\hfil}
    \renewcommand{\@oddhead}{\hfil\rightmark}

    то, начиная с той страницы, на которую попали наши пометки, в левом верхнем колонтитуле будет стоять выключенное влево слово "Кот", а в правом — выключенное вправо слово " Пес"Точнее говоря, так будет, если в тексте нет команд типа \section: эти команды, как мы увидим ниже, автоматически вставляют в текст свои пометки, что усложняет картину.. Кстати, если никаких пометок в тексте нет, то как \leftmark, так и \rightmark дают " пустой" текст.

    До сих пор мы молчаливо предполагали, что на каждой странице присутствует только одна пара пометок. Что будет, если таких пар пометок попадет на страницу несколько? Ответ: команда \leftmark в этом случае означает левую пометку из самой верхней пары пометок, попавших на страницу, а команда \rightmark означает правую пометку из самой нижней пары пометок, попавших на данную страницу. С другой стороны, если на страницу вообще ни одна пара пометок не попала, то \leftmark и \rightmark означают соответственно левую и правую пометки из последней пары пометок, встретившихся до этого.

    Поясним сказанное примером. Пусть пометки

    \markboth{x}{y} и \markboth{z}{t}

    попали (в указанном порядке) на страницу 1, на страницу 2 вообще никаких пометок не попало, на страницу 3 попали целые три пары пометок:

    \markboth{u}{v},
    \markboth{a}{b} и
    \markboth{m}{n},

    а на страницах 4 и дальнейших никаких новых пометок не появлялось. Тогда значения команд \leftmark и \rightmark в процессе обработки этих страниц были таковы:

    Страница\leftmark\rightmark
    1 $$x$$ $$t$$
    2 $$z$$ $$t$$
    3 $$u$$ $$n$$
    4 и далее $$m$$ $$n$$

    Наряду с командой \markboth, которая ставит в тексте новую пару пометок, есть еще и команда \markright с одним аргументом, которая ставит в тексте пару пометок таким образом: левый элемент в этой паре — такой же, как был в предыдущей паре пометок, а правый — тот, что задан в аргументе команды \markright. Например, если сначала идет команда

    \markboth{Кот}{Пес}

    а затем команда

    \markright{Собака}

    (и в промежутке между этими командами никаких других пометок в текст не вносится), то это равносильно тому, как если бы вторая из этих команд была

    \markboth{Кот}{Собака}

    Выше мы уже отмечали, что команды типа \section ставят в тексте пометки автоматически. Понять, как это делается и как можно влиять на этот процесс, проще всего на примере. Сделаем такие предположения о документе: класс — article, разделы и подразделы нумеруются (иными словами, значение счетчика {secnumdepth} больше единицы), действует стилевая опция twoside и в преамбуле была дана команда \pagestyle{headings}.

    Во-первых, отметим, что в этом случае пометки в текст вставляют только команды \section и \subsection. При этом команда \section ставит пометки, автоматически выполняя команду \sectionmark, имеющую один обязательный аргумент — заглавие раздела (если команда \section была дана без необязательного аргумента) или вариант заглавия, заданный в необязательном аргументе команды \section (если таковой присутствует). Вот как определена \sectionmark (на место #1 будет подставляться вариант заглавия, идущий в колонтитулы):

    \newcommand{\sectionmark}[1]{\markboth{%
    \MakeUppercase{\thesection\hspace{1em}#1}}% левая пометка
    {}% правая пометка (она пуста)
    }% конец макроопределения

    Здесь используется LaTeX'овская команда \MakeUppercase, которую мы ранее не рассматривали. Не вдаваясь в подробности, скажем, что эта команда переводит все буквы в текстеНо не в именах команд; что будет с русскими буквами, зависит от русификации., попавшем в ее аргумент, из строчных в прописные. Коль о том зашла речь, отметим, что есть еще и команда \MakeLowercase, которая наоборот переводит все буквы в тексте, попавшем в ее аргумент, из прописных в строчные. (Не пытайтесь, пожалуйста, использовать \MakeUppercase и \MakeLowercase вне аргументов \markboth или \markright, если не любите неприятных сюрпризов.) Если вы не хотите, чтобы в колонтитулах строчные буквы заменялись на прописные, можно при переопределении просто опустить команду \MakeUppercase (так и было сделано при оформлении книги, которую вы читаете).

    Команда \subsectionmark, определяющая вид пометок, автоматически вставляемых в текст командой \subsection, определена следующим образом:

    \newcommand{\subsectionmark}[1]{\markright
    {\thesubsection\hspace{1em}#1}}

    Здесь также аргумент #1 — это заглавие подраздела (точнее, его вариант для колонтитулов).

    Итак, в рассматриваемом нами случае команда \section вносит в текст следующую пару пометок: заглавие раздела, в котором все буквы заменены на прописные, в качестве левой пометки, и пустой текст в качестве правой пометки. Команда же \subsection вносит в текст пару пометок, в которой левая пометка такая же, как в предыдущей паре, а правая — заглавие подраздела (точнее, его вариант для колонтитулов), причем на сей раз "в натуральном виде", без замены строчных букв на прописные. Как уже отмечалось выше, команды \subsubsection и более мелкие никаких пометок в текст не вносят.

    Посмотрим, как в этом стиле используются пометки. Колонтитулы на четных страницах в этом случае определены так:

    \newcommand{\@evenhead}{\thepage\hfil
                  \normalfont\slshape\leftmark}

    Тем самым на страницах с четными номерами (они будут левыми на развороте) колонтитул будет выглядеть следующим образом: выключенный влево номер страницы (прямым шрифтом) и заглавие текущего раздела (наклонным шрифтом, прописными буквами) — выключенное вправоТочнее говоря, это будет заглавие либо текущего раздела, либо первого из разделов, начинающихся на этой странице — см. выше обсуждение \leftmark и \rightmark .: ведь никаких других левых пометок в тексте нет!

    Команда \@oddhead, отвечающая за верхние колонтитулы на страницах с нечетными номерами, определена в стиле article (при условии, что была команда \pagestyle{headings} ) так:

    \newcommand{\@oddhead}{{\normalfont\slshape\rightmark}%
                  \hfil\thepage}

    Стало быть, верхние колонтитулы к нечетным страницам выглядят так: название текущего подраздела наклонным шрифтом — выключенное влево, номер страницы прямым шрифтом — выключенный вправо. Впрочем, если в текущем разделе команд \subsection еще не было, то вместо заглавия будет пустое место, так как \rightmark будет пуста (определение команды \sectionmark, данное выше, показывает, что при исполнении команды \section в текст вносится пустая правая пометка, и пустой она остается до первой команды \subsection ).

    Приведем пример переопределения команд наподобие \sectionmark. Если нам не нравится, что в правом колонтитуле иногда бывает пустое место, то можно попросить команду \section вносить в текст непустую правую пометку — то же заглавие раздела. Для этого напишем в преамбуле так:

    \newcommand{\sectionmark}[1]{\markboth
    {\uppercase{\thesection\hspace{1em}#1}}% левая пометка
    {\uppercase{\thesection\hspace{1em}#1}}% правая пометка
    }% конец макроопределения

    Теперь, если в разделе нет подразделов, то на правых страницах в верхнем колонтитуле будет также печататься заглавие текущего раздела. Оформление колонтитулов при этом будет стандартным. Если вы хотите еще и отойти от этого стандарта, то надо будет, вместо использования команды \pagestyle, напрямую переопределить команды типа \@oddhead и \@evenhead ; надо думать, теперь вы найдете, как применить в этих определениях команды \leftmark и \rightmark.

    Если в документе присутствует команда \pagestyle (с каким бы то ни было аргументом), то она отменит ваши переопределения команд типа \sectionmark. Поэтому все команды \pagestyle должны идти до ваших личных переопределений команд типа \@evenhead.

    Если вы вообще не хотите, чтобы при исполнении, скажем, команды \subsection в текст вносились какие-либо пометки, то можно "отключить" команду \subsectionmark, переопределив ее на "ничего не делать":

    \renewcommand{\subsectionmark}[1]{}

    Бывает и так, что вас устраивает стандартный стиль оформления колонтитулов, но при этом не устраивает, что именно в эти колонтитулы автоматически записывается. Например, у ваших разделов длинные заглавия, и вы при этом хотите, чтобы они в несокращенном виде попали в оглавление, а сокращенные варианты заглавий пошли только в колонтитулы. Команда \section с необязательным аргументом тут не спасет, так как этот необязательный аргумент запишется и в оглавление тоже. Вот бы задать информацию для колонтитулов вручную, без того, чтобы это автоматически делали команды типа \section! Можно, конечно, переопределить на "ничего не делать" все команды типа \sectionmark, как в приведенном выше примере, но LaTeX предоставляет вам более простой способ. Если написать в стилевом файле (до того, как вы переопределяете команды наподобие \@oddhead )

    \pagestyle{myheadings}

    то все LaTeX'овские команды для создания разделов не будут вносить пометок в текст, а оформление колонтитулов будет стандартным. После этого можно самостоятельно переопределить \@oddhead и пр., если вам это нужно: пометки в текст командами рубрикации вноситься все равно не будут.

    Теперь вы сможете, например, писать

    \section
    {О некоторых специальных свойствах
    подмножеств пустых множеств, не рассматривавшихся
    в предыдущих разделах статьи}%
    \markboth{\thesection\hspace{1em}Подмножества}{}

    и в оглавлении будет заголовок целиком, а в колонтитуле — лишь слово "Подмножества" (мы подразумеваем, что стиль все тот же, только аргументом команды \pagestyle был myheadings вместо headings). Команда \markboth помещена после команды \section, чтобы номер раздела, генерируемый командой \thesection, был правильным. Кроме того, мы убрали с помощью знака процента пробел (конец строки) между командами \section и \markboth, чтобы пометки с гарантией попали на ту же страницу, что и заголовок раздела.

    Другие команды, отвечающие за автоматическую расстановку пометок в тексте, устроены аналогичным образом: команда \chapter ставит пометки с помощью команды \chaptermark, команда \section — с помощью команды \sectionmark и т. д. — вообще, если команда, генерирующая раздел документа, определена с помощью \@startsection с первым аргументом abcd, то она будет ставить пометки с помощью команды \abcdmark. Все эти команды автоматически выполняются в процессе выполнения соответствующей команды, генерирующей раздел. Они должны иметь один обязательный аргумент, в качестве которого им передается заглавие раздела (точнее, вариант этого заглавия, предназначенный для колонтитулов и оглавления). Варианты "со звездочкой" команд, генерирующих разделы документа, никаких пометок в текст не вносят (как и следовало ожидать).

    Если в аргументе команды \markboth или \markright присутствует не только текст, но и какие-то команды, то в пометки будут записаны не буквально эти команды, но их значение на момент запоминания пометок. Например, если в аргументе \markboth присутствует команда \thesection, то в пометку реально запишется (а потом и прочтется из \leftmark или \rightmark ) номер раздела. Если же необходимо, чтобы какая-то команда записалась в пометку в том же виде, в каком она была задана в аргументе \markboth или \markright, то надо "защитить" ее, поставив перед ней \protect.

    Еще один случай, когда пометки в текст вносятся LaTeX'ом автоматически, возникает при оформлении таких фрагментов документа, как оглавление, список иллюстраций или таблиц, список литературы и предметный указатель. Как именно они вносятся, зависит от класса документа и от того, пользовались ли мы (и как пользовались) командой \pagestyle. Именно, если класс — article, то никаких пометок при оформлении оглавления и т.п. в текст автоматически вноситься не будет; точно так же не будет этих пометок в любом классе после того, как выполнится команда \pagestyle с аргументом empty, plain или myheadings. С другой стороны, если класс документа — report или book, то, например, при исполнении команды \tableofcontents автоматически выполняется и команда

    \markboth{\contentsname}

    (с очевидными изменениями для списка иллюстраций и т.п.). Та же ситуация возникнет и после исполнения команды \pagestyle с аргументом headings (даже тогда, когда класс — article).

    Итак, вы теперь имеете широкие возможности для создания собственного оформления колонтитулов. Во-первых, можно написать

    \pagestyle{myheadings}

    При этом внешний вид колонтитулов будет стандартный, но материал для колонтитулов вы будете поставлять вручную с помощью команд \markboth и/или \markright. Во-вторых, можно переопределять команды типа \sectionmark ): при этом внешний вид колонтитулов будет по-прежнему стандартный, но материал для помещения в колонтитул будет отбираться автоматически по схеме, отличной от стандартной. В-третьих, можно переопределять команды типа \@oddhead: при этом вы меняете как стиль оформления колонтитулов, так и способ обращения с пометками, вносимыми в текст (в частности, если в ваших определениях команд типа \@oddhead не участвуют \leftmark и \rightmark, то эти пометки будут вообще проигнорированы). Наконец, можно объединить второй и третий подходы. При этом вы самостоятельно разрабатываете как внешний вид колонтитулов, так и то, какая информация из текста и как будет в них отражена.

    Плавающие объекты

    Этот раздел посвящен плавающим иллюстрациям и таблицам (короче: плавающим объектам).

    Оформление подрисуночной подписи

    Обсудим, как можно менять оформление подписи под рисунком (или таблицей), создаваемой командой \caption ).

    Над и под подписью предусмотрены вертикальные отбивки. Их размеры хранятся в параметрах со значением длины (растяжимой) \abovecaptionskip (отбивка над подписью) и \belowcaptionskip (под подписью). В стандарте отбивка над подписью равна 10pt (без растяжимости или сжимаемости), а под подписью — нулю.

    Чтобы изменить само оформление подписи, надо переопределить команду \@makecaption ; вот ее стандартное определение в адаптированном виде (параметр #1 — номер иллюстрации или таблицы с подписью, то есть значение команды \thefigure или \thetable ; параметр #2 — текст подписи):

    \newcommand{\@makecaption}[2]{%
    \vspace{\abovecaptionskip}%
    \sbox{\@tempboxa}{#1: #2}
    \ifdim \wd\@tempboxa >\hsize
       #1: #2\par
    \else
       \global\@minipagefalse
       \hbox to \hsize {\hfil #1: #2\hfil}%
    \fi
    \vspace{\belowcaptionskip}}

    Разберем этот код. Во второй и последней строчках вокруг подписи делаются отбивки, как было объяснено выше. В третьей строке в блоковую переменную \@tempboxa (эта переменная используется LaTeX'ом для временного хранения данных такого рода) записывается текст подписи вместе с номером (пока что в одну строку; поскольку в данный момент этот текст еще не печатается, нас не волнует, не окажется ли он длинней, чем ширина полосы). В следующих шести строках (с помошью не рассматривавшейся нами TeX'овской конструкции "условных макросов") длина подписи с номером сравнивается с шириной текста (она обозначена \tex'овским параметром \hsize: при одноколонном наборе это то же самое, что \textwidth ), а при многоколонном — \columnwidth ). Если подпись вместе с номером длиннее строки, то она печатается как абзац (часть кода между \ifdim ) и \else ), а если не длиннее, то центрируется (часть кода между \else и \fi ). Код на седьмой строке воспринимайте как данность.

    Что можно изменить в этом определении? Поскольку #1 — это номер, а #2 — текст подписи, нетрудно заметить, что номер отделяется от подписи двоеточием, что с отечественными полиграфическими традициями не согласуется. Разумно заменить в этом месте двоеточие на точку. Кроме того, можно изменить шрифт, которым печатается подпись. Только не забудьте, что при переопределении надо будет вставить команды смены шрифта в три места (всюду, где в исходном определении стоит #1: #2): и в "измеряющую размер" строку, начинающуюся с \sbox (от смены шрифта размер тоже может измениться), и в оба варианта печати. Наконец, вы можете решить (не знаю, насколько это правильно) никогда не центрировать подписи; тогда в измененном определении \@makecaption надо будет удалить строки, начинающиеся с \ifdim, \else и \fi, а также текст между \else и \fi (и, возможно, установить свои любимые параметры верстки абзаца). Возможны, наверное, и другие решения. В любом случае помните, что текст между \ifdim и \else относится к случаю, когда подпись с номером в строку не умещается, а текст между \else и \fi — к противоположному.

    И последнее: команду \@makecaption вы будете, конечно, переопределять с помощью \renewcommand ; имейте в виду, что в данном случае надо пользоваться вариантом \renewcommand без звездочки, поскольку второй аргумент этой команды (текст подписи) вполне может состоять из нескольких абзацев.

    Размещение плавающих объектов на странице

    Сейчас мы обсудим параметры, которыми руководствуется LaTeX при размещении плавающих объектов на странице.

    Сразу же отметим, что все эти параметры относятся в равной мере к плавающим иллюстрациям и плавающим таблицам, и любое изменение этих параметров также затрагивает плавающие объекты всех типов.

    Часть параметров, отвечающих за плавающие объекты, представляет собой LaTeX'овские счетчики, которым можно присваивать новые значения командой \setcounter:

  • \topnumber Максимальное количество плавающих объектов, которое разрешается разместить вверху страницы (при двухколонном наборе и иллюстрациях/таблицах шириной в колонку — вверху колонки). Значение по умолчанию: $$2$$.
  • \bottomnumber Максимальное количество плавающих объектов, которое разрешается разместить внизу страницы (при двухколонном наборе и иллюстрациях/таблицах шириной в колонку — внизу колонки). Значение по умолчанию: $$1$$.
  • \totalnumber Максимальное количество плавающих объектов, которое разрешается разместить на странице (при двухколонном наборе и иллюстрациях/таблицах шириной в колонку — в колонке). Значение по умолчанию: $$3$$.
  • \dbltopnumber При наборе в две колонки: максимальное количество плавающих объектов шириной во всю страницу, которое разрешается разместить вверху страницы. Значение по умолчанию: $$2$$.
  • Значение счетчика totalnumber не влияет на количество иллюстраций и/или таблиц на странице, специально для них предназначенной (таковая, как мы помним, выделяется, если в необязательном аргументе окружения {figure} или {table} присутствует буква p).

    Вторая группа параметров регулирует уже не количество плавающих иллюстраций на странице, а величину места, ими занимаемого. Все эти параметры являются командами наподобие \arraystretch или \baselinestretch ; чтобы менять значения параметров, надо их переопределять с помощью команды \renewcommand. Эти параметры таковы:

  • \topfraction Максимальная доля страницы, которую могут занимать плавающие объекты, размещаемые вверху страницы. Значение по умолчанию: $$0.7$$. Это означает, что плавающие иллюстрации и таблицы, размещаемые вверху страницы, могут занимать не более 70% страницы по высоте. Если мы хотим уменьшить эту долю, скажем, до 50%, надо написать
    \renewcommand{\topfraction}{0.5}
    Ниже слова "доля страницы" также всюду означают "доля страницы по высоте".
  • \bottomfraction Максимальная доля страницы, которую могут занимать плавающие объекты внизу страницы. Значение по умолчанию: $$0.3$$.
  • \textfraction Минимальная доля страницы, которую должен занимать текст, а не плавающие объекты (к страницам, создаваемым LaTeX'ом специально для размещения плавающих объектов при обработке необязательного аргумента p, это не относится). Значение по умолчанию: $$0.2$$.
  • \floatpagefraction Этот параметр, напротив, относится именно к страницам, которые LaTeX создает при обработке необязательного аргумента p. Он указывает минимально возможную долю такой страницы, которую могут занимать размещаемые на ней плавающие иллюстрации и таблицы. Значение по умолчанию: $$0.5$$ (стало быть, специальная страница для плавающих иллюстраций, которую вы требуете с помощью необязательного аргумента p к окружению {figure}, не будет создана, пока эти иллюстрации занимают менее 50% высоты страницы текста).
  • Все вышеуказанные параметры применимы также к двухколонному набору и плавающим объектам шириной в колонку. Если же набор — в две колонки, а ширина плавающего объекта — целая страница, то используются такие параметры:

  • \dbltopfraction То же, что \topfraction, применительно к иллюстрациям (таблицам) шириной в целую страницу при двухколонном наборе. Значение по умолчанию: $$0.7$$.
  • \dblfloatpagefraction То же, что \floatpagefraction, применительно к иллюстрациям (таблицам) шириной в целую страницу при двухколонном наборе. Значение по умолчанию: $$0.5$$.
  • При вычислении, какую часть страницы занимает плавающий объект, учитывается не только размер собственно иллюстрации или таблицы, но и величина вертикальных отступов (" отбивок"), отделяющих этот объект от остального текста. Эти отступы задаются следующей группой параметров. Все эти параметры суть длины, присваивать им новое значение надо с помощью \setlength.

  • \textfloatsep Отступ между текстом и иллюстрациями (таблицами), размещаемыми вверху или внизу страницы.
  • \floatsep Отступ между двумя иллюстрациями (таблицами).
  • \intextsep Отступ между текстом и иллюстрациями (таблицами), размещаемыми посреди страницы (при обработке необязательного аргумента h).
  • Как водится, три перечисленных параметра применимы и к иллюстрациям (таблицам) шириной в колонку при двухколонном наборе. А вот как обозначаются соответствующие параметры, если набор в две колонки, а иллюстрация или таблица занимает по ширине всю страницу:

  • \dbltextfloatsep При двухколонном наборе - отступ между текстом и иллюстрацией (таблицей), занимающей всю страницу по ширине.
  • \dblfloatsep При двухколонном наборе - отступ между двумя иллюстрациями (таблицами), занимающими всю страницу по ширине.
  • Если вы почему-либо решите менять эти параметры с помощью команды \setlength, полезно иметь в виду, что при пользовании шрифтом кегля $$11$$ значения \floatsep, \intextsep и \dblfloatsep равны 12pt plus 2pt minus 2pt, а значения \textfloatsep и \dbltextfloatsep равны 20pt plus 2pt minus 4pt.

    По умолчанию плавающие объекты не отделены от текста ничем, кроме вышеперечисленных отбивок. Но можно сделать и так, чтобы иллюстрации (таблицы) отделялись от текста как-то иначе (линейками, например). Для этих целей предусмотрены следующие три команды:

  • \topfigrule Разделитель между плавающим объектом, размещаемым вверху страницы (колонки), и остальным текстом.
  • \botfigrule Разделитель между текстом и размещаемым внизу страницы (колонки) плавающим объектом.
  • Эти две команды относятся и к двухколонному набору, при условии, что иллюстрации (таблицы) занимают по ширине одну колонку (иными словами, если используются окружения {figure} или {table} без звездочек). А если используются варианты этих окружений со звездочками, то используется еще один параметр:

  • \dblfigrule То же, что \topfigrule, для случая, когда набор двухколонный, а плавающий объект занимает по ширине всю страницу.
  • По умолчанию указанные три команды ничего не делают. Если вы хотите задать явные разделители между текстом и иллюстрациями (таблицами), то эти команды надо определить с помощью Именно так, а не переопределить с помощью \renewcommand !. Определять эти команды нужно не произвольным образом: чтобы они правильно стыковались с LaTeX'овскими алгоритмами размещения плавающих объектов, нужно иметь в виду следующее:

  • каждая из этих команда будет выполняться в те моменты, когда TeX находится в вертикальном режиме;
  • по окончании работы каждой из этих команд TeX должен снова оказаться в вертикальном режиме;
  • текст, генерируемый каждой из этих команд, не должен, с точки зрения TeX'а, занимать места по вертикали.
  • Поэтому будет неправильно, если вы, решив отделять текст от иллюстраций линейкой, определите \botfigrule просто как \hrule: первое и второе условия при этом выполнены будут, а вот третье — нет, в результате чего LaTeX собьется со счета при решении вопроса о размещении иллюстраций. Формально правильным было бы такое решение:

    \newcommand{\botfigrule}{\hrule\vspace{-0.4pt}

    (вспомним, что линейка, генерируемая командой \hrule, имеет по умолчанию толщину 0.4pt). Впрочем, формальной правильности мало: если вы опробуете такое определение на практике, то увидите, что линейка вплотную прилегает к иллюстрации, что никуда не годится. Правильно действовать, например, так:

    \newcommand{\botfigrule}{\vspace{-3pt}\hrule
    \vspace{2.6pt}}

    Теперь мы проводим линейку не прямо по верхней кромке иллюстрации, а на три пункта выше; заключительное \vspace{2.6pt} нужно для того, чтобы в сумме получилось нулевое вертикальное смещение.

    С \topfigrule и \dblfigrule вы сможете теперь разобраться самостоятельно.

    В заключение отметим, что разделители, определяемые \topfigrule и ей подобными командами, не обязаны быть именно линейками: необходимо только при их определении учитывать три перечисленных выше обстоятельства.

    Разное

    Теоремы, выключные формулы

    Чтобы изменить оформление "теорем" (окружений, определяемых с помощью \newtheorem ), надо переопределить команды \@begintheorem и \@opargbegintheorem (первая из них отвечает за оформление "теорем" без необязательного аргумента, вторая — за оформление "теорем" с необязательным аргументом). Первая из них определена так:

    \newcommand{\@begintheorem}[2]{\begin{trivlist}
    \item[\hspace{\labelsep}\bfseries#1\ #2]
    \itshape}

    Здесь аргумент #1 означает название "теоремы" (например, " Теорема", "Предложение", "Лемма",...- в команде \newtheorem это слово являлось вторым обязательным аргументом), а аргумент "#2" означает номер "теоремы". Если мы, например, хотим, чтобы после номера "теорем" стояла точка, нам достаточно переопределить эту команду, добавив точку после #2. Что делать для того, чтобы сменить шрифт, которым печатаются номер или текст "теорем", также достаточно ясно.

    Команда \@opargbegintheorem определяется так:

    \newcommand{\@opargbegintheorem}[3]{\begin{trivlist}
    \item[\hspace{\labelsep}{\bfseries #1\ #2\ (#3)}]
    \itshape}

    Здесь #1 и #2 по-прежнему означают название и номер " теоремы", а #3 — необязательный аргумент "теоремы" (обычно в качестве такового задается имя ученого, которому приписывается данная теорема).

    Если оформление, задаваемое окружением trivlist, вас не устраивает, то можно переопределить две вышеуказанные команды более радикально. Общий принцип таков. Перед текстом "теоремы", не имеющей необязательного аргумента, исполняется команда \@begintheorem ; у этой команды должно быть два аргумента, причем первый из них — название "теоремы", а второй — ее номер. Если "теорема" имеет необязательный аргумент, то вместо \@begintheorem перед ее текстом исполняется команда \@opargbegintheorem, имеющая три аргумента: первые два — такие же, как у \@begintheorem, и третий — необязательный аргумент "теоремы" (имя первооткрывателя). Наконец, после текста "теоремы" исполняется команда \@endtheorem, которая изначально определена очень просто:

    \newcommand{\@endtheorem}{\end{trivlist}}

    В принципе можно переопределить все три эти команды, чтобы получить свое оформление "теорем" (например, в духе наших макросов для автоматической нумерации задач из лекции 7). Только следите, чтобы переопределения всех трех команд были согласованы друг с другом: если, например, вы изгоните \begin{trivlist} из определения \@begintheorem, но при этом оставите команду \@endtheorem в неприкосновенности, то на каждой " теореме" LaTeX будет сообщать вам об ошибке (отсутствие баланса команд \begin и \end ).

    При пользовании AMS'овскими классами документов "теоремы" определяются иначе. Вряд ли, впрочем, вы сочтете нужным переделывать стандарт Американского математического общества.

    Теперь скажем кое-что про стиль оформления номеров выключных формул, заданных в виде окружения {equation}. Как вам уже известно, можно переопределить команду \theequation или (с помощью команды \@addtoreset ) изменить подчиненность счетчика {equation}; при этом изменится оформление самих номеров формул. Кроме этого, можно изменить то, что печатается возле этих номеров. Для этого следует переопределить команду \@eqnnum. Изначально она определена так:

    \newcommand{\@eqnnum}{(\theequation)}

    При желании можно заменить тут круглые скобки на что-нибудь другое. Имейте в виду, что номер выключной формулы обрабатывается TeX'ом " в математическом режиме", как формула (латинские буквы по умолчанию набираются "математическим курсивом" и т.п.).

    Сноски

    Стиль оформления сносок зависит от многих вещей. Начнем с пробела между страницей и сносками. Чтобы его изменить, надо применить команду \setlength с необычным первым аргументом. Вот, например, как выглядит команда, устанавливающая стандартную для LaTeX'а величину этого пробела:

    \setlength{\skip\footins}{12pt plus 4pt minus 4pt}

    Почему в первом аргументе \setlength целых две команды и что они означают, объяснить в рамках этой книги невозможно, так что воспринимайте этот рецепт для установки пробела между текстом и сносками догматически (для любознательных: вся правда содержится в пятнадцатой главе книги [2].

    Далее, сноски обычно отделяются от текста не только пробелом, но и линейкой. Чтобы задать вид этой линейки, отличный от стандартного, либо задать какой-то другой разделитель, надо переопределить команду \footnoterule, которая в стандарте определена так:

    \newcommand{\footnoterule}{\vspace*{-3pt}
         \hrule width .4\columnwidth
         \vspace*{2.6pt}}

    К этому макроопределению необходим комментарий: непонятно, зачем нужны команды \vspace. Дело в том, что "текст", генерируемый командой \footnoterule, не должен, с точки зрения TeX'а, занимать места по вертикали (фактически он располагается внутри пробела между текстом и сносками, о котором шла речь выше). Поэтому мы сначала отступаем на 3 пункта вверх, затем печатаем линейку (вспомним, что по умолчанию линейка, генерируемая командой \hrule, имеет толщину 0.4 пункта), а затем спускаемся на 2.6 пункта вниз. В итоге получается, что и линейка напечаталась, и места по вертикали мы не занимаем, поскольку $$-3+0.4+2.6=0$$.

    Может возникнуть вопрос, зачем нужен \vspace*{-3pt}: не проще ли обойтись без этой команды, а после \hrule сказать \vspace*{-0.4pt}? Ответ: в этом случае линейка напечаталась бы вплотную к сноске.

    Если вы хотите изменить ширину или толщину линейки, команду \footnoterule можно переопределить; только не забудьте проследить, чтобы отрицательный \vspace скомпенсировал толщину линейки. Можно, собственно говоря, сделать так, чтобы этой линейки вообще не было, сказав

    \renewcommand{\footnoterule}{}

    (уж тут-то места по вертикали мы не займем!). Если вам вдруг понадобится задать совсем иной разделитель между сносками и текстом, можете переопределить команду \footnoterule принципиально по-иному. В этом случае необходимо знать следующее:

  • команда \footnoterule будет выполняться в те моменты, когда TeX находится в вертикальном режиме;
  • по окончании работы команды \footnoterule TeX должен снова оказаться в вертикальном режиме;
  • текст, генерируемый командой \footnoterule, не должен, с точки зрения TeX'а, занимать места по вертикали.
  • Следующий параметр, от которого зависит оформление сносок, — это параметр со значением длины \footnotesep. Он означает следующее. В начале каждой сноски, для того чтобы линейка, отделяющая сноски от текста, не подходила к тексту слишком близко, вставляется невидимая линейка нулевой ширины наподобие \strut. Так вот, \footnotesep задает высоту этой линейки.

    За вид номеров сносок в тексте отвечает команда \@makefnmark. По умолчанию она определена следующим образом:

    \newcommand{\@makefnmark}{\hbox{\mathsurround=0pt
    $^{\@thefnmark}$}}

    Здесь на место команды \@thefnmark при выполнении будет подставлен номер сноски (или то, что его заменяет, если мы пользовались командой \footnotemark ). Обратите внимание, что номер сноски оформлен как верхний индекс в математической формуле — именно благодаря этому номера сносок печатаются над строкой. По этой же причине внутри группы, являющей собой аргумент команды \hbox, устанавливается в нуль параметр \mathsurround - иначе, если вы установили для него ненулевое значение, номер сноски будет окружен лишними пробелами.

    И, наконец, самое главное — команда, генерирующая собственно текст сноски. Она называется \@makefntext. Вот ее стандартное определение, в котором аргумент #1 обозначает текст сноски, а команда \@thefnmark означает то же, что и выше:

    \newcommand{\@makefntext}[1]{\parindent=1em\noindent
                \hbox to 1.8em{\hss\@makefnmark}#1}

    При переопределении этой команды следует иметь в виду, что она будет выполняться внутри аргумента команды \parbox с длиной строки, равной ширине колонки текста; в приведенном выше определении применена команда \noindent, чтобы подавить абзацный отступ в первом абзаце сноски, в котором будет печататься ее номер.

    Имейте в виду, что поскольку текст сноски, являющийся аргументом команды \@makefntext, может состоять из нескольких абзацев, переопределять эту команду надо с помощью \renewcommand без звездочки.

    Список литературы

    Если вам не нравится, что библиографические ссылки печатаются в квадратных скобках, то вы можете переопределить команды \@cite и \@biblabel. По умолчанию они определены так:

    \newcommand{\@cite}[2]{[{#1\if@tempswa , #2\fi}]}
    \newcommand{\@biblabel}[1]{[#1]\hfill}

    Мы не будем даже пытаться объяснить, что означают заковыристые команды в первом из этих макроопределений (#1 в нем означает номер источника, а #2 — дополнительную информацию, помещенную в необязательном аргументе команды \cite, если таковой имеется), а отметим только, что в " замещающем тексте" первого из этих определений можно заменить квадратные скобки на какие-нибудь другие (скажем, круглые или косые) — и тогда в соответствующих скобках будет печататься ссылка, генерируемая командой \cite ; аналогично, если заменить скобки в "замещающем тексте" второго из этих определений, то в соответствующих скобках будет печататься номер источника в списке литературы. Разумеется, при переопределении этих команд надо писать \renewcommand вместо \newcommand.

    Если вы хотите, чтобы дополнительная информация печаталась вне скобок, скажите

    \renewcommand{\@cite}[2]{{[#1]\if@tempswa , #2\fi}}

    (не делайте пробела между закрывающей скобкой и \if@tempswa, иначе на печати выйдет лишний пробел). Текст между \if@tempswa и \fi будет выполняться тогда и только тогда, когда у команды \cite присутствует необязательный аргумент; если в вашем определении \@cite не будет участвовать #2, то необязательный аргумент команды \cite будет игнорироваться.

    Предметный указатель

    Первое, что вы можете изменить в оформлении предметного указателя (окружение {theindex}), - это отступы, создаваемые командами \item, \subitem и т.д. Для изменения отступов "на первом уровне" (создаваемых командой \item ) надо переопределить команду \@idxitem (но не сам item!). Чтобы вам было от чего отталкиваться, посмотрите на стандартное определение этой команды. Оно очень простое:

    \newcommand{\@idxitem}{\par\hangindent=40pt}

    Для изменения отступов, создаваемых такими командами, как \subitem и subsubitem, надо переопределить непосредственно эти команды. Их стандартные определения также бесхитростны:

    \newcommand{\subitem}{\par\hangindent=40pt\hspace*{20pt}}
    \newcommand{\subsubitem}{\par\hangindent=40pt\hspace*{30pt}}

    Наконец, команда \indexspace, создающая в предметном указателе дополнительный вертикальный пробел, определяется в стандартных стилях так:

    \newcommand{\indexspace}{\par\vspace{10pt plus 5pt minus 3pt}}

    Иногда хочется изменить оформление предметного указателя более существенным образом. Например, вы можете захотеть, чтобы ссылка на предметный указатель присутствовала в оглавлении (в LaTeX'овском стандарте это не предусмотрено); возможно также, что вы захотите предпослать предметному указателю небольшое введение, набранное во всю ширину страницы. Чтобы добиться таких вещей, надо переопределить окружение \theindex. Его стандартное определение в стилях book и report выглядит так:

    \newenvironment{theindex}{\@restonecoltrue
    \if@twocolumn\@restonecolfalse\fi
    \columnseprule=0pt \columnsep=35pt
    \twocolumn[\@makeschapterhead{\indexname}]%
    \@mkboth{\uppercase{\indexname}}{\uppercase{\indexname}}%
    \thispagestyle{plain}\parindent=0pt
    \setlength{\parskip}{0pt plus .3pt}%
    \let\item=\@idxitem}%
    {\if@restonecol \onecolumn \else \clearpage \fi}

    Первая, вторая, предпоследняя и последняя строки этого определения содержат незнакомые вам команды; мы не будем пытаться объяснить, что они значат, а только скажем, что менять эти места в определении окружения {theindex} нельзя. Зато все остальное в этом определении должно быть понятно читателю, усвоившему основную часть нашей книги. Именно, в третьей строке задаются параметры двухколонного оформления в предметном указателе: там сказано, что колонки в окружении theindex не надо разделять линейкой и задается промежуток между двумя колонками. В пятой строке дана команда, задающая (неким не рассматривавшимся нами способом) материал для колонтитулов. Она либо вносит левую и правую пометки, совпадающие со стандартным заглавием предметного указателя, либо ничего не делает. Если вы переопределяете \theindex, то можете в этой строке написать \markboth вместо \@mkboth с теми аргументами, с какими считаете нужным, или вообще убрать эту строку, чтоб пометок не было. В шестой строке обратите внимание на команду, устанавливающую нулевое значение абзацного отступа. Менять ее не надо, поскольку именно с таким значением абзацного отступа согласовано действие команд \item, \subitem и т.п. (вспомните, как действует команда \angindent ).

    Наконец, в четвертой строке стоит команда \twocolumn с необязательным аргументом. Как объяснялось в лекции 3, то, что стоит в необязательном аргументе, будет напечатано во всю ширину страницы. В стандартном определении тут стоит команда \@makeschapterhead, создающая заголовок ненумерованной главы, но вы можете записать туда и любой текст, который хотите предпослать собственно предметному указателю. Правда, тут возникает один технический момент: введение к предметному указателю вы, видимо, захотите редактировать, и нехорошо для этого всякий раз лазать в стилевой пакет. Один из возможных выходов таков. Запишите в вашем определении окружения {theindex} четвертую строку так:

    \twocolumn[\@makeschapterhead{\indexname}\input{ukaz.tex}]

    Здесь ukaz.tex — файл, в который вы запишете свое введение к предметному указателю.

    Если вы хотите, чтобы предметный указатель был отражен в оглавлении, то в необязательный аргумент команды \twocolumn надо добавить команду \addcontentsline, например, в таком виде:

    \addcontentsline{toc}{chapter}{\indexname}

    Поскольку предметный указатель, задаваемый с помощью окружения {theindex}, использует команду \twocolumn, колонки на последней странице указателя могут оказаться разной высоты. Как обычно, лекарство от этого — подключить стилевой пакет {multicol} и сделать так, чтобы окружение {theindex} использовало для печати окружение {multicols}. Для этого нужно переопределить окружение {theindex} следующим образом (мы предполагаем, что пакет {multicol} подключен):

    \renewenvironment*{theindex}{\columnseprule=0pt\columnsep=35pt
    \@makeschapterhead{\indexname}%
    \@mkboth{\uppercase{\indexname}}{\uppercase{\indexname}}%
    \thispagestyle{plain}\parindent=0pt
    \setlength{\parskip}{0pt plus .3pt}%
    \let\item=\@idxitem
    \begin{multicols}{2}}%
    {\end{multicols}}

    Разумеется, вы можете также изменить параметры в этом определении по своему усмотрению.

    Последнее, что нужно сказать про окружение {theindex}, это то, что в классе article четвертая строка его стандартного определения выглядит так:

    \twocolumn[\section*{\indexname}]%

    (поскольку в классе article главы не определены).

    Страницы:

    Мне кажется, гиппопотама

    Зовут так длинно для того,

    Чтоб сторож из глубокой ямы

    Пореже вызывал его.

    С.Я.Маршак

    Эта лекция предназначена для тех, кого не удовлетворяет оформление, предлагаемое стандартными классами LaTeX'а. Возможно, вам даже захочется создать свой собственный класс документов вместо стандартных article, proc, report или book. Задача эта выполнимая, но для этого надо в деталях знать, во-первых, книгу [2], а во-вторых — исходные тексты LaTeX'а (они доступны). У читателя настоящей книги таких познаний не предполагается, так что мы предлагаем нечто более скромное: научиться модифицировать оформление одного конкретного документа.

    Прежде чем двигаться дальше — два предупреждения. В этой лекции мы расскажем вам, как можно довольно сильно изменить стандартное LaTeX'овское оформление: вы научитесь менять по своему усмотрению шрифты в заголовках, интервалы, отделяющие заголовки от текста, и много других подобных вещей. Но вот первое предупреждение: если вы не являетесь профессиональным полиграфистом, применяйте эти познания с осторожностью. Не пытайтесь менять сразу много разных элементов оформления или резко изменять какие-то параметры: лучше осторожно менять только то, что вам действительно нужно. Учтите: когда дилетант берется за оформление книги, в девяти случаях из десяти результат бывает достоин сожаления.

    Второе предупреждение: стиль оформления записан в специальных " стилевых" или "классовых" файлах, входящих в комплект поставки LaTeX'а. Ни в коем случае не меняйте ничего в этих файлах: все изменения в стиле оформления надо записывать в собственном стилевом пакете, как объяснено ниже.

    С чего начать

    Кое-какие изменения в оформлении документа вы делать уже умеете: например, в лекции 4 рассказывалось, как можно, присвоив в преамбуле новые значения нескольким параметрам, изменить размер полей или текста. Однако для более серьезной модификации оформления приходится иметь дело со специальными командами LaTeX'а, содержащими в своем имени символ @. Поскольку @ — не буква, просто так до этих команд не добратьсяЕсли просто написать \@addtoreset (скоро вы узнаете, что это значит), то TeX воспримет это как команду \@ (имя — из одной не-буквы!), за которой следует текст addtoreset.. Поэтому действовать нужно следующим образом.

    Если вы хотите серьезно менять стандартное оформление, нужно создать свой собственный стилевой пакет. Пусть вы решили, что он будет называться {mystyle}. Тогда надо создать файл под названием mystyle.sty и начать документ так (подразумевается, что вы хотите печатать шрифтом кегля 11 и отталкиваетесь от класса book; в других случаях — c очевидными изменениями):

    \documentclass[11pt]{book}
    \usepackage{mystyle}

    После \usepackage можно писать сразу \begin{document}; все установки параметров, определения макросов, и т.п. лучше делать уже не в преамбуле, а непосредественно в файле mystyle.sty (чтобы не запутаться, устанавливая один и тот же параметр по-разному в двух разных местах).

    Для оформления документа вам, скорее всего, понадобятся какие-нибудь уже существующие стилевые пакеты (если в тексте много формул, то вы захотите подключить пакет {amsmath}, если есть таблицы, то пакет {array},...). Начать свой личный стилевой пакет надо с того, что подключить эти пакеты. При этом нужно использовать команду \RequirePackage (вместо знакомой вам \usepackage ), например, так:

    \RequirePackage{array,longtable}
    \RequirePackage[noamsfonts]{amsmath}

    (необязательный аргумент команды \RequirePackage означает то же самое и используется так же, как у команды \usepackage ).

    На крайний случай, если вам понадобилось использовать команду с символом @ в имени не в стилевом пакете, а прямо в тексте документа, предусмотрены команды \makeatletter и \makeatother. Первая из них делает @ буквой, а вторая восстанавливает status quo. Если вы использовали в тексте \makeatletter, не забудьте написать и \makeatother сразу после текста, в котором использовалась @ в имени команд.

    Итак, стандартные стилевые пакеты загружены. После этого надо записать в свой стилевой пакет ваши личные команды для модификации оформления. Начнем.

    Снова о счетчиках

    Для начала расскажем о некоторых манипуляциях со счетчиками, которые иногда бывают полезны. До сих пор мы обходили их молчанием, поскольку команды, используемые для этих манипуляций, содержат @ в своих именах.

    Как подчинить один счетчик другому

    Первый из приемов, о которых пойдет речь, связан с отношением подчинения между счетчиками. Мы знаем, что при создании счетчика с помощью команды \newcounter можно задать и счетчик, которому он будет "подчинен". Но как быть, если уже существует никому не подчиненный счетчик, а мы хотим его кому-то подчинить? Например, за нумерацию сносок отвечает счетчик footnote ; в стиле article этот счетчик определяется как никому не подчиненный, благодаря чему нумерация сносок выходит сплошной в пределах всего документа. Если мы хотим, чтоб нумерация сносок начиналась заново в каждом разделе, то можно в стилевом пакете написать так:

    \@addtoreset{footnote}{section}

    Первый аргумент команды \@addtoreset — имя подчиняемого счетчика, второй — имя подчиняющего.

    Разумеется, для того чтобы осмысленно применять описанную команду, надо знать, какие счетчики определены в стандартных стилях и кому они подчинены (или не подчинены). Эта информация содержится в конце раздела.

    При ознакомлении с командой \@addtoreset может возникнуть искушение написать

    \@addtoreset{footnote}{page}

    чтобы сноски нумеровались заново на каждой странице. К сожалению, по TeXническим причинам это может не дать желаемого результата: если сноски оказываются на нескольких страницах подряд, то может случиться так, что на второй из этих страниц нумерация сносок начнется не с $$1$$.

    Типичный случай использования команды \@addtoreset возникает, если класс документа — article. В этом случае часто пишут

    \@addtoreset{equation}{section}

    чтобы нумерация уравнений была не сплошной, как предусмотрено стандартом, а начиналась заново в каждом разделе. Разумеется, в этом случае надо будет переопределить команду \theequation.

    Если вы подключили пакет {amsmath}, то эту операцию можно осуществить и попросту в преамбуле документа: команда \numberwithin, принимающая в точности те же аргументы, что и \@addtoreset, осуществляет подчинение счетчика и к тому же переопределяет соответствующим образом the-команду.

    Ссылочный префикс

    Вторая тонкость, о которой пойдет речь, связана с автоматическими ссылками и the-командами. Предположим, что перед исполнением команды \label{metka} последним счетчиком, подвергшимся увеличению с помощью \refstepcounter, был abcd. В лекции 7 мы говорили, что при этом команда \ref{metka} представит на печати значение этого счетчика "в соответствии с командой \theabcd ". Настало время сознаться, что это полуправда. На самом деле команда \ref напечатает перед \theabcd еще и так называемый "ссылочный префикс" счетчика. Содержимое ссылочного префикса к счетчику abcd записано в команде \p@abcd (буква p, конечно, латинская). В момент создания счетчика эта команда определяется как макрос с "пустым" замещающим текстом, так что у таких счетчиков, как chapter или section в стандартных классах, ее следов не видно. Можно, однако, переопределить эту команду, чтобы ссылочный префикс реально печатался. Вот пример работы со ссылочным префиксом.

    В классе book вид номера главы и номера раздела определяется следующим образом: команда \thechapter определена стандартным образом как \arabic{chapter} (такое определение, как мы помним, автоматически производится при создании счетчика), а внешний вид номера раздела определен как

    \renewcommand{\thesection}{\thechapter.\arabic{section}}

    Из-за этого номер третьего раздела второй главы печатается в заголовке как 2.3. Пусть мы хотим, чтобы номера разделов в заголовках не содержали номера главы; тогда можно написать

    \renewcommand{\thesection}{\arabic{section}}

    но при этом возникнет другая неприятность. Автоматические ссылки на номер раздела, генерируемые командой \ref, теперь дадут на печати одно и то же число 3 как для третьего раздела второй главы, так и для третьего раздела четвертой главы: ведь из команды \thesection информация о номере главы ушла! Чтобы справиться с этой неприятностью, поместим утерянную информацию в ссылочный префикс счетчика section:

    \renewcommand{\p@section}{\thechapter.}

    Теперь будет печататься 2.3 при ссылке на третий раздел второй главы и 4.3 при ссылке на третий раздел четвертой главы: хотя \thesection в обоих случаях дает просто 3, печатающийся перед ним \p@section обеспечивает печать номера главы и точки. Кстати говоря, именно такой прием применен при подготовке книги, которую вы читаете.

    Русский аналог \alph

    В лекции 7 мы отмечали, что было бы желательно иметь команду, аналогичную \alph или \Alph, печатающую русскую букву с номером, равным значению счетчика. Сейчас мы расскажем, как вы ее можете определить в своем стилевом пакете. К сожалению, в этом определении используются не рассматривавшиеся нами средства TeX'а, так что рецепт вам придется воспринять сугубо догматически.

    Итак, пусть вам нужна команда \ralph, принимающая в качестве аргумента имя счетчика и дающая на печати русскую букву, чей номер в алфавите совпадает со значением счетчика; если этот номер неположителен или превышает число букв в алфавите, команда будет (как и команда \alph в аналогичном случае) выдавать сообщение об ошибке. Определить эту команду (в вашем стилевом пакете) можно так:

    \newcommand*{\ralph}[1]{\@ralph{\@nameuse{c@#1}}}
    \newcommand*{\@ralph}[1]%
    {\ifcase #1\or а\or б\or в\or г\or д\or е\or ж\or з\or и\or
    к\or л\or м\or н\or о\or п\or р\or с\or т\or у\or
    ф\or х\or ц\or ч\or ш\or щ\or э\or ю\or
    я\else\@ctrerr \fi}

    (как иногда делают, мы пропускаем буквы ё, й, ъ, ы, ь). Аналогичным образом можно определить команду \Ralph, печатающую прописную букву (в этом случае "вспомогательную команду" с символом @ в имени надо тоже назвать как-нибудь по-другому, скажем, \@Ralph ). Если вы будете модифицировать это определение, не сделайте в нем пробела между буквой и \or или \else (конец строки — это тоже пробел), иначе ваша команда будет печатать лишний пробел.

    Кто кому подчинен в стандарте

    Нам осталось выполнить свое обещание и рассказать, какие счетчики определены в LaTeX'овском стандарте и каковы отношения подчинения между ними.

    В классах article и proc счетчик section определен как

    \newcounter{section}

    в то время как в классах report и book, в которых существуют еще и главы, определяется никому не подчиненный счетчик chapter для глав, а счетчик section определяется как подчиненный счетчику chapter:

    \newcounter{chapter}
    \newcounter{section}[chapter]

    Остальные счетчики номеров разделов определяются во всех четырех стандартных классах одинаково:

    \newcounter{part}
    \newcounter{subsection}[section]
    \newcounter{subsubsection}[subsection]
    \newcounter{paragraph}[subsubsection]
    \newcounter{subparagraph}[paragraph]

    Соответствующие этим счетчикам the-команды определены в классах article и proc так:

    \renewcommand{\thepart}{\Roman{part}}
    \renewcommand{\thesection}{\arabic{section}}
    \renewcommand{\thesubsection}{\thesection.\arabic{subsection}}
    \renewcommand{\thesubsubsection}%
    {\thesubsection.\arabic{subsubsection}}
    \renewcommand{\theparagraph}%
    {\thesubsubsection.\arabic{paragraph}}
    \renewcommand{\thesubparagraph}%
    {\theparagraph.\arabic{subparagraph}}

    (мы пишем \renewcommand, поскольку все эти the-команды уже получили какое-то определение при создании счетчиков).

    В классах report и book, кроме того, определена the-команда для счетчика chapter и по-другому определена \thesection:

    \renewcommand{\thechapter}{\arabic{chapter}}
    \renewcommand{\thesection}%
    {\thechapter.\arabic{section}}

    За нумерацию сносок отвечает счетчик footnote. В классах article } и proc этот счетчик определяется как никому не подчиненный:

    \newcounter{footnote}

    В классах же report и book этот счетчик подчинен счетчику chapter, так как в них присутствует еще и команда

    \@addtoreset{footnote}{chapter}

    В таком же положении, как счетчик footnote, находится и отвечающий за нумерацию формул счетчик equation: в классах article и proc он определен как никому не подчиненный, а в классах report и book он подчинен счетчику chapter. Однако же в классах report и book переопределяется \theequation:

    \renewcommand{\theequation}{\thechapter.\arabic{equation}}

    Наконец, счетчики figure и table, отвечающие за нумерацию плавающих иллюстраций и таблиц соответственно, устроены точно так же, как счетчик equation: в классах article и proc они никому не подчинены, а в двух других стандартных классах они подчинены счетчику chapter и соответствующие the-команды определены как

    \renewcommand{\thefigure}%
    {\thechapter.\arabic{figure}}

    (аналогично для table).

    Остались еще счетчики, связанные с нумерованными перечнями. Как объяснялось в лекции 7, эти счетчики, в зависимости от уровня вложенности enumerate, называются enumi, enumii, enumiii и enumiv. Все эти счетчики, естественно, последовательно подчинены друг другу, а их ссылочные префиксы определены так (это — единственный случай, когда в стандарте используются нетривиальные ссылочные префиксы):

    \renewcommand{\p@enumii}{\theenumi}
    \renewcommand{\p@enumiii}{\theenumi(\theenumii)}
    \renewcommand{\p@enumiv}{\p@enumiii\theenumiii}

    Рубрикация

    Здесь мы расскажем о том, как менять оформление разделов документа, предписываемое LaTeX'овским стандартом.

    Что нумеровать и что включать в оглавление

    Будет ли раздел документа иметь номер, зависит от двух вещей: "уровня вложенности" раздела и значения счетчика secnumdepth. Раздел документа получает номер, если уровень его вложенности меньше или равен значению secnumdepth (разумеется, все сказанное относится к случаю, когда LaTeX'овская команда для раздела документа дана без звездочки — иначе нумерации не будет заведомо). Уровни вложенности в стандартных стилях приведены в табл. 9.1

    Уровни вложенности разделов документа
    Название разделаУровень
    \section 1
    \subsection 2
    \subsubsection 3
    \paragraph 4
    \subparagraph 5

    Стало быть, если мы хотим, чтобы самый мелкий из нумеруемых разделов был \subsection, то надо написать в преамбуле документа команду

    \setcounter{secnumdepth}{2}

    Что касается команд \chapter и \part, то соответствующие разделы документа будут нумероваться тогда и только тогда, когда значение secnumdepth является неотрицательным числом.

    Какие разделы включать в оглавление, определяется другим счетчиком, а именно tocdepth: информация о разделе документа вносится в оглавление в том и только том случае, если уровень вложенности раздела меньше или равен значения этого счетчика (и раздел вводится командой без звездочки).

    Модификация команд, задающих разделы

    Теперь рассмотрим, что надо делать, чтобы более серьезным образом изменить оформление разделов. Для этого надо переопределить команды \section, \subsection и т.п., а чтобы научиться их должным образом переопределять, надо узнать, как эти команды определены в стандартных LaTeX'овских классах.

    Почти все команды для создания разделов документа определяются в классовых файлах через команду \@startsection. Например, команда \section определяется (не буквально, а по существу) так:

    \newcommand{\section}{\@startsection{section}{1}{0pt}%
    {-3.5ex plus -1ex minus -.2ex}{2.3ex plus.2ex}%
    {\normalfont\Large\bfseries}}

    В этом определении у команды \@startsection указаны шесть аргументов, в которых закодированы различные параметры оформления раздела. Разберем последовательно, что эти аргументы означают.

    Первый из аргументов (в нашем случае section) — это " внутреннее имя", под которым LaTeX будет узнавать определяемый тип разделов документа. Если вы решили использовать команду \@startsection с "нестандартным" первым аргументом (скажем, abcd), то заодно придется определить счетчик с именем abcd, который будет отвечать за нумерацию разделов, а также команду \l@abcd, которая будет отвечать за сбор материала для оглавления, и команду \abcdmark, отвечающую за передачу информации для колонтитулов,так что без надобности командой \@startsection с нестандартным первым аргументом лучше не пользоваться.

    Второй аргумент (в нашем случае 1) — это тот самый " уровень вложенности" раздела, о котором шла речь выше.

    Третий аргумент задает отступ заголовка от левого поля (в нашем случае этот отступ равен нулю).

    Четвертый аргумент команды \@startsection (в нашем случае это -3.5ex plus -1ex minus -.2ex) задает величину вертикального отступа, оставляемого перед заголовком. Точнее говоря, вертикальному отступу равен не сам четвертый аргумент, а его абсолютная величина (при определении отступа знаки - отбрасываются), а знак - означает, что первый абзац нашего раздела будет печататься без абзацного отступа, как и оформляются разделы в стандартных LaTeX'овских стилях. Если задать эти расстояния как положительные числа, то абзацный отступ в первом абзаце подавляться не будет. Тот факт, что отступ перед началом раздела имеет plus- и minus-компоненты, означает, как водится, что этот пробел обладает растяжимостью и сжимаемостью.

    Пятый аргумент (в нашем случае 2.3ex plus .2ex) задает величину вертикального отступа после заголовка раздела, а тот факт, что он положителен, означает, что заголовок раздела печатается на отдельной строке (или строках, если в строку он не умещается). Если он будет отрицательным, то заголовок раздела будет печататься не на отдельной строке, а в подбор; значение пятого аргумента \@startsection будет означать при этом (после отбрасывания знака минус, естественно) величину дополнительного горизонтального отступа между заголовком раздела и продолжающим его текстом из первого абзаца раздела.

    Пятый аргумент \@startsection тоже, как видите, может содержать plus- и/или minus-компоненту.

    Наконец, шестой аргумент команды \@startsection задает стиль оформления заголовка. Точнее говоря, в этом аргументе записан текст и/или команды, которые будут вставлены перед заголовком раздела. В нашем случае этот аргумент содержит только команды

    \normalfont\Large\bfseries

    задающие шрифт, которым заголовок будет напечатан (на последующий текст эта смена шрифта не повлияет, поскольку команды, указанные в шестом аргументе \@startsection, будут выполняться внутри группы).

    Приведем пример того, как можно изменить стандартное оформление. Пусть нам хочется, чтобы команда \section порождала раздел документа, оформленный таким образом:

  • номера разделов печатаются римскими цифрами;
  • перед номером раздела стоит знак $$\S$$ ;
  • номер раздела и его заглавие печатаются прямым светлым шрифтом размера \Large ;
  • абзацный отступ в первом абзаце не подавляется.
  • Как этого добиться? Для начала переопределим команду \thesection, определяющую, в каком виде будет представлен на печати номер раздела:

    \renewcommand{\thesection}{\Roman{section}}

    А теперь переопределим и саму команду \section следующим образом:

    \renewcommand{\section}{\@startsection{section}{1}%
    {\parindent}{3.5ex plus 1ex minus .2ex}%
    {2.3ex plus.2ex}{\normalfont\Large\S}}

    Мы воспользовались \renewcommand, поскольку команда \section ранее уже была определена. В четвертом аргументе мы убрали знаки -, чтобы не подавлять абзацный отступ, а в третьем — задали отступ заголовка от левого поля, равный абзацному отступу (причина этого не программистская, а эстетическая: некрасиво, когда первый абзац раздела идет с отступом, а заголовок начинается вплотную к левому полю). Прочие параметры, задающие размеры отступов, мы оставили такими же, как в стандартной LaTeX'овской команде: они достаточно разумны, и незачем их трогать, если на то нет особых причин.

    Как видите, для того, чтобы модифицировать оформление разделов, надо знать размеры стандартных LaTeX'овских параметров оформления, наподобие отступа перед или после заголовком. Для команды \section

    Стандартное оформление разделов
    Отступ ПередПосле
    \subsection 0pt -3.25ex plus -1ex minus-.2ex 1.5ex plus.2ex
    \subsubsection 0pt -3.25ex plus -1ex minus-.2ex 1.5ex plus.2ex
    \paragraph 0pt 3.25ex plus 1ex minus.2ex -1em
    \subparagraph \parindent 3.25ex plus 1ex minus.2ex -1em

    мы привели их выше, а для остальных стандартных команд рубрикации они собраны в табл.9.2. В ней " отступ" означает отступ заголовка от левого поля, "перед" — отступ перед заголовком (если этот отступ отрицательный, то абзацный отступ в первом абзаце будет подавлен), "после" — отступ после заголовка (если это отрицательное число, то заголовок печатается в подбор). Уровни вложенности разделов см. в табл. 9.1 , а что до "внутреннего имени" раздела (первый аргумент команды \@startsection ), то оно у всех стандартных команд рубрикации совпадает с их именем section для команды \section и т.п.). Шестой аргумент команды \@startsection содержит в стандартных определениях только команды переключения шрифта; при необходимости заинтересованный читатель воспроизведет его самостоятельно.

    Шестой аргумент команды \@startsection позволяет автоматически добавлять текст перед номером раздела. К сожалению, не так простоНо возможно: это сделано, например, в пакете {russcorr}, использованном при подготовке данной книги. См. приложения E и Ж. заставить LaTeX автоматически добавлять текст после номера, хотя такая потребность порой возникает (например, хочется, чтобы в заголовках разделов после номеров стояли точки, чего стандартное LaTeX'овское оформление не предусматривает).

    Можно заставить LaTeX ставить точки после номеров, написав

    \renewcommand{\thesection}{\arabic{section}.}

    но после этого автоматические ссылки на раздел, сгенерированные с помощью команды \ref, также будут заканчиваться точками, что нелепо.

    Оформление глав отличается от оформления остальных разделов тем, что слово "Глава" и номер главы печатаются на отдельной строке. С помощью команды \@startsection определить такой раздел нельзя, поэтому главы определяются в LaTeX'овских классах иначе. Не будем вдаваться в подробности, как именно, а вместо этого рассмотрим единственно важный для нас вопрос: как можно менять оформление глав.

    Большая часть оформления главы задается в определении команды \@makechapterhead, так что для модификации оформления именно ее и надо переопределять. Рассмотрим, как \@makechapterhead определяется в стандарте. Этой команде передается один аргумент — заголовок главы. В переводе с TeX'а на LaTeX определение выглядит так (не забудьте, что #1 — это аргумент, т. е. текст заголовка):

    \newcommand{\@makechapterhead}[1]{% Начало макроопределения
      \vspace*{50 pt}% Пустое место вверху страницы
      {\parindent=0pt
       \raggedright \normalfont\huge\bfseries
       \@chapapp{} % \@chapapp печатает слово "Глава" (см. ниже)
        \thechapter \par % номер главы - в отдельной строке
        \vspace{20 pt} % между словом "Глава" и ее заголовком
        \normalfont\Huge\bfseries #1\par % заголовок главы
        \nopagebreak     % чтоб не оторвать заголовок от текста
        \vspace{40 pt}   % между заголовком и текстом
      }% конец группы.
    }% конец макроопределения

    Разберем эту "программу". Первая команда \vspace* оставляет пустое место вверху страницы (поскольку главы начинаются с новой страницы). Далее печатается слово "Глава", ее номер и заголовок главы; поскольку заголовок может не поместиться в строку, надо предусмотреть, какие будут при этом параметры верстки абзаца. Как видите, устанавливается нулевое значение абзацного отступа и отсутствие выравнивания по правому краю; чтобы такой режим не распространился на дальнейший текст, соответствующие команды даны внутри группы. Внутри этой же группы определен шрифт, которым будет печататься заголовок.

    Команда \@chapapp печатает слово " Chapter", "Глава",... — одним словом, то, как в вашем документе называются главы. Точнее говоря, по умолчанию эта команда работает так же, как \chaptername, а после команды \appendix (если таковая есть в вашем файле) начинает работать как \appendixname. Если в вашем тексте все главы называются одинаково, то при переопределении \@makechapterhead можно не мудрить, а прямо заменить \@chapapp на "Глава". Не забудьте только оставить пробел между этим словом и номером главы (выше это было сделано с помощью обычного трюка с парой фигурных скобок).

    Остальное в приведенном выше определении разъяснений, надо думать, не требует. Скорее всего, вы захотите в этой команде изменить шрифт, которым печатается заголовок главы, или же интервалы, отделяющие заголовок от остального текста. Чтобы изменить вид, в котором представляется на печати номер главы, надо, как водится, переопределить команду \thechapter. Можно при желании задать и какое-нибудь более сложное оформление заголовка с помощью блоков и линеек — все зависит от вашей фантазии и вкуса!

    Надо еще сказать, что мы немного обманули читателя: на самом деле в стандартных классах команда \@makechapterhead определена таким образом, что если значение счетчика secnumdepth отрицательно, то команды, записанные в строках с пятой по седьмую, не исполняются (и номер главы не печатается). В нашем определении эти команды будут исполняться всегда, вне зависимости от значения secnumdepth; если вы переопределяете \@makechapterhead и не хотите, чтобы главы нумеровались, просто удалите соответствующие строки из определения.

    Кроме того, если в классе book вы переопределите \@makechapterhead, отталкиваясь от этого определения, то главы, заданные как \chapter без звездочки, будут нумероваться, невзирая на команды \frontmatter и \backmatter (но вы ведь сможете поставить две-три звездочки самостоятельно?).

    За оформление заголовка главы, определенной командой \chapter со звездочкой, отвечает команда \@makeschapterhead. Ее определение в стандарте аналогично определению \@makechapterhead, с тем отличием, что из него удален фрагмент, отвечающий за печать номера:

    \newcommand{\@makeschapterhead}[1]{%
      \vspace*{50 pt}%
      {\parindent=0pt \raggedright
        \normalfont\Huge\bfseries #1\par
        \nopagebreak
        \vspace{40 pt}}}

    Кроме оформления заголовка, с оформлением глав можно делать еще две вещи. Во-первых, главы начинаются либо просто с новой страницы (как в классе report ), либо с новой нечетной страницы (как в классе book ); чтобы повлиять на этот выбор, не надо ничего делать в личном стилевом пакете, достаточно просто указать классовую опцию openright или openany (в необязательном аргументе команды \documentclass ). Во-вторых, по умолчанию абзацный отступ в первом абзаце главы подавляется; вы можете захотеть сделать так, чтобы он не подавлялся. Чтобы решить эту проблему, надо переопределять уже саму команду \chapter, а для этого надо знать, как она определяется в стандарте. Вот соответствующее определение, опять в переводе на LaTeX с TeX'а, в классе book:

    \newcommand{\chapter}{\cleardoublepage
       \thispagestyle{plain}%
       \global\@topnum=0
       \@afterindentfalse
       \secdef\@chapter\@schapter}

    Разбирать это определение мы не будем, чтобы не запутаться в некоторых слишком хитрых TeX'овских и LaTeX'овских конструкциях, а просто скажем две вещи:

  • чтобы не подавлялся абзацный отступ в первом абзаце главы, замените \@afterindentfalse на \@afterindenttrue ;
  • если вы не хотите, чтобы на странице с заглавием главы печаталась колонцифра (номер страницы), замените аргумент команды \thispagestyle с plain на empty.
  • Что касается команды \part (" часть"), то она отличается тем, что заголовок части занимает отдельную страницу. Если вы решили изменить стандартное оформление таких "частей", то проще всего оформить соответствующие две--три страницы вручную.

    Оглавление, список иллюстраций и прочее

    Автоматическая сборка оглавления — многоэтапный процесс. Сначала материал для оглавления (заглавия разделов и номера соответствующих страниц) записывается в специальный файл с тем же именем, что и у основного файла, и расширением toc (в нормальных условиях эта запись обеспечивается командами \chapter, \section и т.д.); при следующем запуске LaTeX'а этот toc-файл считывается (с помощью команды \input ), команды, записанные в него, исполняются, и в результате происходит фактическая печать оглавления. Аналогичным образом составляются список иллюстраций и список таблиц (при этом информация записывается в файлы с расширениями lof или lot соответственно). Давайте научимся влиять на этот процесс.

    Сначала расскажем, как составлять оглавление полностью вручную, игнорируя его автоматическую сборку, обеспечиваемую командами типа \section. Итак, предположим, что все команды \section, \chapter и т.п. даны в исходном тексте в варианте со звездочкой, и посмотрим, как можно самому создать оглавление.

    Команда \addtocontents служит для записи в toc- (соответственно,lof - или lot-)- файл любого текста и любых TeX'овских команд. У этой команды два обязательных аргумента. Первый из них должен быть toc, lof или lot, в соответствии с тем, в какой из файлов с оглавлениями вы пишете свой текст. Второй аргумент — то, что вы хотите записать в файл. Если, например, вам взбрело в голову внести в оглавление к вашей книге текст "У попа была собака" (не будем спрашивать, зачем), то можете написать

    \addtocontents{toc}{У попа была собака\par}

    ( \par поставить необходимо, так как до и после выполнения каждой команды, записанной в оглавлении, TeX должен находиться в вертикальном режиме). Если после этого запустить LaTeX два раза, то вы увидите в оглавлении свой текст (после первого раза он только попадет в toc-файл, а при втором запуске toc-файл с этим текстом будет обработан).

    С помощью команды \addtocontents можно записывать в оглавление не только всякие глупости. Если, например, вы хотите в каком-то месте оглавления провести горизонтальную линейку шириной во всю страницу, то можно написать

    \addtocontents{toc}{\hrule}

    и в оглавлении появится линейка. Имейте только в виду, что в аргументе \addtocontents необходимо защищать хрупкие команды с помощью команды \protect. В случае с \hrule мы обошлись без \protect, так как эта команда не хрупка, но если есть сомнения, то лучше команду защитить. Напомним, что \protect действует только на непосредственно следующую команду и что команды для смены шрифта или установки пробелов в защите с помощью \protect не нуждаются. Приведем пример более разумного применения \addtocontents, в котором требуется \protect. Пусть вы не хотите, чтобы какая-то из строк в оглавлении начинала новую страницу. Тогда надо перед командой, порождающей эту строку оглавления (обычно таковой будет команда наподобие \section ), написать в своем файле вот что:

    \addtocontents{toc}{\protect\nopagebreak}

    В результате в toc-файл запишется команда \nopagebreak, и нежелательный разрыв страницы в оглавлении будет предотвращен. Если опустить \protect, то получится весьма непонятное сообщение об ошибке.

    При совместном использовании команд \addtocontents возникает следующий неприятный эффект. Пусть ваш файл имеет вид, скажем,

    \documentclass{book}
    \usepackage{mystyle}
    \begin{document}
    \tableofcontents
    \include{ch1}
    \addtocontents{\hrule}
    \include{ch2}
    \end{document}

    Тогда, вопреки всем ожиданиям, в оглавлении линейка окажется не между записями, отвечающими файлам ch1.tex и ch2.tex, а после записей, отвечающих файлу ch2.tex. Чтобы этого избежать, запишите команду \addtocontents в начало файла ch2.tex (самой первой строчкой).

    Чтобы составить полноценное оглавление, надо иметь возможность записать в toc - (соответственно, lof- или lot-) файл не только текст, но и номер той страницы, к которой этот текст относится. Это делается с помощью команды \addcontentsline, имеющей такой синтаксис:

    \addcontentsline{тип\_файла}{тип\_записи}{текст}

    Здесь тип_файла — это toc, lof или lot, текст — тот текст, который будет записан в оглавление (например, команда \section в стандартном стиле article в качестве этого текста передает название раздела и его номер; подробности см. ниже). Наконец, тип_записи определяет, каким образом будет обрабатываться этот текст при чтении файла с оглавлением. Именно, если второй аргумент в команде \addcontentsline был abcd, то, когда при следующем запуске LaTeX'а будет читаться toc- (соответственно, lof- или lot-) файл, будет исполнена команда \l@abcd с двумя аргументами, первый из которых - текст, записанный в третьем аргументе команды \addcontentsline, а второй - номер страницы, на которую попала ваша команда \addcontentsline. Например, если в файле было написано

    \leavevmode
    \hbox to\hsize{\verb"\addcontentsline{toc}{abcd}{О слонах}"\hfill
    $\displaystyle(*)$

    и если эта команда попала на страницу $$95$$, то при следующем запуске LaTeX'а в процессе чтения toc-файла будет исполняться команда

    \l@abcd{О слонах}{95}

    Разумеется, чтобы при этом не получилось сообщения об ошибке, надо, чтобы команда \l@abcd была определена. Стало быть, в стилевом пакете должно присутствовать ее определение. Если мы хотим, чтобы запись $$(*)$$ в исходном файле порождала в оглавлении строку

    О слонах................................ 95

    то в преамбуле надо написать вот что:

    \newcommand{\l@abcd}[2]{\hbox to\textwidth{#1\dotfill #2}}

    Чтобы при этом страница в оглавлении была указана верно, необходимо команду \addcontentsline разместить непосредственно после команды \section* (иначе есть опасность, что они попадут на разные страницы).

    Если в третьем аргументе команды \addcontentsline присутствуют "хрупкие" команды, то их следует, как водится, защитить командой \protect, если, с другой стороны, в нем записана \the -команда, соответствующая какому-то счетчику, то в toc-файл будет записано печатное представление значения этого счетчика по состоянию на тот момент, когда выполнялась \addcontentsline. Таким способом можно, например, записать в оглавление номер текущего раздела документа: достаточно сказать

    \addcontentsline{toc}{abcd}{\thesection. О слонах}

    Теперь рассмотрим, как именно собирают оглавление стандартные команды наподобие \chapter или \section. Делают они это также с помощью \addcontentsline, при этом ее второй аргумент (" тип записи") будет section для команды \section, subsection для команды \subsection, — одним словом, " внутреннее имя", под которым LaTeX знает тип разделов документа (напомним, что внутреннее имя передается в качестве первого аргумента команде \@startsection ). Стало быть, для модификации стиля оформления строк оглавления, соответствующих \section, надо переопределять команду \l@section, для модификации строк оглавления, соответствующих \subsection, надо переопределять \l@subsection и т.д. Чтобы было понятно, как их переопределять, рассмотрим, как они определены в стандарте.

    В классе book команда \l@section определена так:

    \newcommand{\l@section}{\@dottedtocline{1}{1.5em}{2.3em}}

    Смысл трех выражений, стоящих в фигурных скобках после команды \@dottedtocline, таков. Первое выражение — "уровень вложенности" элемента оглавления. Если этот уровень превышает значение счетчика tocdepth, то команда \@dottedtocline ничего в оглавлении не печатает. Второе выражение — отступ строки оглавления от левого поля. Третье выражение определяет, сколько места в строке оглавления TeX отведет на номер раздела. Результат выглядит на печати так: после отступа, указанного во втором выражении, печатается номер раздела, затем, отступя от начала этого номера столько, сколько сказано в третьем выражении, печатается заглавие раздела. Это сделано для того, чтобы заглавия всех разделов печатались в оглавлении одно под другим. После заглавия идут "лидеры" — ряд точек до завершающего строку номера страницы. Если заглавие в строку не укладывается, то оно обычным образом будет перенесено на следующую строку (если есть какие-то неясности, загляните в оглавление к этой книге). Из сказанного следует, что слишком длинный номер раздела может в оглавлении наложиться на заглавие. Средство борьбы с этим — переопределить команду \l@section (или \l@subsection...), увеличив должным образом второй аргумент команды \@dottedtocline.

    Параметры оформления элемента оглавления, задаваемого командами, определенными через \@dottedtocline, можно менять. Именно, размер места, отводимого на номер страницы, задается значением команды \@pnumwidth, которую можно переопределить. В классе book эта команда определена как

    \newcommand{\@pnumwidth}{1.55em}

    и соответственно на номер страницы отводится 1.55em места. Если мы хотим, чтобы на номер страницы отводилось \2em, надо написать

    \renewcommand{\@pnumwidth}{2em}

    Еще одна команда, значение которой отвечает за оформление оглавления, — это \@tocrmarg. Если запись в оглавлении занимает более одной строки, то значение этой команды задает отступ от правого поля, который будет у всех строк, кроме той последней, что завершается номером страницы. Если вы хотите, чтобы размер этого отступа равнялся 3em, напишите так:

    \renewcommand{\@tocrmarg}{3em}

    Хотя \@pnumwidth и \@tocrmarg используются для задания размеров, они не являются параметрами со значением длины; запись наподобие \@tocrmarg=4em приведет к ошибке!

    Наконец, регулировать густоту точек-" лидеров" можно, если переопределить команду \@dotsep. В классе book она определена как

    \newcommand{\@dotsep}{4.5}

    Если вы хотите, чтобы точки шли погуще, попробуйте переопределить ее, заменив 4.5 на число поменьше (число может быть дробным, в нем можно использовать как десятичную запятую, так и десятичную точку):

    \renewcommand{\@dotsep}{3,9}

    Напрашивающаяся запись \@dotsep=3,9 приведет к ошибке.

    Команды \l@subsection и "более мелкие" определяются в классе book так же, как \l@section, отличаются только аргументы команды \@dottedtocline. Мы собрали значения этих параметров в табл. 9.3

    Стандартные определения l@-команд
    Три аргумента \@dottedtocline
    \l@subsection 2 3.8em 3.2em
    \l@subsubsection 3 7.0em 4.1em
    \l@paragraph 4 10em 5em
    \l@subparagraph 5 12em 6em

    Теперь рассмотрим, как в стандарте определяются записи в оглавлении, соответствующие самым крупным разделам ( \chapter в классах book и report, \section в двух других классах). Вот (в адаптированном виде, как водится) определение команды \l@chapter из стандартного класса book. Чтобы было понятно, о чем идет речь, напомним, что в этом определении на место #1 подставляется информация о номере (если главы нумеруются) и названии главы, а на место #2 — номер страницы.

    \newcommand{\l@chapter}[2]%
    {\pagebreak[3]
     \vspace{1em plus 1pt}% отбивка перед строкой оглавления
       \@tempdima=1.5em % место для номера главы
       {% Дальнейшее происходит внутри группы...
         \rightskip=\@pnumwidth % см. ниже
         \parfillskip=-\@pnumwidth
         \noindent\bfseries % Начать абзац, установить шрифт
         \addtolength{\leftskip}{\@tempdima}% см. ниже
         \hspace{-\leftskip}#1\nolinebreak
         \hfil\nolinebreak
         \hbox to \@pnumwidth {\hss #2}\par
         \nopagebreak[3] % лучше бы здесь не рвать страницу...
       }% конец этой группы
    }% конец определения

    Определение, как видите, длинное и сложное, к тому же автору не удалось полностью изгнать из него не упоминавшиеся ранее TeX'овские конструкции. Приведено оно здесь не для того, чтобы вы самостоятельно создавали подобные определения "с нуля", но чтобы вы при необходимости смогли в нем кое-что осторожно изменить. Разберем определение по порядку. В начале встречаются не рассматривавшиеся нами параметры \rightskip и \leftskip. Эти параметры со значением длины (по умолчанию они равны нулю) имеют следующий смысл: все строки абзаца начинаются с отступом \leftskip от левого поля и кончаются с отступом \rightskip от правого поля (если речь идет о последней строке, то в дополнение к отступу \parfillskip ). У нас \rightskip устанавливается равным длине, записанной в определении команды \@pnumwidth (именно столько места будет отведено на номер страницы), а \leftskip устанавливается равным значению переменной \@tempdima, определяющей, сколько места будет отведено на номер главы. С другой стороны, параметр \parfillskip устанавливается равным отрицательной величине - \@pnumwidth. Тем самым, если название главы длинное и не поместится в одну строку оглавления, произойдет следующее: все строки, кроме последней, будут заканчиваться на расстоянии \@pnumwidth от правого края, а последняя строка, содержащая номер страницы, закончится на расстоянии

    \leftskip + \parfillskip =  @pnumwidth - \@pnumwidth =0,

    от края, так что номер страницы будет все-таки прижат вправо.

    Между \@pnumwidth и \@tempdima есть существенная разница. Команда \@pnumwidth всегда определяет только место, отводимое на номер страницы, и эту команду можно переопределять в стилевом пакете. С другой стороны, параметр \@tempdima используется LaTeX'ом для самых разных целей (в основном — для временного хранения различных длин в процессе каких-то вычислений), и он может измениться в процессе выполнения очень многих LaTeX'овских команд, так что присваивать ему какое-то значение в стилевом пакете совершенно бессмысленно — все равно после этого оно сто раз изменится. Как мог заметить читатель, значение этому параметру присваивается в начале исполнения команды \l@chapter, и именно это значение принимается в расчет в дальнейшем. Поэтому, если вы захотите отводить на номер главы, скажем, 2em вместо 1.5em, то вам придется переопределить команду \l@chapter, заменив третью строку на

    \@tempdima=2em

    Нужда в таком переопределении \l@chapter возникает, например, если мы переопределяем команду \thechapter, чтобы номер печатался римскими цифрами (как в книге, которую вы читаете). Далее, #1 - это, как уже было сказано, номер и заглавие главы. Точнее говоря, на месте #1 печатается такой текст (будем считать, что глава называется "Все о слонах"):

    \makebox[\@tempdima][l]{\thechapter}Все о слонах

    Таким образом, величина отступа от левого поля до названия главы всегда равна \@tempdima ; если номер занимает больше места, чем \@tempdima, то он наложится на название.

    Команда \hfil в двенадцатой строке обеспечивает пробел между названием главы и номером страницы. Если вы хотите заполнить этот пробел лидерами, можете в определении \l@chapter заменить \hfil на, скажем,

    \leaders\hbox to .5em{\hss.\hss}\hfil

    (автор не гарантирует, что именно при таком выборе параметров лидеры будут выглядеть красиво).

    Наконец, команды \pagebreak[3] в начале и \nopagebreak[3] в конце играют следующую роль: первая из них призывает LaTeX не печатать, по возможности, строку оглавления, соответствующую главе, внизу страницы, а вторая — не разрывать страницу сразу после строки, посвященной главе (опять же по возможности).

    Имейте также в виду, что мы удалили из нашего упрощенного определения \l@chapter проверку значения счетчика tocdepth, так что если вы в какой-то момент решите не включать главы в оглавление, эту команду надо будет переопределить на "ничего не делать" так:

    \renewcommand{\l@chapter}[2]{}

    Команды, определяющие вид записей в списке иллюстраций (соответствующих плавающим иллюстрациям) и списке таблиц (соответствующих плавающим таблицам) называются \l@figure и \l@table соответственно и определяются в стандарте с помощью \@dottedtocline.

    До сих пор речь шла о сборке материала для оглавления, списка иллюстраций и т.п. Однако же и у самого оглавления есть заголовок, и его оформление тоже можно менять. Чтобы было понятно, как это делать, опишем, как определена команда \tableofcontents стандартное определение} в стандартном стиле article:

    \newcommand{\tableofcontents}%
    {\section*{\contentsname}\@starttoc{toc}}

    Здесь \contentsname — это уже знакомая нам команда, которую при работе с русскими текстами приходится переопределять. Как видите, заголовок оглавления оформляется просто как заголовок ненумерованного раздела. Вы можете вместо этого оформить заголовок, скажем, с помощью \subsection, или еще каким-либо образом. Новой для вас будет команда \@starttoc. У этой команды предусмотрен один обязательный аргумент. Этим аргументом должен быть toc (для оглавления), либо lot или lof (для списка таблиц или иллюстраций соответственно). Команда \@starttoc читает toc- (соответственно, lot- или lof-) файл и создает оглавление как таковое.

    На самом деле в определении \tableofcontents присутствует еще команда, позволяющая задать текст для включения в колонтитулы (вспомним, что \section* сама по себе никакой информации для колонтитулов не дает). Мы не будем здесь вдаваться в скучные подробности. Когда вы научитесь задавать такие команды, вы сможете соответствующим образом переопределить и \tableofcontents.

    Перечни общего вида

    В этом разделе мы завершим рассказ о том, как менять стиль оформления перечней. В лекции 3 мы назвали перечнями окружения {itemize}, {enumerate} и {description} ; помимо этого, к перечням в LaTeX'овском смысле относятся {flushleft}, {flushright}, {center}, {quote}, {quotation}, {verse}, а также окружения, создаваемые с помощью \newtheorem ; как мы увидим в лекции 5, все эти окружения — частные случаи одной LaTeX'овской конструкции. Поэтому многие параметры оформления этих окружений устанавливаются и модифицируются по единой схеме.

    Отбивки в перечнях

    Начнем с важного предупреждения. Чтобы изменить отбивки, с помощью которых оформляются перечни, необходимо, естественно, изменить значение каких-то из перечисляемых в этом разделе параметров. Однако же, если попросту присвоить этим параметрам новые значения в преамбуле или в стилевом пакете, то в большинстве случаев действия это не возымеет. Средства, которые надо применить, чтобы эти изменения подействовали, описаны в следующем подразделе.

    Теперь договоримся о терминологии. Каждый перечень LaTeX рассматривает как состоящий из элементов (каждый элемент вводится, как мы помним, командой \item ). В свою очередь, каждый элемент перечня может состоять из одного или нескольких абзацев. Наконец, у каждого элемента перечня есть свой заголовок — " горошина" на первом уровне окружения {itemize}, заданный вами заголовок в окружении {description} и т.п. (У некоторых перечней — например, таковы "теоремы" — перечень состоит из одного-единственного элемента; у таких перечней, как {quote} или {verse}, кроме того, заголовок к этому единственному элементу всегда пуст.)

    Вооружившись этими терминами и имея в виду предупреждение, приступим к утомительному перечислению параметров. Все они — параметры со значением длины. Во-первых, параметры \leftmargin и \rightmargin задают, с каким отступом от левого (правого) поля начинается (заканчивается) текст элементов перечня (полиграфист сказал бы: насколько втянуты элементы перечня). Если перечень вложен в другой перечень, то \leftmargin и \rightmargin обозначают величину втяжки по отношению к объемлющему перечню.

    Следующие два параметра влияют на размещение заголовков в перечне. Параметр \labelsep задает расстояние между правым краем заголовка и началом текста в элементе перечня, к которому относится этот заголовок, а параметр \labelwidth задает место по горизонтали, которое по умолчанию занимает заголовок. Точный смысл этих параметров следующий. При обработке перечня LaTeX сначала пытается поместить заголовок в блок шириной \labelwidth. Если места хватает, то именно в такой блок он и помещается, причем выключенным вправо: правый край блока при этом находится на расстоянии \labelsep от начала текста, составляющего элемент перечня (так что его левый край будет на расстоянии

    \leftmargin - \labelwidth - \labelsep

    от левой границы основного текста или объемлющего перечня). Если же ширина заголовка больше, чем \labelwidth, то заголовок печатается как есть. Такое, например, регулярно случается при пользовании окружением {description}.

    Мы не сказали еще об одном параметре, влияющем на размещение заголовков. Именно, если параметр \itemindent отличен от нуля, то каждый заголовок перечня будет дополнительно сдвинут на это расстояние вправо. Соответственно, при определении, на каком расстоянии начинается заголовок элемента перечня, надо будет прибавить значение \itemindent к тому, что получается по формуле $$(*)$$. По умолчанию значение этого параметра равно нулю.

    Если элемент перечня состоит из нескольких абзацев, то по умолчанию во всех этих абзацах абзацный отступ будет отсутствовать. Можно, однако, при желании задать такой режим, что во всех, кроме первого, абзацах каждого элемента перечня будет присутствовать абзацный отступ. Для этого надо задать ненулевую величину этого отступа в параметре \listparindent. Кстати, значение этого параметра может быть и отрицательным (в этом случае эффект будет похож на тот, что достигается в обычном тексте установкой параметров \hangindent и \hangafter ).

    Параметры, о которых шла речь до сих пор, относились к размещению материала по горизонтали. Теперь займемся "вертикальными" параметрами. Сразу отметим, что все эти параметры являются " растяжимыми" длинами, т.е. у них можно задавать plus- и minus -компоненты.

    Первый (и основной) из этих параметров называется \topsep. Это величина дополнительного вертикального интервала, который делается перед перечнем и после него (в дополнение к \parskip ).

    Если перед перечнем оставлена пустая строка (или имеется команда \par ), то перед и после перечня устанавливается еще и вертикальный отступ, равный \partopsep (в дополнение к отступам, заданным параметрами \parskip и \topsep ).

    Далее, вертикальный отступ между абзацами внутри одного элемента задается параметром \parsep (а не \parskip, как в обычном тексте). Между различными же элементами перечня, в дополнение к \parsep, оставляется еще и вертикальный отступ \itemsep. Таким образом, если \itemsep отличен от нуля, как это и сделано в стандартных классах, то различные элементы перечня будут более отделены друг от друга, чем абзацы внутри одного элемента перечня.

    Изменение отбивок в перечнях

    Теперь настало время объяснить, как именно можно менять вышеописанные параметры. При "входе" в перечень LaTeX в первую очередь вычисляет уровень вложенности перечней: если перечень не вложен ни в какой другой, то этот уровень равен 1, для перечня, вложенного в перечень, уровень равен 2 и т. д. После этого исполняется команда \@listI, если уровень равен 1, \@listii, если уровень равен 2, и т.д.: имя команды — слово @list, к которому добавлен уровень вложенности, записанный римскими цифрами (если уровень вложенности равен 1, то римская цифра записывается прописной буквой I, в остальных случаях римские цифры записываются строчными латинскими буквами). В стандартных классах команды \@listI, \@listii и т.п. определены таким образом, что они в момент входа в перечень устанавливают значение параметров оформления перечня на соответствующем уровне. Именно поэтому переустановка (некоторых из) параметров перечня в стилевом пакете может ничего не дать.

    Итак, чтобы менять отбивки в перечнях, надо переопределять команды \@listI, \@listii, ..., \@listvi. Видимо, самое практичное — переопределить в своем стилевом пакете команды \@listI, \@listii, ..., \@listvi (или не все из них — в зависимости от того, какова реальная максимальная глубина вложенности перечней в вашем документе), присвоив всем перечисленным в предыдущем разделе десяти параметрам явные значения. Например, можно написать что-нибудь в таком роде:

    \renewcommand{\@listI}{%
    \leftmargin=25pt
    \rightmargin=0pt
    \labelsep=5pt
    \labelwidth=20pt
    \itemindent=0pt
    \listparindent=0pt
    \topsep=8pt plus 2pt minus 4pt
    \partopsep=2pt plus 1pt minus 1pt
    \parsep=0pt plus 1pt
    \itemsep=\parsep}

    Здесь всем параметрам оставлены стандартные значения, за исключением \parsep и \itemsep: в отличие от положительных значений, задаваемых в стандарте, мы устанавливаем их такими же, как обычная вертикальная отбивка между абзацами (как вы помните, она обозначается \parskip и обладает нулевым естественным размером и растяжимостью 1pt). На взгляд автора, такие перечни смотрятся лучше.

    Если какой-то из параметров (например, \labelsep ) одинаков в перечнях всех уровней, то достаточно прописать его установку только в определении \@listI: при входе в перечень верхнего уровня этот параметр будет установлен командой \@listI, и LaTeX будет его помнить, пока не выйдет из " наружного" перечня.

    Окружения list и trivlist

    Все LaTeX'овские перечни являются на самом деле частными случаями одной общей конструкции — окружения list. Рассмотрим, как это окружение работает.

    Окружение list имеет два обязательных аргумента. Общий вид этого окружения в исходном тексте будет такой:

    \begin{list}{заголовок\_по\_умолчанию}{команды}
    ...
    \end{list}

    Аргументы окружения list означают следующее. "Заголовок по умолчанию" — это заголовок элемента перечня, печатающийся в том случае, когда этот элемент перечня вводится командой \item без аргумента. Пример:

    $$\begin{list}{И какой-то}{ \leftmargin=20pt \rightmargin=40pt \labelsep=5pt \labelwidth=0pt \itemindent=0pt %\listparindent=0pt \topsep=8pt plus 2pt minus 4pt \partopsep=2pt plus 1pt minus 1pt %\parsep=0pt plus 1pt \itemsep=\parsep %\itemsep=0pt } \item малыш пока\-зал ему шиш. \item бар\-бос укусил его в нос. Нехороший бар\-бос, невоспитанный! \end{list}$$
    \begin{list}{И какой-то}{}
    \item малыш показал ему шиш.
    \item барбос укусил его в нос.
    Нехороший барбос, 
    невоспитанный!
    \end{list}

    Аргумент команды окружения list содержит те команды, которые будут исполнены после входа в перечень. Поэтому в нем можно задать команды, присваивающие новые значения параметрам оформления перечня (в частности, отбивкам, описанным в лекции 5: эти команды будут выполнены после команды \@list..., выполняющейся при входе в перечень). Кроме этого, во втором аргументе окружения list можно поместить команду \usecounter. Эта последняя требует одного обязательного аргумента — имени счетчика (счетчик должен быть определен). Если \usecounter присутствует во втором аргументе окружения list, то при входе в окружение значение счетчика, являющегося аргументом \usecounter, будет установлено в нуль, а каждая команда \item без аргумента будет увеличивать его на единицу с помощью \refstepcounter (так что на значения этого счетчика можно будет ссылаться с помощью \label и \ref ). Вот пример c \usecounter (подразумевается, что у нас определен счетчик tmp):

    $$Вот как выглядят первые буквы латинского алфавита: \begin{list}{\Alph{tmp}:}% {\usecounter{tmp}} \item Выглядит так же, как соответствующая русская буква, и читается так же. \item Читается не так, как похожая на нее русская буква. \item И с ней та же история. \end{list}$$
    Вот как выглядят первые 
    буквы латинского алфавита:
    \begin{list}{\Alph{tmp}:}%
    {\usecounter{tmp}}
    \item Выглядит так же, как
    соответствующая русская
    буква, и читается так же.
    \item Читается не так,
    как похожая на нее
    русская буква.
    \item И с ней та же 
    история. \end{list}

    Чтобы заголовки элементов перечня выравнивались по левому краю, а не по правому, можно завершить "заголовок по умолчанию" командой \hfill ; чтобы по левому краю выравнивались заголовки, заданные в явном виде в необязательном аргументе команд \item, нужно завершить командой \hfill этот необязательный аргумент.

    Окружением list разумно пользоваться не непосредственно, как в приведенных примерах, а для определения нового окружения с помощью \newenvironment. Вот, например, как в стандарте определяется окружение {quote}:

    \newenvironment{\quote}%
    {\begin{list}{}{\rightmargin=\leftmargin}\item[]}}%
    {\end{list}}

    Команда \item с пустым аргументом необходима, поскольку до команды \item в перечне не должно быть никакого текста.

    Наряду с окружением list в LaTeX'е определен его важный частный случай — окружение trivlist. Его отличия от list таковы:

  • это окружение не требует аргументов (так же, как и все окружения для создания перечней, с которыми мы имели дело раньше);
  • \leftmargin, \labelwidth и \itemindent для него всегда равны нулю (стало быть, текст печатается без втяжки); \parsep равно \parskip ;
  • команда \item, употребленная внутри этого окружения, обязана иметь аргумент (хотя бы пустой).
  • Как видите, многие возможности перечней в этом окружении не работают, но сохраняются такие важные черты, как \topsep (дополнительный интервал перед и после) плюс обычное свойство первой строки после перечня: она делается без абзацного отступа тогда и только тогда, когда после окружения в исходном тексте не оставлено пустой строки. Окружение trivlist также применяют обычно не само по себе, а для определения новых окружений; при этом в "открывающие команды" \newenvironment добавляют команду \item[], а внутри окружения \item вообще не используют. Иногда используют и \item с аргументом (пример тому вы увидите ниже, в лекции 8).

    Окружения list можно вкладывать друг в друга; максимальная глубина вложенности равна шести. В окружениях наподобие {itemize} предусмотрен "ограничитель", снижающий эту макимальную глубину до четырех. В личном стилевом файле, не рассчитанном на общее пользование, предусматривать такой ограничитель большого смысла нет: просто следите за тем, чтобы не вкладывать слишком много list'ов друг в друга.

    Колонтитулы

    Страницу документа, подготовленного с помощью LaTeX'а, можно рассматривать как состоящую из трех частей: тела страницы, верхнего колонтитула и нижнего колонтитулаЭта терминология не совпадает с традиционной, но удобна для наших целей... Мы знаем, что с помощью команды \pagestyle на оформление колонтитулов можно в какой-то мере влиять. Возможностей для этого, однако же, не слишком много. Сейчас мы увидим, как можно радикально менять вид колонтитулов.

    За оформление верхних колонтитулов отвечают команды \@oddhead и \@evenhead. Точнее говоря, если стиль оформления документа "двусторонний", то команда \@oddhead задает верхний колонтитул на страницах с нечетными номерами, а команда \@evenhead — на страницах с четными номерами. Если же стиль оформления документа " односторонний", то \@oddhead задает все верхние колонтитулы, а команда \@evenhead на оформление документа вообще не влияет. Аналогично обстоит дело с \@oddfoot и \@evenfoot, отвечающими за нижние колонтитулы. Все четыре названные команды получают некоторое определение в LaTeX'овском стандарте, так что переопределять их надо с помощью \renewcommand.

    Теперь обсудим, как вышеназванные команды влияют на оформление колонтитулов. Основной принцип таков. При оформлении страницы верхний колонтитул получается в результате исполнения команды

    \hbox to\textwidth{\@evenhead}

    (мы предположили, что стиль двусторонний и страница четная; в других случаях — с очевидными изменениями). Можно сказать, что в каждой из команд \@evenhead и ей подобных записан текст и TeX'овские команды, которые при верстке страницы будут подставлены в \hbox to \textwidth.

    Пусть, например, мы готовим к изданию роман Л.Н.Толстого " Война и мир"; стиль документа выберем двусторонний. Предположим, что мы выбрали такое оформление:

  • на левой странице разворота в верхнем колонтитуле написано имя автора, прижатое (выключенное) вправо;
  • на правой странице разворота в верхнем колонтитуле написано название романа, прижатое (выключенное) влево;
  • В нижних колонтитулах по центру расположен номер страницы, окруженный тире.
  • Тогда надо переопределить команды для колонтитулов так:

    \renewcommand{\@evenhead}{\hfil Л.Н.ТОЛСТОЙ}
    \renewcommand{\@oddhead}{ВОЙНА И МИР\hfil}
    \renewcommand{\@evenfoot}{\hfil --- \thepage ---\hfil}
    \renewcommand{\@oddfoot}{\hfil --- \thepage ---\hfil}

    Если мы хотим, чтобы каких-то колонтитулов вообще не было, то надо переопределить соответствующую команду на "ничего не делать", например, так:

    \renewcommand{\@oddfoot}{}

    Итак, мы научились менять оформление колонтитулов, переопределяя команду \@evenhead и ей подобные. А теперь — важное предупреждение: команда \pagestyle также переопределяет команды типа \@evenhead ; если вы проведете переопределения в своем стилевом пакете, то первой же командой \pagestyle ваши переопределения будут отменены. Стало быть, если уж вы переопределяете команды наподобие \@evenhead, то после этого переопределения командой \pagestyle в документе пользоваться не надо ( \thispagestyle можно).

    Прежде чем перейти к более сложным вещам, скажем еще о трех стилевых параметрах. Во-первых, интервалы между колонтитулами и текстом регулируются параметрами со значением длины \headsep, задающим интервал между верхним колонтитулом и текстом, и \footskip, задающим расстояние между базисной линией последней строки в теле страницы и базисной линией нижнего колонтитула. Во-вторых, существует параметр \headheight, задающий высоту верхних колонтитулов. Если сумма высоты и глубины заданного вами колонтитула будет превышать \headheight, то при трансляции вы получите сообщение

    Overfull \vbox occurred while \output was active.

    Приведем пример, когда надо учитывать \headheight. Пусть мы хотим в том же издании "Войны и мира" отделять верхние колонтитулы от текста линейками. Разумный способ это сделать — передать в \hbox to \textwidth уже готовый блок шириной \textwidth, содержащий как текст колонтитула, так и линейку. Так как линейку под текстом удобно проводить в вертикальном режиме с помощью команды \hrule, в голову приходит вот что (здесь и далее мы для краткости приводим только определение \@evenhead ):

    \renewcommand{\@evenhead}%
    {\vbox{\hbox to\textwidth{\hfil Л.Н.ТОЛСТОЙ}\hrule}}

    У такого определения есть, однако, два недостатка. Во-первых, так как линейки в вертикальном режиме добавляются "впритык" к предшествующему блоку, у нас нет гарантии, что линейка не подойдет к тексту слишком близко; если бы к тому же текст в колонтитулах на разных страницах варьировался, как в дальнейших примерах, то может случиться и так, что две соседние линейки на развороте окажутся на разной высоте (из-за того, что в колонтитуле на одной странице будет буквы вроде у, опускающиеся ниже базисной линии, а на другой — нет). Средство от этого недостатка — добавить \strut в наш блок:

    \renewcommand{\@evenhead}%
    {\vbox{\hbox to\textwidth{\hfil \strut
    Л.Н.ТОЛСТОЙ}\hrule}}

    Второй недостаток — это то, что к размеру блока с текстом добавится ширина линейки, в результате чего этот размер превысит \headheight и мы будем получать уйму сообщений об overfull'е. Чтобы уйти от этого, надо еще чуть-чуть схитрить:

    \renewcommand{\@evenhead}%
    {\raisebox{0pt}[\headheight][0pt]{% начало блока
    \vbox{\hbox to\textwidth{\hfil \strut
    Л.Н.ТОЛСТОЙ}\hrule}}% конец блока
    }% конец макроопределения

    Понятно ли, что происходит? С помощью \raisebox мы заставляем TeX считать, что блок имеет высоту \headheight (нам даже незачем вникать, чему она фактически равна) и нулевую глубину (чтобы в сумме получилось то, что надо). Теперь ни о каких переполнениях речи не будет; пробел между колонтитулом и текстом можно при желании изменить, изменив значение \headsep.

    Для нижних колонтитулов параметра, аналогичного \headheight, нет, так что смело делайте их любой высоты.

    Кстати говоря, команду \@evenhead в этом примере можно было бы переопределить более простым образом, без \vbox, с использованием команды \underline. Наш способ, однако, более гибок: например, мы можем регулировать толщину линейки, чего с \underline не добьешься.

    Итак, мы научились создавать собственные колонтитулы. Однако в LaTeX'овском стандарте в колонтитулы обычно помещается не только номер страницы, но и, например, номер и заглавие текущего раздела. Давайте научимся делать и это.

    Чтобы передать в колонтитул какую-то информацию из текста, в LaTeX'е используются команды \markboth и \markright. Разберем, как они работают. Команда \markboth, требующая двух обязательных аргументов, запоминает пару " пометок" — два фрагмента текста (возможно, с TeX'овскими командами). Например, если мы скажем (где-нибудь между абзацами)

    \markboth{Кот}{Пес}

    то поместим между этими абзацами пару пометок: "левую пометку" Кот и "правую пометку" Пес. Сами по себе эти пометки никак не отражаются на печати. Однако же в определениях команд \@oddhead и ей подобных мы можем на эти пометки ссылаться. Именно, в этих определениях команда \leftmark дает левую пометку, а команда \rightmark — правую пометку. Например, если мы переопределим верхние колонтитулы как

    \renewcommand{\@evenhead}{\leftmark\hfil}
    \renewcommand{\@oddhead}{\hfil\rightmark}

    то, начиная с той страницы, на которую попали наши пометки, в левом верхнем колонтитуле будет стоять выключенное влево слово "Кот", а в правом — выключенное вправо слово " Пес"Точнее говоря, так будет, если в тексте нет команд типа \section: эти команды, как мы увидим ниже, автоматически вставляют в текст свои пометки, что усложняет картину.. Кстати, если никаких пометок в тексте нет, то как \leftmark, так и \rightmark дают " пустой" текст.

    До сих пор мы молчаливо предполагали, что на каждой странице присутствует только одна пара пометок. Что будет, если таких пар пометок попадет на страницу несколько? Ответ: команда \leftmark в этом случае означает левую пометку из самой верхней пары пометок, попавших на страницу, а команда \rightmark означает правую пометку из самой нижней пары пометок, попавших на данную страницу. С другой стороны, если на страницу вообще ни одна пара пометок не попала, то \leftmark и \rightmark означают соответственно левую и правую пометки из последней пары пометок, встретившихся до этого.

    Поясним сказанное примером. Пусть пометки

    \markboth{x}{y} и \markboth{z}{t}

    попали (в указанном порядке) на страницу 1, на страницу 2 вообще никаких пометок не попало, на страницу 3 попали целые три пары пометок:

    \markboth{u}{v},
    \markboth{a}{b} и
    \markboth{m}{n},

    а на страницах 4 и дальнейших никаких новых пометок не появлялось. Тогда значения команд \leftmark и \rightmark в процессе обработки этих страниц были таковы:

    Страница\leftmark\rightmark
    1 $$x$$ $$t$$
    2 $$z$$ $$t$$
    3 $$u$$ $$n$$
    4 и далее $$m$$ $$n$$

    Наряду с командой \markboth, которая ставит в тексте новую пару пометок, есть еще и команда \markright с одним аргументом, которая ставит в тексте пару пометок таким образом: левый элемент в этой паре — такой же, как был в предыдущей паре пометок, а правый — тот, что задан в аргументе команды \markright. Например, если сначала идет команда

    \markboth{Кот}{Пес}

    а затем команда

    \markright{Собака}

    (и в промежутке между этими командами никаких других пометок в текст не вносится), то это равносильно тому, как если бы вторая из этих команд была

    \markboth{Кот}{Собака}

    Выше мы уже отмечали, что команды типа \section ставят в тексте пометки автоматически. Понять, как это делается и как можно влиять на этот процесс, проще всего на примере. Сделаем такие предположения о документе: класс — article, разделы и подразделы нумеруются (иными словами, значение счетчика {secnumdepth} больше единицы), действует стилевая опция twoside и в преамбуле была дана команда \pagestyle{headings}.

    Во-первых, отметим, что в этом случае пометки в текст вставляют только команды \section и \subsection. При этом команда \section ставит пометки, автоматически выполняя команду \sectionmark, имеющую один обязательный аргумент — заглавие раздела (если команда \section была дана без необязательного аргумента) или вариант заглавия, заданный в необязательном аргументе команды \section (если таковой присутствует). Вот как определена \sectionmark (на место #1 будет подставляться вариант заглавия, идущий в колонтитулы):

    \newcommand{\sectionmark}[1]{\markboth{%
    \MakeUppercase{\thesection\hspace{1em}#1}}% левая пометка
    {}% правая пометка (она пуста)
    }% конец макроопределения

    Здесь используется LaTeX'овская команда \MakeUppercase, которую мы ранее не рассматривали. Не вдаваясь в подробности, скажем, что эта команда переводит все буквы в текстеНо не в именах команд; что будет с русскими буквами, зависит от русификации., попавшем в ее аргумент, из строчных в прописные. Коль о том зашла речь, отметим, что есть еще и команда \MakeLowercase, которая наоборот переводит все буквы в тексте, попавшем в ее аргумент, из прописных в строчные. (Не пытайтесь, пожалуйста, использовать \MakeUppercase и \MakeLowercase вне аргументов \markboth или \markright, если не любите неприятных сюрпризов.) Если вы не хотите, чтобы в колонтитулах строчные буквы заменялись на прописные, можно при переопределении просто опустить команду \MakeUppercase (так и было сделано при оформлении книги, которую вы читаете).

    Команда \subsectionmark, определяющая вид пометок, автоматически вставляемых в текст командой \subsection, определена следующим образом:

    \newcommand{\subsectionmark}[1]{\markright
    {\thesubsection\hspace{1em}#1}}

    Здесь также аргумент #1 — это заглавие подраздела (точнее, его вариант для колонтитулов).

    Итак, в рассматриваемом нами случае команда \section вносит в текст следующую пару пометок: заглавие раздела, в котором все буквы заменены на прописные, в качестве левой пометки, и пустой текст в качестве правой пометки. Команда же \subsection вносит в текст пару пометок, в которой левая пометка такая же, как в предыдущей паре, а правая — заглавие подраздела (точнее, его вариант для колонтитулов), причем на сей раз "в натуральном виде", без замены строчных букв на прописные. Как уже отмечалось выше, команды \subsubsection и более мелкие никаких пометок в текст не вносят.

    Посмотрим, как в этом стиле используются пометки. Колонтитулы на четных страницах в этом случае определены так:

    \newcommand{\@evenhead}{\thepage\hfil
                  \normalfont\slshape\leftmark}

    Тем самым на страницах с четными номерами (они будут левыми на развороте) колонтитул будет выглядеть следующим образом: выключенный влево номер страницы (прямым шрифтом) и заглавие текущего раздела (наклонным шрифтом, прописными буквами) — выключенное вправоТочнее говоря, это будет заглавие либо текущего раздела, либо первого из разделов, начинающихся на этой странице — см. выше обсуждение \leftmark и \rightmark .: ведь никаких других левых пометок в тексте нет!

    Команда \@oddhead, отвечающая за верхние колонтитулы на страницах с нечетными номерами, определена в стиле article (при условии, что была команда \pagestyle{headings} ) так:

    \newcommand{\@oddhead}{{\normalfont\slshape\rightmark}%
                  \hfil\thepage}

    Стало быть, верхние колонтитулы к нечетным страницам выглядят так: название текущего подраздела наклонным шрифтом — выключенное влево, номер страницы прямым шрифтом — выключенный вправо. Впрочем, если в текущем разделе команд \subsection еще не было, то вместо заглавия будет пустое место, так как \rightmark будет пуста (определение команды \sectionmark, данное выше, показывает, что при исполнении команды \section в текст вносится пустая правая пометка, и пустой она остается до первой команды \subsection ).

    Приведем пример переопределения команд наподобие \sectionmark. Если нам не нравится, что в правом колонтитуле иногда бывает пустое место, то можно попросить команду \section вносить в текст непустую правую пометку — то же заглавие раздела. Для этого напишем в преамбуле так:

    \newcommand{\sectionmark}[1]{\markboth
    {\uppercase{\thesection\hspace{1em}#1}}% левая пометка
    {\uppercase{\thesection\hspace{1em}#1}}% правая пометка
    }% конец макроопределения

    Теперь, если в разделе нет подразделов, то на правых страницах в верхнем колонтитуле будет также печататься заглавие текущего раздела. Оформление колонтитулов при этом будет стандартным. Если вы хотите еще и отойти от этого стандарта, то надо будет, вместо использования команды \pagestyle, напрямую переопределить команды типа \@oddhead и \@evenhead ; надо думать, теперь вы найдете, как применить в этих определениях команды \leftmark и \rightmark.

    Если в документе присутствует команда \pagestyle (с каким бы то ни было аргументом), то она отменит ваши переопределения команд типа \sectionmark. Поэтому все команды \pagestyle должны идти до ваших личных переопределений команд типа \@evenhead.

    Если вы вообще не хотите, чтобы при исполнении, скажем, команды \subsection в текст вносились какие-либо пометки, то можно "отключить" команду \subsectionmark, переопределив ее на "ничего не делать":

    \renewcommand{\subsectionmark}[1]{}

    Бывает и так, что вас устраивает стандартный стиль оформления колонтитулов, но при этом не устраивает, что именно в эти колонтитулы автоматически записывается. Например, у ваших разделов длинные заглавия, и вы при этом хотите, чтобы они в несокращенном виде попали в оглавление, а сокращенные варианты заглавий пошли только в колонтитулы. Команда \section с необязательным аргументом тут не спасет, так как этот необязательный аргумент запишется и в оглавление тоже. Вот бы задать информацию для колонтитулов вручную, без того, чтобы это автоматически делали команды типа \section! Можно, конечно, переопределить на "ничего не делать" все команды типа \sectionmark, как в приведенном выше примере, но LaTeX предоставляет вам более простой способ. Если написать в стилевом файле (до того, как вы переопределяете команды наподобие \@oddhead )

    \pagestyle{myheadings}

    то все LaTeX'овские команды для создания разделов не будут вносить пометок в текст, а оформление колонтитулов будет стандартным. После этого можно самостоятельно переопределить \@oddhead и пр., если вам это нужно: пометки в текст командами рубрикации вноситься все равно не будут.

    Теперь вы сможете, например, писать

    \section
    {О некоторых специальных свойствах
    подмножеств пустых множеств, не рассматривавшихся
    в предыдущих разделах статьи}%
    \markboth{\thesection\hspace{1em}Подмножества}{}

    и в оглавлении будет заголовок целиком, а в колонтитуле — лишь слово "Подмножества" (мы подразумеваем, что стиль все тот же, только аргументом команды \pagestyle был myheadings вместо headings). Команда \markboth помещена после команды \section, чтобы номер раздела, генерируемый командой \thesection, был правильным. Кроме того, мы убрали с помощью знака процента пробел (конец строки) между командами \section и \markboth, чтобы пометки с гарантией попали на ту же страницу, что и заголовок раздела.

    Другие команды, отвечающие за автоматическую расстановку пометок в тексте, устроены аналогичным образом: команда \chapter ставит пометки с помощью команды \chaptermark, команда \section — с помощью команды \sectionmark и т. д. — вообще, если команда, генерирующая раздел документа, определена с помощью \@startsection с первым аргументом abcd, то она будет ставить пометки с помощью команды \abcdmark. Все эти команды автоматически выполняются в процессе выполнения соответствующей команды, генерирующей раздел. Они должны иметь один обязательный аргумент, в качестве которого им передается заглавие раздела (точнее, вариант этого заглавия, предназначенный для колонтитулов и оглавления). Варианты "со звездочкой" команд, генерирующих разделы документа, никаких пометок в текст не вносят (как и следовало ожидать).

    Если в аргументе команды \markboth или \markright присутствует не только текст, но и какие-то команды, то в пометки будут записаны не буквально эти команды, но их значение на момент запоминания пометок. Например, если в аргументе \markboth присутствует команда \thesection, то в пометку реально запишется (а потом и прочтется из \leftmark или \rightmark ) номер раздела. Если же необходимо, чтобы какая-то команда записалась в пометку в том же виде, в каком она была задана в аргументе \markboth или \markright, то надо "защитить" ее, поставив перед ней \protect.

    Еще один случай, когда пометки в текст вносятся LaTeX'ом автоматически, возникает при оформлении таких фрагментов документа, как оглавление, список иллюстраций или таблиц, список литературы и предметный указатель. Как именно они вносятся, зависит от класса документа и от того, пользовались ли мы (и как пользовались) командой \pagestyle. Именно, если класс — article, то никаких пометок при оформлении оглавления и т.п. в текст автоматически вноситься не будет; точно так же не будет этих пометок в любом классе после того, как выполнится команда \pagestyle с аргументом empty, plain или myheadings. С другой стороны, если класс документа — report или book, то, например, при исполнении команды \tableofcontents автоматически выполняется и команда

    \markboth{\contentsname}

    (с очевидными изменениями для списка иллюстраций и т.п.). Та же ситуация возникнет и после исполнения команды \pagestyle с аргументом headings (даже тогда, когда класс — article).

    Итак, вы теперь имеете широкие возможности для создания собственного оформления колонтитулов. Во-первых, можно написать

    \pagestyle{myheadings}

    При этом внешний вид колонтитулов будет стандартный, но материал для колонтитулов вы будете поставлять вручную с помощью команд \markboth и/или \markright. Во-вторых, можно переопределять команды типа \sectionmark ): при этом внешний вид колонтитулов будет по-прежнему стандартный, но материал для помещения в колонтитул будет отбираться автоматически по схеме, отличной от стандартной. В-третьих, можно переопределять команды типа \@oddhead: при этом вы меняете как стиль оформления колонтитулов, так и способ обращения с пометками, вносимыми в текст (в частности, если в ваших определениях команд типа \@oddhead не участвуют \leftmark и \rightmark, то эти пометки будут вообще проигнорированы). Наконец, можно объединить второй и третий подходы. При этом вы самостоятельно разрабатываете как внешний вид колонтитулов, так и то, какая информация из текста и как будет в них отражена.

    Плавающие объекты

    Этот раздел посвящен плавающим иллюстрациям и таблицам (короче: плавающим объектам).

    Оформление подрисуночной подписи

    Обсудим, как можно менять оформление подписи под рисунком (или таблицей), создаваемой командой \caption ).

    Над и под подписью предусмотрены вертикальные отбивки. Их размеры хранятся в параметрах со значением длины (растяжимой) \abovecaptionskip (отбивка над подписью) и \belowcaptionskip (под подписью). В стандарте отбивка над подписью равна 10pt (без растяжимости или сжимаемости), а под подписью — нулю.

    Чтобы изменить само оформление подписи, надо переопределить команду \@makecaption ; вот ее стандартное определение в адаптированном виде (параметр #1 — номер иллюстрации или таблицы с подписью, то есть значение команды \thefigure или \thetable ; параметр #2 — текст подписи):

    \newcommand{\@makecaption}[2]{%
    \vspace{\abovecaptionskip}%
    \sbox{\@tempboxa}{#1: #2}
    \ifdim \wd\@tempboxa >\hsize
       #1: #2\par
    \else
       \global\@minipagefalse
       \hbox to \hsize {\hfil #1: #2\hfil}%
    \fi
    \vspace{\belowcaptionskip}}

    Разберем этот код. Во второй и последней строчках вокруг подписи делаются отбивки, как было объяснено выше. В третьей строке в блоковую переменную \@tempboxa (эта переменная используется LaTeX'ом для временного хранения данных такого рода) записывается текст подписи вместе с номером (пока что в одну строку; поскольку в данный момент этот текст еще не печатается, нас не волнует, не окажется ли он длинней, чем ширина полосы). В следующих шести строках (с помошью не рассматривавшейся нами TeX'овской конструкции "условных макросов") длина подписи с номером сравнивается с шириной текста (она обозначена \tex'овским параметром \hsize: при одноколонном наборе это то же самое, что \textwidth ), а при многоколонном — \columnwidth ). Если подпись вместе с номером длиннее строки, то она печатается как абзац (часть кода между \ifdim ) и \else ), а если не длиннее, то центрируется (часть кода между \else и \fi ). Код на седьмой строке воспринимайте как данность.

    Что можно изменить в этом определении? Поскольку #1 — это номер, а #2 — текст подписи, нетрудно заметить, что номер отделяется от подписи двоеточием, что с отечественными полиграфическими традициями не согласуется. Разумно заменить в этом месте двоеточие на точку. Кроме того, можно изменить шрифт, которым печатается подпись. Только не забудьте, что при переопределении надо будет вставить команды смены шрифта в три места (всюду, где в исходном определении стоит #1: #2): и в "измеряющую размер" строку, начинающуюся с \sbox (от смены шрифта размер тоже может измениться), и в оба варианта печати. Наконец, вы можете решить (не знаю, насколько это правильно) никогда не центрировать подписи; тогда в измененном определении \@makecaption надо будет удалить строки, начинающиеся с \ifdim, \else и \fi, а также текст между \else и \fi (и, возможно, установить свои любимые параметры верстки абзаца). Возможны, наверное, и другие решения. В любом случае помните, что текст между \ifdim и \else относится к случаю, когда подпись с номером в строку не умещается, а текст между \else и \fi — к противоположному.

    И последнее: команду \@makecaption вы будете, конечно, переопределять с помощью \renewcommand ; имейте в виду, что в данном случае надо пользоваться вариантом \renewcommand без звездочки, поскольку второй аргумент этой команды (текст подписи) вполне может состоять из нескольких абзацев.

    Размещение плавающих объектов на странице

    Сейчас мы обсудим параметры, которыми руководствуется LaTeX при размещении плавающих объектов на странице.

    Сразу же отметим, что все эти параметры относятся в равной мере к плавающим иллюстрациям и плавающим таблицам, и любое изменение этих параметров также затрагивает плавающие объекты всех типов.

    Часть параметров, отвечающих за плавающие объекты, представляет собой LaTeX'овские счетчики, которым можно присваивать новые значения командой \setcounter:

  • \topnumber Максимальное количество плавающих объектов, которое разрешается разместить вверху страницы (при двухколонном наборе и иллюстрациях/таблицах шириной в колонку — вверху колонки). Значение по умолчанию: $$2$$.
  • \bottomnumber Максимальное количество плавающих объектов, которое разрешается разместить внизу страницы (при двухколонном наборе и иллюстрациях/таблицах шириной в колонку — внизу колонки). Значение по умолчанию: $$1$$.
  • \totalnumber Максимальное количество плавающих объектов, которое разрешается разместить на странице (при двухколонном наборе и иллюстрациях/таблицах шириной в колонку — в колонке). Значение по умолчанию: $$3$$.
  • \dbltopnumber При наборе в две колонки: максимальное количество плавающих объектов шириной во всю страницу, которое разрешается разместить вверху страницы. Значение по умолчанию: $$2$$.
  • Значение счетчика totalnumber не влияет на количество иллюстраций и/или таблиц на странице, специально для них предназначенной (таковая, как мы помним, выделяется, если в необязательном аргументе окружения {figure} или {table} присутствует буква p).

    Вторая группа параметров регулирует уже не количество плавающих иллюстраций на странице, а величину места, ими занимаемого. Все эти параметры являются командами наподобие \arraystretch или \baselinestretch ; чтобы менять значения параметров, надо их переопределять с помощью команды \renewcommand. Эти параметры таковы:

  • \topfraction Максимальная доля страницы, которую могут занимать плавающие объекты, размещаемые вверху страницы. Значение по умолчанию: $$0.7$$. Это означает, что плавающие иллюстрации и таблицы, размещаемые вверху страницы, могут занимать не более 70% страницы по высоте. Если мы хотим уменьшить эту долю, скажем, до 50%, надо написать
    \renewcommand{\topfraction}{0.5}
    Ниже слова "доля страницы" также всюду означают "доля страницы по высоте".
  • \bottomfraction Максимальная доля страницы, которую могут занимать плавающие объекты внизу страницы. Значение по умолчанию: $$0.3$$.
  • \textfraction Минимальная доля страницы, которую должен занимать текст, а не плавающие объекты (к страницам, создаваемым LaTeX'ом специально для размещения плавающих объектов при обработке необязательного аргумента p, это не относится). Значение по умолчанию: $$0.2$$.
  • \floatpagefraction Этот параметр, напротив, относится именно к страницам, которые LaTeX создает при обработке необязательного аргумента p. Он указывает минимально возможную долю такой страницы, которую могут занимать размещаемые на ней плавающие иллюстрации и таблицы. Значение по умолчанию: $$0.5$$ (стало быть, специальная страница для плавающих иллюстраций, которую вы требуете с помощью необязательного аргумента p к окружению {figure}, не будет создана, пока эти иллюстрации занимают менее 50% высоты страницы текста).
  • Все вышеуказанные параметры применимы также к двухколонному набору и плавающим объектам шириной в колонку. Если же набор — в две колонки, а ширина плавающего объекта — целая страница, то используются такие параметры:

  • \dbltopfraction То же, что \topfraction, применительно к иллюстрациям (таблицам) шириной в целую страницу при двухколонном наборе. Значение по умолчанию: $$0.7$$.
  • \dblfloatpagefraction То же, что \floatpagefraction, применительно к иллюстрациям (таблицам) шириной в целую страницу при двухколонном наборе. Значение по умолчанию: $$0.5$$.
  • При вычислении, какую часть страницы занимает плавающий объект, учитывается не только размер собственно иллюстрации или таблицы, но и величина вертикальных отступов (" отбивок"), отделяющих этот объект от остального текста. Эти отступы задаются следующей группой параметров. Все эти параметры суть длины, присваивать им новое значение надо с помощью \setlength.

  • \textfloatsep Отступ между текстом и иллюстрациями (таблицами), размещаемыми вверху или внизу страницы.
  • \floatsep Отступ между двумя иллюстрациями (таблицами).
  • \intextsep Отступ между текстом и иллюстрациями (таблицами), размещаемыми посреди страницы (при обработке необязательного аргумента h).
  • Как водится, три перечисленных параметра применимы и к иллюстрациям (таблицам) шириной в колонку при двухколонном наборе. А вот как обозначаются соответствующие параметры, если набор в две колонки, а иллюстрация или таблица занимает по ширине всю страницу:

  • \dbltextfloatsep При двухколонном наборе - отступ между текстом и иллюстрацией (таблицей), занимающей всю страницу по ширине.
  • \dblfloatsep При двухколонном наборе - отступ между двумя иллюстрациями (таблицами), занимающими всю страницу по ширине.
  • Если вы почему-либо решите менять эти параметры с помощью команды \setlength, полезно иметь в виду, что при пользовании шрифтом кегля $$11$$ значения \floatsep, \intextsep и \dblfloatsep равны 12pt plus 2pt minus 2pt, а значения \textfloatsep и \dbltextfloatsep равны 20pt plus 2pt minus 4pt.

    По умолчанию плавающие объекты не отделены от текста ничем, кроме вышеперечисленных отбивок. Но можно сделать и так, чтобы иллюстрации (таблицы) отделялись от текста как-то иначе (линейками, например). Для этих целей предусмотрены следующие три команды:

  • \topfigrule Разделитель между плавающим объектом, размещаемым вверху страницы (колонки), и остальным текстом.
  • \botfigrule Разделитель между текстом и размещаемым внизу страницы (колонки) плавающим объектом.
  • Эти две команды относятся и к двухколонному набору, при условии, что иллюстрации (таблицы) занимают по ширине одну колонку (иными словами, если используются окружения {figure} или {table} без звездочек). А если используются варианты этих окружений со звездочками, то используется еще один параметр:

  • \dblfigrule То же, что \topfigrule, для случая, когда набор двухколонный, а плавающий объект занимает по ширине всю страницу.
  • По умолчанию указанные три команды ничего не делают. Если вы хотите задать явные разделители между текстом и иллюстрациями (таблицами), то эти команды надо определить с помощью Именно так, а не переопределить с помощью \renewcommand !. Определять эти команды нужно не произвольным образом: чтобы они правильно стыковались с LaTeX'овскими алгоритмами размещения плавающих объектов, нужно иметь в виду следующее:

  • каждая из этих команда будет выполняться в те моменты, когда TeX находится в вертикальном режиме;
  • по окончании работы каждой из этих команд TeX должен снова оказаться в вертикальном режиме;
  • текст, генерируемый каждой из этих команд, не должен, с точки зрения TeX'а, занимать места по вертикали.
  • Поэтому будет неправильно, если вы, решив отделять текст от иллюстраций линейкой, определите \botfigrule просто как \hrule: первое и второе условия при этом выполнены будут, а вот третье — нет, в результате чего LaTeX собьется со счета при решении вопроса о размещении иллюстраций. Формально правильным было бы такое решение:

    \newcommand{\botfigrule}{\hrule\vspace{-0.4pt}

    (вспомним, что линейка, генерируемая командой \hrule, имеет по умолчанию толщину 0.4pt). Впрочем, формальной правильности мало: если вы опробуете такое определение на практике, то увидите, что линейка вплотную прилегает к иллюстрации, что никуда не годится. Правильно действовать, например, так:

    \newcommand{\botfigrule}{\vspace{-3pt}\hrule
    \vspace{2.6pt}}

    Теперь мы проводим линейку не прямо по верхней кромке иллюстрации, а на три пункта выше; заключительное \vspace{2.6pt} нужно для того, чтобы в сумме получилось нулевое вертикальное смещение.

    С \topfigrule и \dblfigrule вы сможете теперь разобраться самостоятельно.

    В заключение отметим, что разделители, определяемые \topfigrule и ей подобными командами, не обязаны быть именно линейками: необходимо только при их определении учитывать три перечисленных выше обстоятельства.

    Разное

    Теоремы, выключные формулы

    Чтобы изменить оформление "теорем" (окружений, определяемых с помощью \newtheorem ), надо переопределить команды \@begintheorem и \@opargbegintheorem (первая из них отвечает за оформление "теорем" без необязательного аргумента, вторая — за оформление "теорем" с необязательным аргументом). Первая из них определена так:

    \newcommand{\@begintheorem}[2]{\begin{trivlist}
    \item[\hspace{\labelsep}\bfseries#1\ #2]
    \itshape}

    Здесь аргумент #1 означает название "теоремы" (например, " Теорема", "Предложение", "Лемма",...- в команде \newtheorem это слово являлось вторым обязательным аргументом), а аргумент "#2" означает номер "теоремы". Если мы, например, хотим, чтобы после номера "теорем" стояла точка, нам достаточно переопределить эту команду, добавив точку после #2. Что делать для того, чтобы сменить шрифт, которым печатаются номер или текст "теорем", также достаточно ясно.

    Команда \@opargbegintheorem определяется так:

    \newcommand{\@opargbegintheorem}[3]{\begin{trivlist}
    \item[\hspace{\labelsep}{\bfseries #1\ #2\ (#3)}]
    \itshape}

    Здесь #1 и #2 по-прежнему означают название и номер " теоремы", а #3 — необязательный аргумент "теоремы" (обычно в качестве такового задается имя ученого, которому приписывается данная теорема).

    Если оформление, задаваемое окружением trivlist, вас не устраивает, то можно переопределить две вышеуказанные команды более радикально. Общий принцип таков. Перед текстом "теоремы", не имеющей необязательного аргумента, исполняется команда \@begintheorem ; у этой команды должно быть два аргумента, причем первый из них — название "теоремы", а второй — ее номер. Если "теорема" имеет необязательный аргумент, то вместо \@begintheorem перед ее текстом исполняется команда \@opargbegintheorem, имеющая три аргумента: первые два — такие же, как у \@begintheorem, и третий — необязательный аргумент "теоремы" (имя первооткрывателя). Наконец, после текста "теоремы" исполняется команда \@endtheorem, которая изначально определена очень просто:

    \newcommand{\@endtheorem}{\end{trivlist}}

    В принципе можно переопределить все три эти команды, чтобы получить свое оформление "теорем" (например, в духе наших макросов для автоматической нумерации задач из лекции 7). Только следите, чтобы переопределения всех трех команд были согласованы друг с другом: если, например, вы изгоните \begin{trivlist} из определения \@begintheorem, но при этом оставите команду \@endtheorem в неприкосновенности, то на каждой " теореме" LaTeX будет сообщать вам об ошибке (отсутствие баланса команд \begin и \end ).

    При пользовании AMS'овскими классами документов "теоремы" определяются иначе. Вряд ли, впрочем, вы сочтете нужным переделывать стандарт Американского математического общества.

    Теперь скажем кое-что про стиль оформления номеров выключных формул, заданных в виде окружения {equation}. Как вам уже известно, можно переопределить команду \theequation или (с помощью команды \@addtoreset ) изменить подчиненность счетчика {equation}; при этом изменится оформление самих номеров формул. Кроме этого, можно изменить то, что печатается возле этих номеров. Для этого следует переопределить команду \@eqnnum. Изначально она определена так:

    \newcommand{\@eqnnum}{(\theequation)}

    При желании можно заменить тут круглые скобки на что-нибудь другое. Имейте в виду, что номер выключной формулы обрабатывается TeX'ом " в математическом режиме", как формула (латинские буквы по умолчанию набираются "математическим курсивом" и т.п.).

    Сноски

    Стиль оформления сносок зависит от многих вещей. Начнем с пробела между страницей и сносками. Чтобы его изменить, надо применить команду \setlength с необычным первым аргументом. Вот, например, как выглядит команда, устанавливающая стандартную для LaTeX'а величину этого пробела:

    \setlength{\skip\footins}{12pt plus 4pt minus 4pt}

    Почему в первом аргументе \setlength целых две команды и что они означают, объяснить в рамках этой книги невозможно, так что воспринимайте этот рецепт для установки пробела между текстом и сносками догматически (для любознательных: вся правда содержится в пятнадцатой главе книги [2].

    Далее, сноски обычно отделяются от текста не только пробелом, но и линейкой. Чтобы задать вид этой линейки, отличный от стандартного, либо задать какой-то другой разделитель, надо переопределить команду \footnoterule, которая в стандарте определена так:

    \newcommand{\footnoterule}{\vspace*{-3pt}
         \hrule width .4\columnwidth
         \vspace*{2.6pt}}

    К этому макроопределению необходим комментарий: непонятно, зачем нужны команды \vspace. Дело в том, что "текст", генерируемый командой \footnoterule, не должен, с точки зрения TeX'а, занимать места по вертикали (фактически он располагается внутри пробела между текстом и сносками, о котором шла речь выше). Поэтому мы сначала отступаем на 3 пункта вверх, затем печатаем линейку (вспомним, что по умолчанию линейка, генерируемая командой \hrule, имеет толщину 0.4 пункта), а затем спускаемся на 2.6 пункта вниз. В итоге получается, что и линейка напечаталась, и места по вертикали мы не занимаем, поскольку $$-3+0.4+2.6=0$$.

    Может возникнуть вопрос, зачем нужен \vspace*{-3pt}: не проще ли обойтись без этой команды, а после \hrule сказать \vspace*{-0.4pt}? Ответ: в этом случае линейка напечаталась бы вплотную к сноске.

    Если вы хотите изменить ширину или толщину линейки, команду \footnoterule можно переопределить; только не забудьте проследить, чтобы отрицательный \vspace скомпенсировал толщину линейки. Можно, собственно говоря, сделать так, чтобы этой линейки вообще не было, сказав

    \renewcommand{\footnoterule}{}

    (уж тут-то места по вертикали мы не займем!). Если вам вдруг понадобится задать совсем иной разделитель между сносками и текстом, можете переопределить команду \footnoterule принципиально по-иному. В этом случае необходимо знать следующее:

  • команда \footnoterule будет выполняться в те моменты, когда TeX находится в вертикальном режиме;
  • по окончании работы команды \footnoterule TeX должен снова оказаться в вертикальном режиме;
  • текст, генерируемый командой \footnoterule, не должен, с точки зрения TeX'а, занимать места по вертикали.
  • Следующий параметр, от которого зависит оформление сносок, — это параметр со значением длины \footnotesep. Он означает следующее. В начале каждой сноски, для того чтобы линейка, отделяющая сноски от текста, не подходила к тексту слишком близко, вставляется невидимая линейка нулевой ширины наподобие \strut. Так вот, \footnotesep задает высоту этой линейки.

    За вид номеров сносок в тексте отвечает команда \@makefnmark. По умолчанию она определена следующим образом:

    \newcommand{\@makefnmark}{\hbox{\mathsurround=0pt
    $^{\@thefnmark}$}}

    Здесь на место команды \@thefnmark при выполнении будет подставлен номер сноски (или то, что его заменяет, если мы пользовались командой \footnotemark ). Обратите внимание, что номер сноски оформлен как верхний индекс в математической формуле — именно благодаря этому номера сносок печатаются над строкой. По этой же причине внутри группы, являющей собой аргумент команды \hbox, устанавливается в нуль параметр \mathsurround - иначе, если вы установили для него ненулевое значение, номер сноски будет окружен лишними пробелами.

    И, наконец, самое главное — команда, генерирующая собственно текст сноски. Она называется \@makefntext. Вот ее стандартное определение, в котором аргумент #1 обозначает текст сноски, а команда \@thefnmark означает то же, что и выше:

    \newcommand{\@makefntext}[1]{\parindent=1em\noindent
                \hbox to 1.8em{\hss\@makefnmark}#1}

    При переопределении этой команды следует иметь в виду, что она будет выполняться внутри аргумента команды \parbox с длиной строки, равной ширине колонки текста; в приведенном выше определении применена команда \noindent, чтобы подавить абзацный отступ в первом абзаце сноски, в котором будет печататься ее номер.

    Имейте в виду, что поскольку текст сноски, являющийся аргументом команды \@makefntext, может состоять из нескольких абзацев, переопределять эту команду надо с помощью \renewcommand без звездочки.

    Список литературы

    Если вам не нравится, что библиографические ссылки печатаются в квадратных скобках, то вы можете переопределить команды \@cite и \@biblabel. По умолчанию они определены так:

    \newcommand{\@cite}[2]{[{#1\if@tempswa , #2\fi}]}
    \newcommand{\@biblabel}[1]{[#1]\hfill}

    Мы не будем даже пытаться объяснить, что означают заковыристые команды в первом из этих макроопределений (#1 в нем означает номер источника, а #2 — дополнительную информацию, помещенную в необязательном аргументе команды \cite, если таковой имеется), а отметим только, что в " замещающем тексте" первого из этих определений можно заменить квадратные скобки на какие-нибудь другие (скажем, круглые или косые) — и тогда в соответствующих скобках будет печататься ссылка, генерируемая командой \cite ; аналогично, если заменить скобки в "замещающем тексте" второго из этих определений, то в соответствующих скобках будет печататься номер источника в списке литературы. Разумеется, при переопределении этих команд надо писать \renewcommand вместо \newcommand.

    Если вы хотите, чтобы дополнительная информация печаталась вне скобок, скажите

    \renewcommand{\@cite}[2]{{[#1]\if@tempswa , #2\fi}}

    (не делайте пробела между закрывающей скобкой и \if@tempswa, иначе на печати выйдет лишний пробел). Текст между \if@tempswa и \fi будет выполняться тогда и только тогда, когда у команды \cite присутствует необязательный аргумент; если в вашем определении \@cite не будет участвовать #2, то необязательный аргумент команды \cite будет игнорироваться.

    Предметный указатель

    Первое, что вы можете изменить в оформлении предметного указателя (окружение {theindex}), - это отступы, создаваемые командами \item, \subitem и т.д. Для изменения отступов "на первом уровне" (создаваемых командой \item ) надо переопределить команду \@idxitem (но не сам item!). Чтобы вам было от чего отталкиваться, посмотрите на стандартное определение этой команды. Оно очень простое:

    \newcommand{\@idxitem}{\par\hangindent=40pt}

    Для изменения отступов, создаваемых такими командами, как \subitem и subsubitem, надо переопределить непосредственно эти команды. Их стандартные определения также бесхитростны:

    \newcommand{\subitem}{\par\hangindent=40pt\hspace*{20pt}}
    \newcommand{\subsubitem}{\par\hangindent=40pt\hspace*{30pt}}

    Наконец, команда \indexspace, создающая в предметном указателе дополнительный вертикальный пробел, определяется в стандартных стилях так:

    \newcommand{\indexspace}{\par\vspace{10pt plus 5pt minus 3pt}}

    Иногда хочется изменить оформление предметного указателя более существенным образом. Например, вы можете захотеть, чтобы ссылка на предметный указатель присутствовала в оглавлении (в LaTeX'овском стандарте это не предусмотрено); возможно также, что вы захотите предпослать предметному указателю небольшое введение, набранное во всю ширину страницы. Чтобы добиться таких вещей, надо переопределить окружение \theindex. Его стандартное определение в стилях book и report выглядит так:

    \newenvironment{theindex}{\@restonecoltrue
    \if@twocolumn\@restonecolfalse\fi
    \columnseprule=0pt \columnsep=35pt
    \twocolumn[\@makeschapterhead{\indexname}]%
    \@mkboth{\uppercase{\indexname}}{\uppercase{\indexname}}%
    \thispagestyle{plain}\parindent=0pt
    \setlength{\parskip}{0pt plus .3pt}%
    \let\item=\@idxitem}%
    {\if@restonecol \onecolumn \else \clearpage \fi}

    Первая, вторая, предпоследняя и последняя строки этого определения содержат незнакомые вам команды; мы не будем пытаться объяснить, что они значат, а только скажем, что менять эти места в определении окружения {theindex} нельзя. Зато все остальное в этом определении должно быть понятно читателю, усвоившему основную часть нашей книги. Именно, в третьей строке задаются параметры двухколонного оформления в предметном указателе: там сказано, что колонки в окружении theindex не надо разделять линейкой и задается промежуток между двумя колонками. В пятой строке дана команда, задающая (неким не рассматривавшимся нами способом) материал для колонтитулов. Она либо вносит левую и правую пометки, совпадающие со стандартным заглавием предметного указателя, либо ничего не делает. Если вы переопределяете \theindex, то можете в этой строке написать \markboth вместо \@mkboth с теми аргументами, с какими считаете нужным, или вообще убрать эту строку, чтоб пометок не было. В шестой строке обратите внимание на команду, устанавливающую нулевое значение абзацного отступа. Менять ее не надо, поскольку именно с таким значением абзацного отступа согласовано действие команд \item, \subitem и т.п. (вспомните, как действует команда \angindent ).

    Наконец, в четвертой строке стоит команда \twocolumn с необязательным аргументом. Как объяснялось в лекции 3, то, что стоит в необязательном аргументе, будет напечатано во всю ширину страницы. В стандартном определении тут стоит команда \@makeschapterhead, создающая заголовок ненумерованной главы, но вы можете записать туда и любой текст, который хотите предпослать собственно предметному указателю. Правда, тут возникает один технический момент: введение к предметному указателю вы, видимо, захотите редактировать, и нехорошо для этого всякий раз лазать в стилевой пакет. Один из возможных выходов таков. Запишите в вашем определении окружения {theindex} четвертую строку так:

    \twocolumn[\@makeschapterhead{\indexname}\input{ukaz.tex}]

    Здесь ukaz.tex — файл, в который вы запишете свое введение к предметному указателю.

    Если вы хотите, чтобы предметный указатель был отражен в оглавлении, то в необязательный аргумент команды \twocolumn надо добавить команду \addcontentsline, например, в таком виде:

    \addcontentsline{toc}{chapter}{\indexname}

    Поскольку предметный указатель, задаваемый с помощью окружения {theindex}, использует команду \twocolumn, колонки на последней странице указателя могут оказаться разной высоты. Как обычно, лекарство от этого — подключить стилевой пакет {multicol} и сделать так, чтобы окружение {theindex} использовало для печати окружение {multicols}. Для этого нужно переопределить окружение {theindex} следующим образом (мы предполагаем, что пакет {multicol} подключен):

    \renewenvironment*{theindex}{\columnseprule=0pt\columnsep=35pt
    \@makeschapterhead{\indexname}%
    \@mkboth{\uppercase{\indexname}}{\uppercase{\indexname}}%
    \thispagestyle{plain}\parindent=0pt
    \setlength{\parskip}{0pt plus .3pt}%
    \let\item=\@idxitem
    \begin{multicols}{2}}%
    {\end{multicols}}

    Разумеется, вы можете также изменить параметры в этом определении по своему усмотрению.

    Последнее, что нужно сказать про окружение {theindex}, это то, что в классе article четвертая строка его стандартного определения выглядит так:

    \twocolumn[\section*{\indexname}]%

    (поскольку в классе article главы не определены).

    Вернуться к учебному плану