# Set boolean of environment before a command

A command must be put before an environment, defining the kind of environment. However, the first boolean does not execute, the result is wrong. Please help me fix the problem.

\documentclass[12pt]{article}
\usepackage{etoolbox}
\newbool{blbt}
\newbool{blvd}
%%%=======================
\newenvironment{bt}{\global\setbool{blvd}{false}\global\setbool{blbt}{true}\par}{}
%%%=======================
\newenvironment{vd}{\global\setbool{blvd}{true}\global\setbool{blbt}{false}\par}{}
%%%=======================
\newcommand{\classify}{The below environment is
\ifbool{blvd}{Example}{\ifbool{blbt}{Problem}{Wrong}}}
\begin{document}
{\bfseries\classify}
\begin{bt}
Contents PPP
\end{bt}

{\bfseries\classify}
\begin{vd}
Contents EXEXEX
\end{vd}
\end{document}


• Are you sure that there is a problem with the booleans? In your definition of \classify you are testing the same boolean blvd twice. Jul 23 at 17:32
• As @campa says. In addition, I see no reason for \global. Jul 23 at 17:37
• @campa Thank you. I typed wrong. The problem is really in setting boolean. I have just edited my codes. Jul 23 at 22:50
• @egreg Thank you! Jul 23 at 22:50

\documentclass[12pt]{article}
\usepackage{etoolbox}
\newbool{blbt}
\newbool{blvd}
\newcommand{\classify}{The environment below is
\ifbool{blvd}{Example}{\ifbool{blbt}{Problem}{Wrong}}}
%%%=======================
\newenvironment{bt}{\global\setbool{blvd}{false}\global\setbool{blbt}{true}{\bfseries\classify}\par}{}
%%%=======================
\newenvironment{vd}{\global\setbool{blvd}{true}\global\setbool{blbt}{false}{\bfseries\classify}\par}{}
%%%=======================
\begin{document}
\begin{bt}
Contents PPP
\end{bt}

\begin{vd}
Contents EXEXEX
\end{vd}
\end{document}


• Thank you! My problem is that the command must be before the environment. I have just edited my code. Jul 23 at 22:52
• @NamTranLe, I modified my answer for your updated question. Jul 23 at 23:06
• Thank you. That is my problem. The command must input outside the environment. Jul 23 at 23:28
• Base on your suggestion, I create an extra command included in the environment. Then We call it an outside environment with a condition. Thank you! Jul 24 at 0:50

If you don't mind your command \classify and your environments bt and vt to have a non-optional argument, then you can use the package zref and have

• the environments bt and vt place referencing-labels for properties blvd and blbt
• the command \classify extract values of properties from these referencing-labels:
\documentclass[12pt]{article}
\usepackage{etoolbox}
\usepackage{zref}

\makeatletter
\@ifdefinable\@zrefpropdefined{%
\ZREF@Robust\def\@zrefpropdefined{%
\zref@wrapper@babel\@ZREFpropdefined
}%
}%
\@ifdefinable\@ZREFpropdefined{%
\def\@ZREFpropdefined#1#2#3#4{%
% #1  - label
% #2  - property
% #3  - tokens in case label and property are available
% #4  - tokens in case label undefined or property not available
\zref@ifrefundefined{#1}{%
\zref@refused{#1}#4%
}{%
\zref@ifrefcontainsprop{#1}{#2}{#3}{%
\protect\G@refundefinedtrue
\@latex@warning{%
Missing property #2' in reference #1' on page \thepage
}%
#4%
}%
}%
}%
}%
\zref@newprop{blbt}{false}%
\zref@newprop{blvd}{false}%
\newcommand\blvdANDblbtLABEL[3]{%
\zref@setcurrent{blvd}{#1}%
\zref@setcurrent{blbt}{#2}%
\zref@wrapper@immediate{%
\zref@labelbyprops{#3}{blbt,blvd}%
}%
}%
%%%=======================
\newenvironment{bt}[1]{%
\blvdANDblbtLABEL{false}{true}{#1}%
% Here you could place code that forks
% via \ifbool{\zref@getcurrent{blvd}}{<true>}{<false>}%
% and \ifbool{\zref@getcurrent{blbt}}{<true>}{<false>}%
\par}{}
%%%=======================
\newenvironment{vd}[1]{%
\blvdANDblbtLABEL{true}{false}{#1}%
% Here you could place code that forks
% via \ifbool{\zref@getcurrent{blvd}}{<true>}{<false>}%
% and \ifbool{\zref@getcurrent{blbt}}{<true>}{<false>}%
\par}{}
%%%=======================
\newcommand{\classify}[1]{The below environment is
\@zrefpropdefined{#1}{blvd}{%
\@zrefpropdefined{#1}{blbt}{\@firstoftwo}{\@secondoftwo}%
}{%
\@zrefpropdefined{#1}{blbt}{}{}%
\@secondoftwo
}%
{%
\ifbool{\zref@extractdefault{#1}{blvd}{}}{Example}{%
\ifbool{\zref@extractdefault{#1}{blbt}{}}{Problem}{Wrong}%
}%
}{%
\nfss@text{\reset@font\bfseries??}%
}%
}%
\makeatother

\begin{document}

{\bfseries\classify{Label Of This Environment}}
\begin{bt}{Label Of This Environment}
Contents PPP
\end{bt}

{\bfseries\classify{Label Of That Environment}}
\begin{vd}{Label Of That Environment}
Contents EXEXEX
\end{vd}

\end{document}


(If the real-life-scenario also is about only two environments, you could do with a single boolean if the \classify-command's wrong-case" can be omitted.)

Using zref you can probably do without boolean at all:

\documentclass[12pt]{article}
\usepackage{zref}

\makeatletter

\@ifdefinable\@zrefpropdefined{%
\ZREF@Robust\def\@zrefpropdefined{%
\zref@wrapper@babel\@ZREFpropdefined
}%
}%
\@ifdefinable\@ZREFpropdefined{%
\def\@ZREFpropdefined#1#2#3#4{%
% #1  - label
% #2  - property
% #3  - tokens in case label and property are available
% #4  - tokens in case label undefined or property not available
\zref@ifrefundefined{#1}{%
\zref@refused{#1}#4%
}{%
\zref@ifrefcontainsprop{#1}{#2}{#3}{%
\protect\G@refundefinedtrue
\@latex@warning{%
Missing property #2' in reference #1' on page \thepage
}%
#4%
}%
}%
}%
}%

\zref@newprop{environmentphrase}{unknown}%
\newcommand\environmentphraseLABEL[2]{%
\zref@setcurrent{environmentphrase}{#1}%
\zref@wrapper@immediate{%
\zref@labelbyprops{#2}{environmentphrase}%
}%
}%
%%%=======================
\newenvironment{bt}[1]{%
\environmentphraseLABEL{Problem}{#1}%
\par}{}
%%%=======================
\newenvironment{vd}[1]{%
\environmentphraseLABEL{Example}{#1}%
\par}{}
%%%=======================
\newcommand{\classify}[1]{The below environment is
\zref@extractdefault{#1}{environmentphrase}{%
\@zrefpropdefined{#1}{environmentphrase}{%
\protect\G@refundefinedtrue
\@latex@warning{%
Unspecified problem in reference #1' on page \thepage
}%
}{}%
\nfss@text{\reset@font\bfseries??}%
}%
}%
\makeatother

\begin{document}

{\bfseries\classify{Label Of This Environment}}
\begin{bt}{Label Of This Environment}
Contents PPP
\end{bt}

{\bfseries\classify{Label Of That Environment}}
\begin{vd}{Label Of That Environment}
Contents EXEXEX
\end{vd}

\end{document}


With both examples you need two LaTeX-compilations (without having auxiliary-files deleted between these runs) for having everything match out.

With both examples the resulting .pdf-file looks like this:

• Thank you very much! Jul 24 at 2:15
\documentclass[12pt]{article}
\newif\ifblbt
\newif\ifblvd
\newenvironment{bt}
{\blvdfalse\blbttrue{\bfseries\classify\par}}
{}
\newenvironment{vd}
{\blvdtrue\blbtfalse{\bfseries\classify\par}}
{}
\newcommand\classify{The below environment is \ifblvd Example\else\ifblbt Problem\else Wrong\fi\fi}
\begin{document}
\begin{bt}
Contents PPP
\end{bt}

\begin{vd}
Contents EXEXEX
\end{vd}
\end{document}

• Thank you! My problem is that the command must be before the environment. I have just edited my code. Jul 23 at 22:53
• See edited answer. Jul 24 at 15:00

Base on the @modnar's suggestion. Thank you very much for your helps!

\documentclass[12pt]{article}
\usepackage{etoolbox}
\newbool{blbt}
\newbool{blvd}
\newif\ifoutput
\newcommand{\classify}{\outputtrue}
\newcommand{\classifyp}{
\ifoutput{
The environment below is
\ifbool{blvd}{Example}{\ifbool{blbt}{Problem}{Wrong}}
}\fi
}
%%%=======================
\newenvironment{bt}{\global\setbool{blvd}{false}\global\setbool{blbt}{true}{\bfseries\classifyp}\par}{}
%%%=======================
\newenvironment{vd}{\global\setbool{blvd}{true}\global\setbool{blbt}{false}{\bfseries\classifyp}\par}{}
%%%=======================
\begin{document}
\classify

\begin{bt}
Contents PPP
\end{bt}

\begin{vd}
Contents EXEXEX
\end{vd}

\begin{bt}
Contents PPP
\end{bt}
\end{document}
`