2

xstring staff...

Target

I want to create two labels at beginning and end of specific text respectively. I have sucessfully writen some code to do this, see the following code:

\usepackage{xstring}
\usepackage{lineno}
\linenumbers
\usepackage{hyperref}
\newcommand{\hlabel}[1]{\label{#1}\hypertarget{#1}{\linelabel{line:#1}}}

\makeatother
\newcommand{\clab}[2]{%
\protected@write \@auxout {}{\string \newlabel {r:#1}{{#2}{}}}\hlabel{#1}#2\hlabel{#1end}}
\makeatother

I can use

\clab{lab1}{some text, some text, more text...}

to create two lables, which are pointing to the beginning and the end of the text "some text, some text, more text..."

Some error

The \clab{lab}{text...} function goes wrong if using it like this:

  \clab{lab1}{some text, some text, more text..., \clab{lab2}{other text, other text, more other text...}, even more text...}

My unsuccessful solution

I found some code from a example of xstring package (page 18-19) which could replace the function with another function. My idea is to replace the inner \clab{lab2}{text...} by another empty function \elab{lab2}{text...} using the xstring package.

First, define pattern and replace function name:
\expandarg
\def\pattern{\clab}
\def\replace{\elab}
Then, define the two functions \clab and \elab,
 % define a empty function to replace the function \clab
 \newcommand{\elab}[2]{#2}  

 % define a function \clab{label}{texts, texts, blabla}
 \newcommand{\clab}[2]{%
 \protected@write \@auxout {}{\string \newlabel {r:#1}{{#2}{}}}\hlabel{#1}#2\hlabel{#1end}}
Finally, I used the xstring package to replace the \clab function by \elab function:

modify the #2 -----> \StrSubstitute[2]{#2}{\pattern}{\replace}

\protected@write \@auxout {}{\string \newlabel {r:#1}{{#2}{}}}\hlabel{#1}#2\hlabel{#1end}}

It goes like this:

\protected@write \@auxout {}{\string \newlabel {r:#1}{{#2}{}}}\hlabel{#1}\StrSubstitute[2]{#2}{\pattern}{\replace}\hlabel{#1end}}

Still wrong, please help!

The executable LaTeX code is here:

LaTeX code

Please read the following code and help me with the problem

\documentclass{article}
\usepackage{xstring}
\usepackage{lineno}
\linenumbers
\usepackage{hyperref}
\newcommand{\hlabel}[1]{\label{#1}\hypertarget{#1}{\linelabel{line:#1}}}

% learn from a example of xstring package (page 18-19, xstring.pdf)
\expandarg
\def\pattern{\clab}
\def\replace{\elab}

\makeatletter
  % define a empty function to replace the function \clab
  \newcommand{\elab}[2]{#2}  

 % define a function \clab{label}{texts, texts, blabla}
  % to create two labels, one is at the beginning of the texts
  % the other is at the end of the texts
  \newcommand{\clab}[2]{%
    % I use the following line to do the job,
    % it is fine to do 
    % \clab{lab1}{texts texts} texts, \clab{lab2}{texts texts} texts, 
    % but it goes wrong with
    % \clab{lab1}{texts texts texts, \clab{lab2}{texts texts} texts}, 
  %\protected@write \@auxout {}{\string \newlabel {r:#1}{{#2}{}}}\hlabel{#1}#2\hlabel{#1end}}
    %so I tried to find the solution,
    % the idea is using xstring function to replace the \clab{lab2}{texts texts texts} by a empty function
    % \elab{lab2}{texts texts texts},
    % I use the following code to do the job, but it still goes wrong!!
    % \expandarg
    % \def\pattern{\clab}
    % \def\replace{\elab}
    % \StrSubstitute[2]{#2}{\pattern}{\replace}
  \protected@write \@auxout {}{\string \newlabel {r:#1}{{#2}{}}}\hlabel{#1}\StrSubstitute[2]{#2}{\pattern}{\replace}\hlabel{#1end}}
\makeatother


\begin{document}

THis one not work:
% please uncomment the following line to see the error messages

 % \clab{lab1}{one two three four \clab{lab2}{five six seven eigth} nine ten}.

THis one works:

\clab{lab1}{one two three four}, \clab{lab2}{five six seven eigth} nine ten.

\end{document}
% end of file template.tex
4
  • 3
    Well, I think you should describe what you want. Having the question at the end of the code is perhaps not the best way?
    – Mensch
    Jul 29, 2013 at 8:12
  • Thanks, I have tried my best to make me clear, please help.
    – user30816
    Jul 29, 2013 at 12:24
  • The problem still isn't clear. However, \StrSubstitute cannot work inside \protected@write, where only expansion can take place, not assignments.
    – egreg
    Jul 29, 2013 at 17:43
  • Could any body help me?
    – user30816
    Jul 30, 2013 at 8:43

1 Answer 1

4
\documentclass{article}
\usepackage{xstring}
\usepackage{lineno}
\linenumbers
\usepackage{hyperref}
\newcommand{\hlabel}[1]{\label{#1}\hypertarget{#1}{\linelabel{line:#1}}}

\makeatletter
\newcommand{\clab}[2]{%
  \protected@write\@auxout{\let\clab\@secondoftwo}{\string\newlabel{r:#1}{{#2}{}}}%
  \hlabel{#1}#2\hlabel{#1end}}

\makeatother
\begin{document}
  \clab{lab1}{one two three four \clab{lab2}{five six seven eigth} nine ten}.
\end{document}
3
  • 4
    Welcome to TeX.SX! Would you like to expand your answer with some explanation? Code only answer, even if working, don't help readers who may have similar, but not identical, problems.
    – egreg
    Jul 30, 2013 at 9:47
  • Welcome to TeX-SX! Have a look at our starter page for a quick intro if you wish to familiarize yourself with our format. Jul 30, 2013 at 10:03
  • I don't really know how it works, but it is what i wanted.
    – user30816
    Jul 30, 2013 at 13:52

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .