Написание собственных шаблонов LaTeX с относительными путями, разница между include, input, class

Написание собственных шаблонов LaTeX с относительными путями, разница между include, input, class

Я работаю в среде Windows с Miktex. Большинство моих документов создаются с помощью XeLaTeX, но я думаю, что моя проблема не связана с компилятором.

Я хотел бы создать шаблон со всеми моими пакетами, настройками заголовка и графическим путем, например, для включения логотипов заголовка. Во всех моих документах, использующих шаблон, я хотел бы иметь только настройки документа и содержимое документа. Моя проблема в том, что документы могут находиться в папке, отличной от папки шаблона, но я все равно хотел бы включить изображения из папки шаблона. Моя настройка выглядит так:

.
├── templates/
│   ├── my_template.tex
│   └── pictures/
│       └── header_logo.pdf
└── documents/
    ├── my_document.tex
    └── pictures/
        └── some_picture.png

Минимальными примерами могут быть:

мой_шаблон.tex:

\documentclass[
    11pt,
    a4paper,
]{scrarticle}

\usepackage{scrextend}
\usepackage{scrlayer-scrpage}

%%%%% Graphics %%%%%
\usepackage{graphicx}
\graphicspath{{./pictures/}}

%%%% Title Setup %%%%%
\ihead{\includegraphics[width=6cm]{header_logo.pdf}}
\cfoot{}
\setlength{\headheight}{14pt}

мой_документ.tex:

\input{../templates/my_template.tex}

\graphicspath{{./pictures/}}

\begin{document}
\includegraphics[width=6cm]{some_picture.png}
\end{document}

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

решение1

Как вhttps://tex.stackexchange.com/a/250/162943, \inputперепечатает содержимое файла и includesдобавит clearpagesи не может быть вложенным. Я бы остановился на \input.
Команда \graphicspathполучает в качестве аргумента список папок: \graphcispath{{folder1}{folder2}}, поэтому я предлагаю использовать полный путь для папки с изображениями шаблонов (templates/pictures) и относительный путь для папки с изображениями документов (documents/pictures), которая, как я предполагаю, всегда будет иметь одно и то же имя.

мой_шаблон.tex:

\documentclass[
    11pt,
    a4paper,
]{scrarticle}

\usepackage{scrextend}
\usepackage{scrlayer-scrpage}

%%%%% Graphics %%%%%
\usepackage{graphicx}
\graphicspath{{C:/Path/to/template/image/folder}{./pictures/}}

%%%% Title Setup %%%%%
\ihead{\includegraphics[width=6cm]{header_logo.pdf}}
\cfoot{}
\setlength{\headheight}{14pt}

мой_документ.tex:

\input{../templates/my_template.tex}

\begin{document}
\includegraphics[width=6cm]{some_picture.png}
\end{document}

Другим решением будет использование символических ссылок. Создайте символическую ссылку на папку с изображениями шаблонов внутри папки с изображениями вашего проекта и используйте только \graphicspath{{./pictures/}}. В этом случае вам нужно будет не забыть добавить имя папки в каждый includegraphics.

решение2

Чтобы избежать абсолютных путей, вы можете использовать пакет subfiles(хотя его основной вариант использования немного отличается). Требуемые изменения:

  • Сделайте шаблон полноценным документом, добавив \begin{document}\end{document}.

  • В конце преамбулы шаблона загрузите пакет subfilesи затем укажите путь к графике, но разрешите ему ссылаться только на каталоги изображений, соответствующие шаблону, используя относительные пути.

  • Начните свой настоящий документ со строки

    \documentclass[rel.path to template]{subfiles}
    
  • В преамбуле настоящего документа добавьте дополнительные локальные каталоги изображений в графические пути.

Преимущество перед другими решениями заключается в том, что шаблону нужно знать только о каталогах изображений, относящихся к шаблону, а документы могут хранить свои конкретные изображения в каталогах, которые не обязательно должны быть одинаковыми. Более того, не требуются абсолютные пути.

Для вашего примера эти изменения выглядят следующим образом:

% templates/my_template.tex
\documentclass[
    11pt,
    a4paper,
]{scrarticle}

\usepackage{scrextend}
\usepackage{scrlayer-scrpage}

%%%%% Graphics %%%%%
\usepackage{graphicx}
\usepackage{subfiles}
\graphicspath{{./pictures/}}% <<< PICTURES LOCAL TO template DIRECTORY

%%%% Title Setup %%%%%
\ihead{\includegraphics[width=6cm]{header_logo.pdf}}
\cfoot{}
\setlength{\headheight}{14pt}
\begin{document}% <<< NECESSARY FOR subfiles TO WORK
\end{document}% <<< NECESSARY FOR subfiles TO WORK

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

