Test if Current Color is Black
up vote
10
down vote
favorite
The MWE below does exactly what I want via the TypsetInBlueOnlyIfCurrentColorIsBlack
macro:
TypsetInBlueOnlyIfCurrentColorIsBlack
is intended to change the color of its parameter to blue, only if the current color is black. Otherwise, the current color is to be used.
Questions:
- I expected that
xcolor
would provide a macro to do this, but was not able to locate it. Thus, wondering if there any obvious problems with this approach, or is there an official interface that is provided.
References:
- This solution is adapted from How to get a textual representation of the current color?
.
Code:
documentclass{article}
usepackage{xcolor}
usepackage{xstring}
%% At this point the default color is black so save that.
edefBlackColor{csnamestringcolor@.endcsname}
makeatletter
newcommand{@CurrentColor}{}% Make sure we are not using an existing macro
newcommand*{TypsetInBlueOnlyIfCurrentColorIsBlack}[1]{%
edef@CurrentColor{csnamestringcolor@.endcsname}% Get current color
IfStrEq{@CurrentColor}{BlackColor}{%
{bfseriesttfamilytextcolor{blue}{#1}}% current color IS black
}{%
{bfseriesttfamily#1}% current color is NOT black
}%
}
makeatother
begin{document}
Following should be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}.
color{red}
Following should be in red:
TypsetInBlueOnlyIfCurrentColorIsBlack{red}.
color{blue}
Following should also be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}.
end{document}
color
add a comment |
up vote
10
down vote
favorite
The MWE below does exactly what I want via the TypsetInBlueOnlyIfCurrentColorIsBlack
macro:
TypsetInBlueOnlyIfCurrentColorIsBlack
is intended to change the color of its parameter to blue, only if the current color is black. Otherwise, the current color is to be used.
Questions:
- I expected that
xcolor
would provide a macro to do this, but was not able to locate it. Thus, wondering if there any obvious problems with this approach, or is there an official interface that is provided.
References:
- This solution is adapted from How to get a textual representation of the current color?
.
Code:
documentclass{article}
usepackage{xcolor}
usepackage{xstring}
%% At this point the default color is black so save that.
edefBlackColor{csnamestringcolor@.endcsname}
makeatletter
newcommand{@CurrentColor}{}% Make sure we are not using an existing macro
newcommand*{TypsetInBlueOnlyIfCurrentColorIsBlack}[1]{%
edef@CurrentColor{csnamestringcolor@.endcsname}% Get current color
IfStrEq{@CurrentColor}{BlackColor}{%
{bfseriesttfamilytextcolor{blue}{#1}}% current color IS black
}{%
{bfseriesttfamily#1}% current color is NOT black
}%
}
makeatother
begin{document}
Following should be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}.
color{red}
Following should be in red:
TypsetInBlueOnlyIfCurrentColorIsBlack{red}.
color{blue}
Following should also be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}.
end{document}
color
2
color
stores the current colour incurrent@color
. So you could dousepackage{xcolor}{color{black}globalletmy@black@colorcurrent@color}newcommand*ifblack{ifxmy@black@colorcurrent@color}
.
– Skillmon
Dec 15 at 22:20
@Skillmon Better yet:sbox0{color{black}globalletmy@black@colorcurrent@color}
so no whatsit is added to the main vertical list.
– egreg
Dec 16 at 0:00
add a comment |
up vote
10
down vote
favorite
up vote
10
down vote
favorite
The MWE below does exactly what I want via the TypsetInBlueOnlyIfCurrentColorIsBlack
macro:
TypsetInBlueOnlyIfCurrentColorIsBlack
is intended to change the color of its parameter to blue, only if the current color is black. Otherwise, the current color is to be used.
Questions:
- I expected that
xcolor
would provide a macro to do this, but was not able to locate it. Thus, wondering if there any obvious problems with this approach, or is there an official interface that is provided.
References:
- This solution is adapted from How to get a textual representation of the current color?
.
Code:
documentclass{article}
usepackage{xcolor}
usepackage{xstring}
%% At this point the default color is black so save that.
edefBlackColor{csnamestringcolor@.endcsname}
makeatletter
newcommand{@CurrentColor}{}% Make sure we are not using an existing macro
newcommand*{TypsetInBlueOnlyIfCurrentColorIsBlack}[1]{%
edef@CurrentColor{csnamestringcolor@.endcsname}% Get current color
IfStrEq{@CurrentColor}{BlackColor}{%
{bfseriesttfamilytextcolor{blue}{#1}}% current color IS black
}{%
{bfseriesttfamily#1}% current color is NOT black
}%
}
makeatother
begin{document}
Following should be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}.
color{red}
Following should be in red:
TypsetInBlueOnlyIfCurrentColorIsBlack{red}.
color{blue}
Following should also be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}.
end{document}
color
The MWE below does exactly what I want via the TypsetInBlueOnlyIfCurrentColorIsBlack
macro:
TypsetInBlueOnlyIfCurrentColorIsBlack
is intended to change the color of its parameter to blue, only if the current color is black. Otherwise, the current color is to be used.
Questions:
- I expected that
xcolor
would provide a macro to do this, but was not able to locate it. Thus, wondering if there any obvious problems with this approach, or is there an official interface that is provided.
References:
- This solution is adapted from How to get a textual representation of the current color?
.
Code:
documentclass{article}
usepackage{xcolor}
usepackage{xstring}
%% At this point the default color is black so save that.
edefBlackColor{csnamestringcolor@.endcsname}
makeatletter
newcommand{@CurrentColor}{}% Make sure we are not using an existing macro
newcommand*{TypsetInBlueOnlyIfCurrentColorIsBlack}[1]{%
edef@CurrentColor{csnamestringcolor@.endcsname}% Get current color
IfStrEq{@CurrentColor}{BlackColor}{%
{bfseriesttfamilytextcolor{blue}{#1}}% current color IS black
}{%
{bfseriesttfamily#1}% current color is NOT black
}%
}
makeatother
begin{document}
Following should be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}.
color{red}
Following should be in red:
TypsetInBlueOnlyIfCurrentColorIsBlack{red}.
color{blue}
Following should also be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}.
end{document}
color
color
asked Dec 15 at 22:09
Peter Grill
163k25433745
163k25433745
2
color
stores the current colour incurrent@color
. So you could dousepackage{xcolor}{color{black}globalletmy@black@colorcurrent@color}newcommand*ifblack{ifxmy@black@colorcurrent@color}
.
– Skillmon
Dec 15 at 22:20
@Skillmon Better yet:sbox0{color{black}globalletmy@black@colorcurrent@color}
so no whatsit is added to the main vertical list.
– egreg
Dec 16 at 0:00
add a comment |
2
color
stores the current colour incurrent@color
. So you could dousepackage{xcolor}{color{black}globalletmy@black@colorcurrent@color}newcommand*ifblack{ifxmy@black@colorcurrent@color}
.
– Skillmon
Dec 15 at 22:20
@Skillmon Better yet:sbox0{color{black}globalletmy@black@colorcurrent@color}
so no whatsit is added to the main vertical list.
– egreg
Dec 16 at 0:00
2
2
color
stores the current colour in current@color
. So you could do usepackage{xcolor}{color{black}globalletmy@black@colorcurrent@color}newcommand*ifblack{ifxmy@black@colorcurrent@color}
.– Skillmon
Dec 15 at 22:20
color
stores the current colour in current@color
. So you could do usepackage{xcolor}{color{black}globalletmy@black@colorcurrent@color}newcommand*ifblack{ifxmy@black@colorcurrent@color}
.– Skillmon
Dec 15 at 22:20
@Skillmon Better yet:
sbox0{color{black}globalletmy@black@colorcurrent@color}
so no whatsit is added to the main vertical list.– egreg
Dec 16 at 0:00
@Skillmon Better yet:
sbox0{color{black}globalletmy@black@colorcurrent@color}
so no whatsit is added to the main vertical list.– egreg
Dec 16 at 0:00
add a comment |
1 Answer
1
active
oldest
votes
up vote
6
down vote
An interface? Use expl3
, of course!
With storecolor
you can store the representation of the colors you need to do comparison with.
I define a generic comparison command and also yours as a special case.
At begin document each color in the list passed to storecolors
and also black
are converted in the internal representation and stored in a property list. This is for greater efficiency and not actually necessary: it saves several steps in the evaluation.
The main command converts the current color in the internal representation and compares it with the color given as the first argument (only named colors, but this could be generalized). If the test returns true, the color specified as second argument is used to print the third argument; otherwise no color change is performed.
documentclass{article}
usepackage{xcolor}
usepackage{xparse}
ExplSyntaxOn
NewDocumentCommand{perhapschangecolor}{mmm}
{% #1 = color to compare with current
% #2 = color to use if match
% #3 = text
peter_color_change:nnn { #1 } { #2 } { #3 }
}
% the same but with black and blue preset
NewDocumentCommand{TypsetInBlueOnlyIfCurrentColorIsBlack}{m}
{
perhapschangecolor{black}{blue}{#1}
}
NewDocumentCommand{storecolors}{m}
{% black is always stored
AtBeginDocument { peter_color_store:n { black,#1 } }
}
prop_new:N g_peter_color_stored_prop
tl_new:N l__peter_color_current_tl
cs_new:Nn peter_color_store:n
{
hbox_set:Nn l_tmpa_box
{
clist_map_inline:nn { #1 }
{
color{##1}
driver_color_pickup:N l_tmpa_tl
prop_gput:NnV g_peter_color_stored_prop { ##1 } l_tmpa_tl
}
}
}
cs_new_protected:Nn peter_color_change:nnn
{
driver_color_pickup:N l__peter_color_current_tl
prop_if_in:NnTF g_peter_color_stored_prop { #1 }
{% more efficient test
str_if_eq:eeTF
{ l__peter_color_current_tl }
{ prop_item:Nn g_peter_color_stored_prop { #1 } }
{ textcolor{#2}{#3} }
{ #3 }
}
{
hbox_set:Nn l_tmpa_box
{
color{#1}
driver_color_pickup:N l_tmpa_tl
tl_gset_eq:NN g_tmpa_tl l_tmpa_tl
}
driver_color_pickup:N l_tmpa_tl
str_if_eq:eeTF { g_tmpa_tl } { l_tmpa_tl }
{ textcolor{#2}{#3} }
{ #3 }
}
}
ExplSyntaxOff
storecolors{red!60}
begin{document}
Following should be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}
color{red}
Following should be in red:
TypsetInBlueOnlyIfCurrentColorIsBlack{red}
color{blue}
Following should be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}
color{black}
Following should be in pale red:
perhapschangecolor{black}{red!60}{red!60}
color{red!60}
Following should be in pale red:
perhapschangecolor{black}{red!60}{red!60}
color{blue}
Following should be in blue:
perhapschangecolor{black}{red!60}{blue}
% blue has not been stored, but the test succeeds as well
Following should be in pale red:
perhapschangecolor{blue}{red!60}{red!60}
end{document}
Inclist_map_inline:nn
inpeter_color_store:n
you're missing an additional group aroundcolor{##1}
.
– Skillmon
Dec 16 at 8:37
@Skillmon It's not necessary, as the code is executed inside a box being built and then unused.
– egreg
Dec 16 at 10:46
I'd still do so, just to not lead to bad practise. Somebody not knowing the limitations and seeing this code might write faulty code because he thinks it's generally safe to use it inside a box.
– Skillmon
Dec 16 at 13:01
add a comment |
Your Answer
StackExchange.ready(function() {
var channelOptions = {
tags: "".split(" "),
id: "85"
};
initTagRenderer("".split(" "), "".split(" "), channelOptions);
StackExchange.using("externalEditor", function() {
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled) {
StackExchange.using("snippets", function() {
createEditor();
});
}
else {
createEditor();
}
});
function createEditor() {
StackExchange.prepareEditor({
heartbeatType: 'answer',
autoActivateHeartbeat: false,
convertImagesToLinks: false,
noModals: true,
showLowRepImageUploadWarning: true,
reputationToPostImages: null,
bindNavPrevention: true,
postfix: "",
imageUploader: {
brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
allowUrls: true
},
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
});
}
});
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2ftex.stackexchange.com%2fquestions%2f466026%2ftest-if-current-color-is-black%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
1 Answer
1
active
oldest
votes
1 Answer
1
active
oldest
votes
active
oldest
votes
active
oldest
votes
up vote
6
down vote
An interface? Use expl3
, of course!
With storecolor
you can store the representation of the colors you need to do comparison with.
I define a generic comparison command and also yours as a special case.
At begin document each color in the list passed to storecolors
and also black
are converted in the internal representation and stored in a property list. This is for greater efficiency and not actually necessary: it saves several steps in the evaluation.
The main command converts the current color in the internal representation and compares it with the color given as the first argument (only named colors, but this could be generalized). If the test returns true, the color specified as second argument is used to print the third argument; otherwise no color change is performed.
documentclass{article}
usepackage{xcolor}
usepackage{xparse}
ExplSyntaxOn
NewDocumentCommand{perhapschangecolor}{mmm}
{% #1 = color to compare with current
% #2 = color to use if match
% #3 = text
peter_color_change:nnn { #1 } { #2 } { #3 }
}
% the same but with black and blue preset
NewDocumentCommand{TypsetInBlueOnlyIfCurrentColorIsBlack}{m}
{
perhapschangecolor{black}{blue}{#1}
}
NewDocumentCommand{storecolors}{m}
{% black is always stored
AtBeginDocument { peter_color_store:n { black,#1 } }
}
prop_new:N g_peter_color_stored_prop
tl_new:N l__peter_color_current_tl
cs_new:Nn peter_color_store:n
{
hbox_set:Nn l_tmpa_box
{
clist_map_inline:nn { #1 }
{
color{##1}
driver_color_pickup:N l_tmpa_tl
prop_gput:NnV g_peter_color_stored_prop { ##1 } l_tmpa_tl
}
}
}
cs_new_protected:Nn peter_color_change:nnn
{
driver_color_pickup:N l__peter_color_current_tl
prop_if_in:NnTF g_peter_color_stored_prop { #1 }
{% more efficient test
str_if_eq:eeTF
{ l__peter_color_current_tl }
{ prop_item:Nn g_peter_color_stored_prop { #1 } }
{ textcolor{#2}{#3} }
{ #3 }
}
{
hbox_set:Nn l_tmpa_box
{
color{#1}
driver_color_pickup:N l_tmpa_tl
tl_gset_eq:NN g_tmpa_tl l_tmpa_tl
}
driver_color_pickup:N l_tmpa_tl
str_if_eq:eeTF { g_tmpa_tl } { l_tmpa_tl }
{ textcolor{#2}{#3} }
{ #3 }
}
}
ExplSyntaxOff
storecolors{red!60}
begin{document}
Following should be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}
color{red}
Following should be in red:
TypsetInBlueOnlyIfCurrentColorIsBlack{red}
color{blue}
Following should be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}
color{black}
Following should be in pale red:
perhapschangecolor{black}{red!60}{red!60}
color{red!60}
Following should be in pale red:
perhapschangecolor{black}{red!60}{red!60}
color{blue}
Following should be in blue:
perhapschangecolor{black}{red!60}{blue}
% blue has not been stored, but the test succeeds as well
Following should be in pale red:
perhapschangecolor{blue}{red!60}{red!60}
end{document}
Inclist_map_inline:nn
inpeter_color_store:n
you're missing an additional group aroundcolor{##1}
.
– Skillmon
Dec 16 at 8:37
@Skillmon It's not necessary, as the code is executed inside a box being built and then unused.
– egreg
Dec 16 at 10:46
I'd still do so, just to not lead to bad practise. Somebody not knowing the limitations and seeing this code might write faulty code because he thinks it's generally safe to use it inside a box.
– Skillmon
Dec 16 at 13:01
add a comment |
up vote
6
down vote
An interface? Use expl3
, of course!
With storecolor
you can store the representation of the colors you need to do comparison with.
I define a generic comparison command and also yours as a special case.
At begin document each color in the list passed to storecolors
and also black
are converted in the internal representation and stored in a property list. This is for greater efficiency and not actually necessary: it saves several steps in the evaluation.
The main command converts the current color in the internal representation and compares it with the color given as the first argument (only named colors, but this could be generalized). If the test returns true, the color specified as second argument is used to print the third argument; otherwise no color change is performed.
documentclass{article}
usepackage{xcolor}
usepackage{xparse}
ExplSyntaxOn
NewDocumentCommand{perhapschangecolor}{mmm}
{% #1 = color to compare with current
% #2 = color to use if match
% #3 = text
peter_color_change:nnn { #1 } { #2 } { #3 }
}
% the same but with black and blue preset
NewDocumentCommand{TypsetInBlueOnlyIfCurrentColorIsBlack}{m}
{
perhapschangecolor{black}{blue}{#1}
}
NewDocumentCommand{storecolors}{m}
{% black is always stored
AtBeginDocument { peter_color_store:n { black,#1 } }
}
prop_new:N g_peter_color_stored_prop
tl_new:N l__peter_color_current_tl
cs_new:Nn peter_color_store:n
{
hbox_set:Nn l_tmpa_box
{
clist_map_inline:nn { #1 }
{
color{##1}
driver_color_pickup:N l_tmpa_tl
prop_gput:NnV g_peter_color_stored_prop { ##1 } l_tmpa_tl
}
}
}
cs_new_protected:Nn peter_color_change:nnn
{
driver_color_pickup:N l__peter_color_current_tl
prop_if_in:NnTF g_peter_color_stored_prop { #1 }
{% more efficient test
str_if_eq:eeTF
{ l__peter_color_current_tl }
{ prop_item:Nn g_peter_color_stored_prop { #1 } }
{ textcolor{#2}{#3} }
{ #3 }
}
{
hbox_set:Nn l_tmpa_box
{
color{#1}
driver_color_pickup:N l_tmpa_tl
tl_gset_eq:NN g_tmpa_tl l_tmpa_tl
}
driver_color_pickup:N l_tmpa_tl
str_if_eq:eeTF { g_tmpa_tl } { l_tmpa_tl }
{ textcolor{#2}{#3} }
{ #3 }
}
}
ExplSyntaxOff
storecolors{red!60}
begin{document}
Following should be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}
color{red}
Following should be in red:
TypsetInBlueOnlyIfCurrentColorIsBlack{red}
color{blue}
Following should be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}
color{black}
Following should be in pale red:
perhapschangecolor{black}{red!60}{red!60}
color{red!60}
Following should be in pale red:
perhapschangecolor{black}{red!60}{red!60}
color{blue}
Following should be in blue:
perhapschangecolor{black}{red!60}{blue}
% blue has not been stored, but the test succeeds as well
Following should be in pale red:
perhapschangecolor{blue}{red!60}{red!60}
end{document}
Inclist_map_inline:nn
inpeter_color_store:n
you're missing an additional group aroundcolor{##1}
.
– Skillmon
Dec 16 at 8:37
@Skillmon It's not necessary, as the code is executed inside a box being built and then unused.
– egreg
Dec 16 at 10:46
I'd still do so, just to not lead to bad practise. Somebody not knowing the limitations and seeing this code might write faulty code because he thinks it's generally safe to use it inside a box.
– Skillmon
Dec 16 at 13:01
add a comment |
up vote
6
down vote
up vote
6
down vote
An interface? Use expl3
, of course!
With storecolor
you can store the representation of the colors you need to do comparison with.
I define a generic comparison command and also yours as a special case.
At begin document each color in the list passed to storecolors
and also black
are converted in the internal representation and stored in a property list. This is for greater efficiency and not actually necessary: it saves several steps in the evaluation.
The main command converts the current color in the internal representation and compares it with the color given as the first argument (only named colors, but this could be generalized). If the test returns true, the color specified as second argument is used to print the third argument; otherwise no color change is performed.
documentclass{article}
usepackage{xcolor}
usepackage{xparse}
ExplSyntaxOn
NewDocumentCommand{perhapschangecolor}{mmm}
{% #1 = color to compare with current
% #2 = color to use if match
% #3 = text
peter_color_change:nnn { #1 } { #2 } { #3 }
}
% the same but with black and blue preset
NewDocumentCommand{TypsetInBlueOnlyIfCurrentColorIsBlack}{m}
{
perhapschangecolor{black}{blue}{#1}
}
NewDocumentCommand{storecolors}{m}
{% black is always stored
AtBeginDocument { peter_color_store:n { black,#1 } }
}
prop_new:N g_peter_color_stored_prop
tl_new:N l__peter_color_current_tl
cs_new:Nn peter_color_store:n
{
hbox_set:Nn l_tmpa_box
{
clist_map_inline:nn { #1 }
{
color{##1}
driver_color_pickup:N l_tmpa_tl
prop_gput:NnV g_peter_color_stored_prop { ##1 } l_tmpa_tl
}
}
}
cs_new_protected:Nn peter_color_change:nnn
{
driver_color_pickup:N l__peter_color_current_tl
prop_if_in:NnTF g_peter_color_stored_prop { #1 }
{% more efficient test
str_if_eq:eeTF
{ l__peter_color_current_tl }
{ prop_item:Nn g_peter_color_stored_prop { #1 } }
{ textcolor{#2}{#3} }
{ #3 }
}
{
hbox_set:Nn l_tmpa_box
{
color{#1}
driver_color_pickup:N l_tmpa_tl
tl_gset_eq:NN g_tmpa_tl l_tmpa_tl
}
driver_color_pickup:N l_tmpa_tl
str_if_eq:eeTF { g_tmpa_tl } { l_tmpa_tl }
{ textcolor{#2}{#3} }
{ #3 }
}
}
ExplSyntaxOff
storecolors{red!60}
begin{document}
Following should be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}
color{red}
Following should be in red:
TypsetInBlueOnlyIfCurrentColorIsBlack{red}
color{blue}
Following should be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}
color{black}
Following should be in pale red:
perhapschangecolor{black}{red!60}{red!60}
color{red!60}
Following should be in pale red:
perhapschangecolor{black}{red!60}{red!60}
color{blue}
Following should be in blue:
perhapschangecolor{black}{red!60}{blue}
% blue has not been stored, but the test succeeds as well
Following should be in pale red:
perhapschangecolor{blue}{red!60}{red!60}
end{document}
An interface? Use expl3
, of course!
With storecolor
you can store the representation of the colors you need to do comparison with.
I define a generic comparison command and also yours as a special case.
At begin document each color in the list passed to storecolors
and also black
are converted in the internal representation and stored in a property list. This is for greater efficiency and not actually necessary: it saves several steps in the evaluation.
The main command converts the current color in the internal representation and compares it with the color given as the first argument (only named colors, but this could be generalized). If the test returns true, the color specified as second argument is used to print the third argument; otherwise no color change is performed.
documentclass{article}
usepackage{xcolor}
usepackage{xparse}
ExplSyntaxOn
NewDocumentCommand{perhapschangecolor}{mmm}
{% #1 = color to compare with current
% #2 = color to use if match
% #3 = text
peter_color_change:nnn { #1 } { #2 } { #3 }
}
% the same but with black and blue preset
NewDocumentCommand{TypsetInBlueOnlyIfCurrentColorIsBlack}{m}
{
perhapschangecolor{black}{blue}{#1}
}
NewDocumentCommand{storecolors}{m}
{% black is always stored
AtBeginDocument { peter_color_store:n { black,#1 } }
}
prop_new:N g_peter_color_stored_prop
tl_new:N l__peter_color_current_tl
cs_new:Nn peter_color_store:n
{
hbox_set:Nn l_tmpa_box
{
clist_map_inline:nn { #1 }
{
color{##1}
driver_color_pickup:N l_tmpa_tl
prop_gput:NnV g_peter_color_stored_prop { ##1 } l_tmpa_tl
}
}
}
cs_new_protected:Nn peter_color_change:nnn
{
driver_color_pickup:N l__peter_color_current_tl
prop_if_in:NnTF g_peter_color_stored_prop { #1 }
{% more efficient test
str_if_eq:eeTF
{ l__peter_color_current_tl }
{ prop_item:Nn g_peter_color_stored_prop { #1 } }
{ textcolor{#2}{#3} }
{ #3 }
}
{
hbox_set:Nn l_tmpa_box
{
color{#1}
driver_color_pickup:N l_tmpa_tl
tl_gset_eq:NN g_tmpa_tl l_tmpa_tl
}
driver_color_pickup:N l_tmpa_tl
str_if_eq:eeTF { g_tmpa_tl } { l_tmpa_tl }
{ textcolor{#2}{#3} }
{ #3 }
}
}
ExplSyntaxOff
storecolors{red!60}
begin{document}
Following should be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}
color{red}
Following should be in red:
TypsetInBlueOnlyIfCurrentColorIsBlack{red}
color{blue}
Following should be in blue:
TypsetInBlueOnlyIfCurrentColorIsBlack{blue}
color{black}
Following should be in pale red:
perhapschangecolor{black}{red!60}{red!60}
color{red!60}
Following should be in pale red:
perhapschangecolor{black}{red!60}{red!60}
color{blue}
Following should be in blue:
perhapschangecolor{black}{red!60}{blue}
% blue has not been stored, but the test succeeds as well
Following should be in pale red:
perhapschangecolor{blue}{red!60}{red!60}
end{document}
answered Dec 16 at 1:04
egreg
706k8618773159
706k8618773159
Inclist_map_inline:nn
inpeter_color_store:n
you're missing an additional group aroundcolor{##1}
.
– Skillmon
Dec 16 at 8:37
@Skillmon It's not necessary, as the code is executed inside a box being built and then unused.
– egreg
Dec 16 at 10:46
I'd still do so, just to not lead to bad practise. Somebody not knowing the limitations and seeing this code might write faulty code because he thinks it's generally safe to use it inside a box.
– Skillmon
Dec 16 at 13:01
add a comment |
Inclist_map_inline:nn
inpeter_color_store:n
you're missing an additional group aroundcolor{##1}
.
– Skillmon
Dec 16 at 8:37
@Skillmon It's not necessary, as the code is executed inside a box being built and then unused.
– egreg
Dec 16 at 10:46
I'd still do so, just to not lead to bad practise. Somebody not knowing the limitations and seeing this code might write faulty code because he thinks it's generally safe to use it inside a box.
– Skillmon
Dec 16 at 13:01
In
clist_map_inline:nn
in peter_color_store:n
you're missing an additional group around color{##1}
.– Skillmon
Dec 16 at 8:37
In
clist_map_inline:nn
in peter_color_store:n
you're missing an additional group around color{##1}
.– Skillmon
Dec 16 at 8:37
@Skillmon It's not necessary, as the code is executed inside a box being built and then unused.
– egreg
Dec 16 at 10:46
@Skillmon It's not necessary, as the code is executed inside a box being built and then unused.
– egreg
Dec 16 at 10:46
I'd still do so, just to not lead to bad practise. Somebody not knowing the limitations and seeing this code might write faulty code because he thinks it's generally safe to use it inside a box.
– Skillmon
Dec 16 at 13:01
I'd still do so, just to not lead to bad practise. Somebody not knowing the limitations and seeing this code might write faulty code because he thinks it's generally safe to use it inside a box.
– Skillmon
Dec 16 at 13:01
add a comment |
Thanks for contributing an answer to TeX - LaTeX Stack Exchange!
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
To learn more, see our tips on writing great answers.
Some of your past answers have not been well-received, and you're in danger of being blocked from answering.
Please pay close attention to the following guidance:
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
To learn more, see our tips on writing great answers.
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2ftex.stackexchange.com%2fquestions%2f466026%2ftest-if-current-color-is-black%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
2
color
stores the current colour incurrent@color
. So you could dousepackage{xcolor}{color{black}globalletmy@black@colorcurrent@color}newcommand*ifblack{ifxmy@black@colorcurrent@color}
.– Skillmon
Dec 15 at 22:20
@Skillmon Better yet:
sbox0{color{black}globalletmy@black@colorcurrent@color}
so no whatsit is added to the main vertical list.– egreg
Dec 16 at 0:00