8

I am trying to convert a predefined string in a variable to its lowercase and replace the spaces to underscore. But it's not working. The new string after conversion is like this:

gameΩ_ofΩ_Ω_rollingΩ_Ω_Ω_dice

Desired output is:

game_of_rolling_dice

Can any one help me out please?

\documentclass{article}
\usepackage{xstring}
\usepackage{textcase}

\newcommand{\questionsection}{Game of  rolling   dice}
\newcommand{\questionsectionfiltered}{\StrSubstitute{\questionsection}{ }{\textunderscore}[\SUBtemp]\MakeLowercase{\SUBtemp}}

\begin{document}
    \questionsectionfiltered
\end{document}
1
  • 2
    Welcome to TeX.SE.
    – Mico
    Jan 25 at 22:41

3 Answers 3

5

Perfect candidate for a token cycle. EDITED to add lowercasing, as requested.

\documentclass{article}
\usepackage{tokcycle}
\Characterdirective{\addcytoks[x]{\explowerchar{#1}}}
\Spacedirective{\addcytoks{\textunderscore\allowbreak}}
\def\explowerchar#1{%
  \ifcase\numexpr`#1-`A\relax
   a\or b\or c\or d\or e\or f\or g\or h\or i\or j\or k\or l\or m\or
   n\or o\or p\or q\or r\or s\or t\or u\or v\or w\or x\or y\or z\else
   #1\fi
}

\newcommand{\questionsection}{Game of  rolling   dice, plus this should
  allow line breaks as well.  Let us see if it does}
\newcommand{\questionsectionfiltered}{\expandafter\tokencyclexpress
  \questionsection\endtokencyclexpress}

\begin{document}
    \questionsectionfiltered
\end{document}

enter image description here

3
  • this looks simple but it is not lowercasing the whole string
    – t.abraham
    Jan 26 at 11:45
  • @t.abraham I failed to see that requirement, but I will edit my answer to provide that Jan 26 at 15:26
  • @t.abraham I have added the lowercasing feature, as well. Jan 26 at 15:31
7

You can use expl3 that's more robust than xstring (and more flexible).

\documentclass{article}

\ExplSyntaxOn

\NewDocumentCommand{\filter}{m}
 {
  \tabraham_filter:n { #1 }
 }

\tl_new:N \l__tabraham_filter_text_tl

\cs_new_protected:Nn \tabraham_filter:n
 {
  % set the tl variable to the lowercased version of the input
  \tl_set:Nx \l__tabraham_filter_text_tl { \text_lowercase:n { #1 } }
  % replace spaces with underscores
  \tl_replace_all:Nnn \l__tabraham_filter_text_tl { ~ } { \_ }
  % deliver the result
  \tl_use:N \l__tabraham_filter_text_tl
 }

\ExplSyntaxOff

\newcommand{\questionsection}{Game of  rolling   dice}

\begin{document}

\filter{\questionsection}

\filter{Game of  rolling   dice}

\end{document}

enter image description here

You may want to define a filtered version of some token list, so when using it you don't have to repeat the whole process.

\documentclass{article}

\ExplSyntaxOn

\NewDocumentCommand{\filter}{m}
 {
  \tabraham_filter:nn { #1 } { \tl_use:N }
 }
\NewDocumentCommand{\newfilteredcommand}{mm}
 {
  \tl_if_exist:NF #1
   {
    You~don't~want~to~silently~redefine~something,~do~you?
   }
   {
    \tl_new:N #1
    \tabraham_filter:nn { #2 } { \tl_set_eq:NN #1 }
   }
 }

\tl_new:N \l__tabraham_filter_text_tl

\cs_new_protected:Nn \tabraham_filter:nn
 {
  \tl_set:Nx \l__tabraham_filter_text_tl { \text_lowercase:n { #1 } }
  \tl_replace_all:Nnn \l__tabraham_filter_text_tl { ~ } { \_ }
  #2 \l__tabraham_filter_text_tl
 }

\ExplSyntaxOff

\newcommand{\questionsection}{Game of  rolling   dice}
\newfilteredcommand{\questionsectionfiltered}{\questionsection}

\begin{document}

\filter{\questionsection}

\filter{Game of  rolling   dice}

\questionsectionfiltered

\texttt{\meaning\questionsectionfiltered}

\end{document}

The last line is to show that \questionsectionfiltered is what's expected.

enter image description here

3

Here's a LuaLaTeX-based solution. It provides a user macro called \LowercaseUnderscore, which passes its argument to a Lua function called function lc_underscore, which does most of the work with the help of the Lua built-in functions string.lower and string.gsub.

The argument of \LowercaseUnderscore needn't be a string. It could be a LaTeX macro; if it is, the macro gets expanded before it is passed to the Lua function for final processing.

enter image description here

% !TeX program = lualatex
\documentclass{article}
\usepackage{luacode} % for 'luacode' environment and '\luastring' macro
\begin{luacode}
  function lc_underscore ( s )
    s = string.lower ( s )
    s = string.gsub ( s , "%s" , "\\textunderscore" )
    return ( s )
  end
\end{luacode}
\newcommand\LowercaseUnderscore[1]{%
    \directlua{tex.sprint(lc_underscore(\luastring{#1}))}}

\newcommand{\questionsection}{Game of  Rolling   Dice}

\begin{document}
\LowercaseUnderscore{\questionsection}
\end{document}

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.