Changes

Jump to navigation Jump to search
1,463 bytes added ,  13:54, 24 June 2020
m
< [[The ConTeXt Way]] | [[Inside ConTeXt]] | [[Project structure]] >
 
Very often, you want to generate multiple versions of the same document:
one version for printing and one for viewing on the screen, one version for
multiple modes can be simultaneously enabled or disabled, and the status of multiple
modes can be checked easily. Moreover, modes can be set from a command line
switch. As a result, multiple versions of a document can be generated without changingthe source file.
The name or identifier of a mode can be any combination of letters, digits, or
spaces. Names starting with <code>*</code> are reserved for system modes.
 
In this article I explain how to activate a mode and how to check if a mode is
active or not.
= Setting modes =
ConTeXt has three commands for setting modes:
* <code><{{cmd>|enablemode </cmd>}}[...]</code>* <code><{{cmd>|disablemode</cmd>}}[...]</code>* <code><{{cmd>|preventmode</cmd>}}[...]</code>
The names are self-descriptive. <{{cmd>|enablemode</cmd> }} activates a mode,<{{cmd>|disablemode</cmd> }} deactivates a mode, and <{{cmd>|preventmode</cmd> }} permanently
deactivates a mode. All three commands take a list of modes as an argument. For
example, you can activate to active modes named <code>screen</code> and <code>solution</code> withuse:
<texcode>
\enablemode[screen,solution]
Modes can also be activated by a command line switch <code>--modes</code> to
<code>texexec</code> or <code>context</code>. For example, another way to activate the <code>screen</code> and
<code>solution</code> modes, to run ConTeXt using one of:
texexec --mode=screen,solution ...
context --mode=screen,solution ...
== Pre-defining modes ==
 
Normally, the overhead for testing modes is negligible, but it can add up if
modes are tested multiple times in a document (for example, as part of a
macro). To speed up the processing, a mode can be ''define''d before being
used:
 
<texcode>
\definemode[...][...]
</texcode>
The first argument is a list of modes; the second argument may be `yes`, `no`, or `keep`. For example,
 
* <code>\definemode[screen][yes]</code> defines a mode and enables it;
* <code>\definemode[screen][no]</code> defines a mode and disables it;
* <code>\definemode[screen][keep]</code> defines a mode and keeps its previous status.
 
Typically, it is better to use <code>\definemode[...][keep]</code> so that the modes may be enabled or disabled from command line as well.
= Conditional processing based on modes =
4:3 aspect ratio and a width equal to the width of A4 paper.)
Alternatively, youcould set a default paper size for the screen and change it if screen mode isnot enabled:
<texcode>
\setuppapersize[S6][S6]
== Checking for multiple modes (`<code>or`</`code>/<code>and` </code> statements for modes) ==
<code>\startmode</code> and <code>\startnotmode</code> can check for multiple modes,
by giving a list of modes as their arguments. <code>\startmode</code>
<texcode>
\doifmode {modesmode1, mode2, ...} {contentProcessed if any mode is enabled}\doifnotmode {modesmode1, mode2, ...} {contentProcessed if any mode is disabled}\doifallmodes {modesmode1, mode2, ...} {contentProcessed if all modes are enabled}\doifnotallmodes {modesmode1, mode2, ...} {contentProcessed if all modes are disabled}
</texcode>
The logic for determining when the content is processed is exactly the same as
the conditions are not satisfied (like the <code>\else</code> branch of <code>\if</code>).
<texcode>
\doifmodeelse {modesmode1, mode2, ...} {contentProcessed if any mode is enabled} {altelse this is processed}\doifnotmodeelse doifallmodeselse {modes} {contentmode1, mode2, ...} {alt}\doifallmodeselse {Processed if all modesare enabled} {content} {altelse this is processed}\doifnotallmodeselse{modesmode1, mode2, ...} {contentProcessed if all modes are disabled} {altelse this is processed}
</texcode>
== Checking multiple modes in sequence Note that there is no command <code>\doifnotmodeelse</code> because there is no need for it; <code>\doifmodeelse</code> may be used for the same effect (`case` statement for modeswith the <code>if</code> and <code>else</code> branches switched) == Sometimes you have to choose between a couple of modes. One way to do this is the following:
== Checking multiple modes in parallel (<texcodecode>\doifmodeelse {one} { ... } { \doifmodeelse {two} { ... } { \doifmodeelse { three} { ... etc ... } } } case</texcodecode>statement for modes) ==
A more readable but In addition to the above <em>"or"</em> and <em>"and"</em> environment which check modes is sequence, you can also more efficient way check multiple modes in parallel. The syntax for such a <em>"case"</em> environment is to use a modesetas follows:
<texcode>
\startmodeset
[one] {1}% NOTE: Empty lines are not allowed here! [twomode1, mode2, ...] {2Processed if either mode is enabled} [twomode3, mode4, ...] {2} [three] {3Processed if either mode is enabled} [default] {?Processed if none of the above modes match}
\stopmodeset
</texcode>
\startmodesetThe same mode can be referenced multiple times, and '''all''' matching branches are executed. [one] The {1{cmd|startmodeset}} [three] ... {{3cmd|stopmodeset} [default] {?}\stopmodesetenvironments can be nested. So, you can use
<texcode>
\startmodeset
[onemode1, mode2] { \input tufteProcessed when either mode1 or mode2 is enabled
}
[twomode3] {
\startmodeset
[onemode1] {AProcessed when mode1 and mode3 are enabled} [twomode2] {BProcessed when mode2 and mode3 are enabled} [two] {B} [threedefault] {C} [default] {!Processed when mode3 is enabled and mode1 and mode2 are disabled}
\stopmodeset
}
[three,four] {
\input zapf
}
[default] {
\input wardProcessed when mode1, mode2, and mode3 are disabled.:
}
\stopmodeset
</texcode>
 
The syntax is somewhat special but suits the purpose. It's a sort of
case statement. There can be multiple references to the same mode and
each match is honored. Of course the default only is used when no match
has taken place.
== Checking modes in Lua ==
In MkIV, the The state of any mode is accessible at the Lua end as <code>tex.modes</code> table. Specifically,
<texcode>
checks if both <code>mode1</code> and <code>mode2</code> are enabled.
'''Note''': This table was added in 2010.10.14 beta and is not available in earlier releases.
= System modes =
| Enabled when running [[MkIV]]
|}
 
