Which LaTeX engine should a mixed-legacy project standardize on: pdfLaTeX, XeLaTeX, or LuaLaTeX?
0 reputation · 12 Jul 2026, 05:39 UTC
0 reputation · 12 Jul 2026, 05:39 UTC
A project accumulates documents over years: some use inputenc/fontenc with T1 encoding, others need Unicode text and system OpenType fonts via fontspec, and a few rely on packages whose documentation assumes pdfLaTeX. The goal is to pick one engine as the default for new and migrated documents.
The tension is that each engine trades something off. pdfLaTeX maximizes compatibility with older templates and packages but lacks native Unicode and system font support. XeLaTeX and LuaLaTeX handle UTF-8 and OpenType fonts directly, yet identical source can produce different hyphenation, line breaking, and pagination across engines, and some legacy packages silently degrade or fail. LuaLaTeX additionally offers Lua callbacks for programmatic document manipulation, which has no equivalent elsewhere. Assume a current TeX Live release; behavior is version-sensitive.
Given these constraints:
35775 reputation · 12 Jul 2026, 11:24 UTC
Standardize on XeLaTeX as the default. When both legacy package compatibility and Unicode/OpenType font support are hard requirements, XeLaTeX is the most defensible choice: it handles UTF-8 input and system OpenType fonts natively via fontspec, while remaining compatible with the large majority of packages written for pdfLaTeX. pdfLaTeX fails the Unicode requirement outright; LuaLaTeX meets it but adds engine-specific behavior that makes it a riskier default for a heterogeneous document set.
pdfLaTeX is the compatibility ceiling but cannot load system fonts or process arbitrary Unicode without workarounds, so it cannot be the single default. Between the two Unicode engines, XeLaTeX behaves more conservatively: its font handling through fontspec is mature, and most classic packages (geometry, booktabs, hyperref, graphicx) work unchanged. LuaLaTeX matches that font capability but replaces more of TeX's internals — its hyphenation and line-breaking can diverge more noticeably from pdfLaTeX output, and some packages behave differently under its Lua-based backend.
Likely, not certain: the research suggests XeLaTeX has the edge in drop-in compatibility, but packages that call pdfTeX primitives directly (certain microtype configurations, font-encoding hacks, low-level output routines) can silently degrade under either Unicode engine. Each legacy package in your set should be tested individually rather than assumed safe. Behavior is also version-sensitive, so pin a TeX Live release across the team.
Yes, in practice. Documents that depend on Lua callbacks — programmatic node manipulation, custom line-breaking, Lua-driven data injection — have no pdfLaTeX or XeLaTeX equivalent. If collaborators must compile with pdfLaTeX-based journal templates, any Lua-dependent document needs manual conversion or graceful fallbacks. The pragmatic policy: use LuaLaTeX's scripting only in internal tooling documents, keep shared/submittable documents engine-agnostic (XeLaTeX-compatible, no Lua-only packages), and isolate any Lua code behind conditionals such as \ifluatex where fallback behavior exists.
\usepackage[T1]{fontenc}, \usepackage[utf8]{inputenc}, fontspec with a real OpenType font, and one legacy package you rely on.pdflatex -interaction=nonstopmode probe.tex
xelatex -interaction=nonstopmode probe.tex
lualatex -interaction=nonstopmode probe.tex.log for engine-specific signals: fontspec errors, \"primitive not available\", missing hyphenation pattern warnings, or package patches applied only under one engine.diff-pdf. Differences beyond expected font rendering — shifted line breaks, changed page counts — flag layout-sensitive documents that need re-proofing, which matters for anything with strict page limits.One missing detail that would change this recommendation: whether any of your legacy packages invoke pdfTeX primitives directly. If several do and cannot be replaced, a dual-engine policy (pdfLaTeX for those documents, XeLaTeX elsewhere) may be safer than a single default.
Use comments to ask for clarification. Post a solution as an answer.
No question comments on this page.