# Change size of underscore in detokenize

My question is closely related to this one. The solution there works fine for text, but here is my scenario.

I want to typeset the names of all packages specially, so it is clear what I refer to. For this, I defined the command:

\newcommand*{\pkg}[1]{\textsf{\detokenize{#1}}}


I use \detokenize because I have to use _ often in the name of a package, so it I don't want the extra \. Also, sometimes I copy-paste the name from somewhere, so it already has the form package_name.

I am using lmodern fonts, mostly out of inertia. Surely, if you can suggest a better font which has a decent underscore and looks nice, that's great. I tried palatino and times, as suggested in the related question. I don't like palatino. times could work, but the \textsf seems too big in relation to normal text.

\documentclass[12pt]{report}
\usepackage{lmodern}        % use modern latin fonts
\usepackage[T1]{fontenc}    % use 8 bit output font encoding with more glyphs
\usepackage[utf8]{inputenc} % so you can type ă

\usepackage{relsize}        % allows you to resize individual characters e.g. underscore
\renewcommand{\_}{\textscale{.5}{\textunderscore}}

\newcommand*{\pkg}[1]{\textsf{\detokenize{#1}}} % typeset the name of a package: \pkg{tum_ardrone}
\newcommand*{\ds}[1]{\textsl{\textsf{\detokenize{#1}}}} % and of a dataset \ds{RIMES}
% these complicated definitions ensure that you always get correct spacing after the command
% and that you cannot forget the correct form (e.g. \FRCNN{}) because this would give you
% bad spacing; and that the name is not hyphenated
\makeatletter
\@ifdefinable{\FRCNN}{\def\FRCNN#{\mbox{\pkg{Faster R-CNN}}}}
\@ifdefinable{\CTPN}{\def\CTPN#{\mbox{\pkg{CTPN}}}}
\@ifdefinable{\RESNET}{\def\RESNET#{\mbox{\pkg{ResNet-101}}}}
\@ifdefinable{\CRNN}{\def\CRNN#{\mbox{\pkg{CRNN}}}}
\makeatother

\begin{document}

Template\_bin % works

\pkg{Template_bin} % nope

\end{document}


Edit: Forgot to say that I use things like \section{The \pkg{Template_bin}}, \caption[\pkg{Pkg_name}]{...} etc . Ideally, it would work there too, but if it's too difficult I guess I can find a workaround or not use \pkg{} there.

• Neither palatino nor times affects the sans-serif font. Why do you have special characters in filenames? This is just asking for trouble, surely? – cfr Mar 6 '18 at 1:07
• Interesting about the effect of font on sans-serif. I didn't know. They are not filenames, but how I chose to name my datasets :(. This was before writing the report, so all the figures bear these names. Also, I thought _ is a way of avoid trouble with spaces in filenames ? – Ciprian Tomoiagă Mar 6 '18 at 10:16
• Well, spaces are bad, for sure, and underscores are good in filenames. But underscores are trouble when processing because they are special characters. – cfr Mar 6 '18 at 21:55

Ask TeX to do the required replacement without touching the other tokens.

I'd prefer \scalebox to \textscale; I also add some simplification for your complicated definitions.

\documentclass[12pt]{report}
\usepackage{lmodern}        % use modern latin fonts
\usepackage[T1]{fontenc}    % use 8 bit output font encoding with more glyphs
\usepackage[utf8]{inputenc} % so you can type ă
\usepackage{graphicx}
\usepackage{xparse}

\RenewDocumentCommand{\_}{}{\scalebox{0.5}[1]{\textunderscore}}

\ExplSyntaxOn
\NewDocumentCommand{\changeunderscore}{m}
{
\tl_set:Nn \l_tmpa_tl { #1 }
\regex_replace_all:nnN { _ } { \c{_} } \l_tmpa_tl
\tl_use:N \l_tmpa_tl
}
\ExplSyntaxOff

% typeset the name of a package: \pkg{tum_ardrone}
\newcommand*{\pkg}[1]{\textsf{\changeunderscore{#1}}}
% and of a dataset \ds{RIMES}
\newcommand*{\ds}[1]{\textsl{\textsf{\changeunderscore{#1}}}}
% syntactic sugar
\makeatletter
\makeatother

\newcommandb{\FRCNN}{\mbox{\pkg{Faster R-CNN}}}
\newcommandb{\CTPN}{\mbox{\pkg{CTPN}}}
\newcommandb{\RESNET}{\mbox{\pkg{ResNet-101}}}
\newcommandb{\CRNN}{\mbox{\pkg{CRNN}}}

\newcommandb{\TB}{\pkg{Template_bin}}

\begin{document}

Template\_bin

\pkg{Template_bin}

\TB{}

\end{document}


• Wow ! Super nice ! Thank you, @egreg ! I need to learn LaTeX3 syntax to understand how all this works, but it works ! Thank you for the nice syntactic sugar, too ! p.s. Should I downvote because it doesn't answer the question, haha ? I can't figure out a better title, without \detokenize :( – Ciprian Tomoiagă Mar 6 '18 at 18:20
• @CiprianTomoiagă It doesn't use \detokenize, yes; what if your package has an accent in the name? ;-) – egreg Mar 6 '18 at 18:26

Here I use listofitems to read the \detokenized output of \pkg and replace the instances of catcode12 _ with \_.

\documentclass[12pt]{report}
\usepackage{lmodern}        % use modern latin fonts
\usepackage[T1]{fontenc}    % use 8 bit output font encoding with more glyphs
\usepackage[utf8]{inputenc} % so you can type ă

\usepackage{relsize}        % allows you to resize individual characters e.g. underscore
\usepackage{listofitems}
\renewcommand{\_}{\textscale{.5}{\textunderscore}}
% THIS IS WHAT I AM SEARCHING THE DETOKENIZED STRING FOR
\expandafter\setsepchar\expandafter{\detokenize{_}}%
%
\newcommand*{\pkg}[1]{%
\edef\tmp{\detokenize{#1}}%
\readlist\xyz{\tmp}% FIND ALL INSTANCES OF _
{\sffamily%
\foreachitem\x\in\xyz{\ifnum\xcnt=1\else\_\fi\x}}% REPLACE _ WITH \_
} % typeset the name of a package: \pkg{tum_ardrone}
\newcommand*{\ds}[1]{\textsl{\textsf{\detokenize{#1}}}} % and of a dataset \ds{RIMES}
% these complicated definitions ensure that you always get correct spacing after the command
% and that you cannot forget the correct form (e.g. \FRCNN{}) because this would give you
% bad spacing; and that the name is not hyphenated
\makeatletter
\@ifdefinable{\FRCNN}{\def\FRCNN#{\mbox{\pkg{Faster R-CNN}}}}
\@ifdefinable{\CTPN}{\def\CTPN#{\mbox{\pkg{CTPN}}}}
\@ifdefinable{\RESNET}{\def\RESNET#{\mbox{\pkg{ResNet-101}}}}
\@ifdefinable{\CRNN}{\def\CRNN#{\mbox{\pkg{CRNN}}}}
\makeatother

\begin{document}

\textsf{Template\_bin} % works

\pkg{Template_bin} % nope

\pkg{Template_double_bin} % nope

\end{document}


As a follow up for the OP, who expanded the question to include having \pkg in section titles, the best I could do is have a quiet mode of \pkg that did not print out its result, instead saving it in \pkgname. In this way, one could define the \pkgname before the section heading with \pkg[q]{My_bad} and then use the result in the section heading: \section{The package is \pkgname}.

\documentclass[12pt]{report}
\usepackage{lmodern}        % use modern latin fonts
\usepackage[T1]{fontenc}    % use 8 bit output font encoding with more glyphs
\usepackage[utf8]{inputenc} % so you can type ă

\usepackage{relsize}        % allows you to resize individual characters e.g. underscore
\usepackage{listofitems}
\renewcommand{\_}{\textscale{.5}{\textunderscore}}
% THIS IS WHAT I AM SEARCHING THE DETOKENIZED STRING FOR
\expandafter\setsepchar\expandafter{\detokenize{_}}%
%
\makeatletter
\newcommand*{\pkg}[2][\relax]{%
\edef\tmp{\detokenize{#2}}%
\readlist\xyz{\tmp}% FIND ALL INSTANCES OF _
\def\pkgname{}%
\expandafter\def\expandafter\pkgname\expandafter{%
\expandafter\textsf\expandafter{\pkgname}}%
\ifx\relax#1\relax\pkgname\fi% REPLACE _ WITH \_
} % typeset the name of a package: \pkg{tum_ardrone}
\makeatother
\newcommand*{\ds}[1]{\textsl{\textsf{\detokenize{#1}}}} % and of a dataset \ds{RIMES}
% these complicated definitions ensure that you always get correct spacing after the command
% and that you cannot forget the correct form (e.g. \FRCNN{}) because this would give you
% bad spacing; and that the name is not hyphenated
\makeatletter
\@ifdefinable{\FRCNN}{\def\FRCNN#{\mbox{\pkg{Faster R-CNN}}}}
\@ifdefinable{\CTPN}{\def\CTPN#{\mbox{\pkg{CTPN}}}}
\@ifdefinable{\RESNET}{\def\RESNET#{\mbox{\pkg{ResNet-101}}}}
\@ifdefinable{\CRNN}{\def\CRNN#{\mbox{\pkg{CRNN}}}}
\makeatother

\begin{document}
\tableofcontents

\section{The package is \pkgname}

\textsf{Template\_bin} % works

\pkg{Template_bin} % nope

\pkg{Template_double_bin} % nope


• Beautiful ! I was thinking it must be something along the lines foreach token in \detokenize; if ..., but I need to learn latex programming. Small question: does the \setsepchar mean that the items in \xyz will be {Template, _, bin}, as opposed to {T, e, m, ..., _, b, i, n} ? – Ciprian Tomoiagă Mar 6 '18 at 10:30
• Hmm, I now realise that it works on the MWE, but I failed to say that I use \pkg inside section titles and other places like that (captions, etc). And it fails there with ! Incomplete \iffalse; all text was ignored after line 44 , where line 44 is \section{\pkg{Template_bin}} – Ciprian Tomoiagă Mar 6 '18 at 10:53
• @CiprianTomoiagă The listofitems package (ctan.org/pkg/listofitems) can do multi-level parsing of an input, based on parsing separators you provide. Here is an answer that shows some of its capability, tex.stackexchange.com/questions/338634/…, though you should look at the documentation. – Steven B. Segletes Mar 6 '18 at 10:53
• @CiprianTomoiagă I cannot make it seamless, but instead provide a quiet mode of \pkg that doesn't output the result immediately, but saves it in \pkgname, to be used later (like in a section heading). – Steven B. Segletes Mar 6 '18 at 11:20
• @CiprianTomoiagă The \readlist is not expandable; however the result of the \readlist if fully expandable. This is, again, part of the listofitems package. – Steven B. Segletes Mar 6 '18 at 11:46