Perhaps the most useful system modes are <code>*mkii</code> and <code>*mkiv</code> which
Other modes are useful for very specific situations. Some of these are described
below.
 
{|cellpadding="5" style="border-collapse: collapse;border-width: 1px; border-style: solid;"
<code>*first</code> mode is handy&mdash;it is active only on the first run of the
document.
 
 
{|cellpadding="5" style="border-collapse: collapse;border-width: 1px; border-style: solid;"
| '''*export'''
| Enabled when <code>\setupbackend[export=yes]</code> is set
|}
 
You may want to use different images for XML [Export]. The <code>*export</code> mode is useful in such cases.
 
{|cellpadding="5" style="border-collapse: collapse;border-width: 1px; border-style: solid;"
encountered. Similarly, a mode <code>*text</code> is enabled when
<code>\starttext</code> is encountered, and likewise for the others.
 
 
{|cellpadding="5" style="border-collapse: collapse;border-width: 1px; border-style: solid;"
if you want macros that work differently in different section blocks, you can
check for modes <code>*frontpart</code>, <code>*bodypart</code>, and so on.
 
 
{|cellpadding="5" style="border-collapse: collapse;border-width: 1px; border-style: solid;"
| Enabled inside the corresponding section head.
|}
 
Sometimes you want a macro to behave differently if it is part of a section head, a section number, a list, a marking, or a register. For section heads, you can check for modes <code>*chapter</code>, <code>*section</code>, <code>*subsection</code>, etc. Similarly, <code>*list</code> is enabled inside a list, <code>*marking</code> is enabled inside a marking, and <code>*register</code> is enabled inside a register.
Sometimes you want a macro to behave differently if it is part of a section head, a section number, a list, a marking, or a register. For section heads, you can check for modes <code>*chapter</code>, <code>*section</code>, <code>*subsection</code>, etc. Similarly, <code>*list<code> is enabled inside a list, <code>*marking</code> is enabled inside a marking, and <code>*register</code> is enabled inside a register.
{|cellpadding="5" style="border-collapse: collapse;border-width: 1px; border-style: solid;"
English and the current language is Dutch, the modes <code>**en-us</code> and
<code>*nl</code> are set (notice the extra <code>*</code> in <code>**en-us</code>).
 
 
{|cellpadding="5" style="border-collapse: collapse;border-width: 1px; border-style: solid;"
|'''*grid'''
| Enabled when grid typesetting is enabled
|-
|'''*singlesided'''
| Enabled when singlesided layout is enabled
|-
|'''*doublesided'''
| Enabled when doublesided layout is enabled
|}
 
{|cellpadding="5" style="border-collapse: collapse;border-width: 1px; border-style: solid;"
\executesystemcommand{some_external_program ...}
% convert PS into PDF
\executesystemcommand{texmfstart pstopdf fig-1.ps}
\stopmode
</texcode>
  [[Category:ConTeXt programmingTools]]

Navigation menu