% documents/my_document.tex
\documentclass[../templates/my_template]{subfiles}% <<< LOAD PREAMBLE FROM ../templates/my_template.tex

\makeatletter% <<< EXTEND THE GRAPHICS SEARCH PATH BY LOCAL DIRECTORIES
\edef\Ginput@path{\Ginput@path{./pictures/}}% <<<<<<<<<<<<<<<<<
\makeatother% <<<<<<<<<<<<<<<<<

\begin{document}
\includegraphics[width=6cm]{some_picture.png}
\end{document}

решение3

Как упоминалось в одном из других ответов, \inputнапрямую скопируйте текст из другого файла, как будто вы просто вручную объединили их. Это, как правило, самый простой способ сделать это, и его можно вложить для больших документов. \includeвсегда будет создавать новую страницу для размещения контента и не может быть вложенным.

Преимущество использования \includeзаключается в том, что в начале документа вы можете использовать \includeonlyсо списком имен файлов, а затем любые включения, которые указывают другое имя файла, будут игнорироваться. Я использовал это в очень больших проектах, где основные разделы использовались, \includeчтобы мне не приходилось ждать компиляции других разделов, когда я работал над одним из них. Затем я использовал \inputдля подразделов, поскольку вы не можете вкладывать \include. Вы также можете сделать это другим способом, введя разделы и включив подразделы.

Очень часто преамбулу помещают в другой файл. Есть несколько способов сделать это, которые более или менее правильны, чем другие. Самый распространенный способ сделать это — поместить преамбулу (кроме \documentclass) в отдельный файл, который вы можете назвать как угодно, скажем mypreamble.sty, обратите внимание, что он должен заканчиваться на .sty, а затем вы можете \usepackage{mypreamble}использовать любой другой пакет. Вам также нужно добавить строку \ProvidesPackage{mypreabmle}в начало файла преамбулы. Это также можно сделать с помощью , \includeно это не рекомендуется, так как \usepackageвыполняет некоторую внутреннюю обработку и допускает необязательные параметры и т. д.

Один из других пакетов, который полезен для нескольких файлов, называется , importкоторый позволяет использовать команду следующим образом: \import{path\to\secton}{sectionname.tex}. Хорошая вещь в этом заключается в том, что если вы хотите импортировать что-то в файл, который вы уже импортировали, вы можете вызвать , \subimport{relitive/path/}{plot1.tex}который использует путь относительно импортированного файла, что весьма полезно.

решение4

Ответы gernot и bryce привели меня к попытке поместить мою преамбулу в .clsфайл. Мне пришлось переставить некоторые файлы, так что мое дерево файлов теперь выглядит так:

.
├── templates/
│   └── tex/
│       └── latex/
│           └── my_template/
│               ├── my_template.cls
│               └── header_logo.pdf
└── documents/
    ├── my_document.tex
    └── pictures/
        └── some_picture.png

my_template.cls теперь становится

\NeedsTeXFormat{LaTeX2e}
\ProvidesClass{my_template}
\LoadClass[
    11pt,
    a4paper,
]{scrarticle}

\RequirePackage{scrextend}
\RequirePackage{scrlayer-scrpage}

%%%%% Graphics %%%%%
\RequirePackage{graphicx}
\graphicspath{{./pictures/}}

%%%% Title Setup %%%%%
\ihead{\includegraphics[width=6cm]{header_logo.pdf}}
\cfoot{}
\setlength{\headheight}{14pt}

и my_document.tex становится

\documentclass{my_template}

\begin{document}
\includegraphics[width=6cm]{some_picture.png}
\end{document}

Graphicspath внутри my_template.clsтеперь является относительным к файлу, my_document.texв то время как cls напрямую извлекает графику из своего собственного расположения. Для работы каталог templatesдолжен быть инициализирован как его собственный корень texmf (я сделал это с помощью Miktex console --> Settings --> Directories --> Add). Преимущество этой настройки в том, что я могу использовать шаблон из любого места на моем ПК без необходимости указывать относительные или абсолютные пути к каталогу, в котором он находится. Это очень помогает мне с точки зрения контроля версий GIT.

Еще несколько ответов по этому подходу и подробности, например, для передвижных установок, можно найти здесь:

Где мне разместить собственные файлы .sty или .cls, чтобы сделать их доступными для всех моих файлов .tex?

Как написать пакет LaTeX, который объединяет не только файлы .sty и .cls, но и некоторые логотипы в форматах .pdf или .eps?

с особенноэтотответ для путей по умолчанию.

Связанный контент