Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use colors without defining them beforehand #13

Closed
tobiasBora opened this issue Jan 10, 2022 · 16 comments
Closed

Use colors without defining them beforehand #13

tobiasBora opened this issue Jan 10, 2022 · 16 comments

Comments

@tobiasBora
Copy link

As I explained in this question, using definecolor everytime I want to use a new color can be sometimes cumbersome. Notably, when the color is supposed to be used only once, it does not make sense to create a named color: it is not only time consuming, but it can also lead to strange bugs, for instance if multiple parts of the file redefine the same color by mistake.

As of today, it is possible to use something like \textcolor[HTML]{a65dbd}{...} but it does not generalize to other packages easily, each package need a custom code to accept this optional argument. For instance, it is not possible to do \tikz \node[draw=[HTML]{a65dbd},text=[HTML]{00aa00}]{...}, and people are struggling to find a syntax to add it to existing packages like tabularray lvjr/tabularray#106.

On the other hand, xcolor already accepts pretty involved colors with arguments (which work for any package based on xcolor like tikz or tabularray...), like red!50!white!30.

Would it be possible to follow the approach used in red!50!white!30 to provide a way to use colors without defining them beforehand? Something like model(parameters), such as HTML(00aa52) or rgb(0.1,0.5,0.9)? If it's too hard to get a generic approach, at least could you provide this syntax for the html model as it is used pretty much in all applications?

@josephwright
Copy link
Member

Isn't that already in xcolor as an 'extended' expression?

@tobiasBora
Copy link
Author

tobiasBora commented Jan 10, 2022

Hum, I don't know, but I was not able to make it work:

\documentclass{article}
\usepackage{xcolor}
\usepackage{tikz}
\begin{document}
\textcolor{HTML:a65dbd,1}{This is NOT working}
\tikz \node[draw={HTML:a65dbd,1}]{This is NOT working};
\end{document}

I get an error ERROR: Package xcolor Error: Undefined color a65dbd.. Maybe you could provide an example where this compiles?

@josephwright
Copy link
Member

Hmm. checking I was wrong: the extended models won't help. The thing here is, I suspect, that for xcolor itself the use case is already covered by \textcolor[model]{values}. The fact that some packages using xcolor don't provide an easy way to get to that input form isn't something we can fix from 'here'.

@josephwright
Copy link
Member

In particular, for TikZ the docs say

The ⟨color name⟩ is the name of a previously defined color. For LATEX users, this is just a normal
“LATEX-color” and the xcolor extensions are allowed.

@u-fischer
Copy link
Member

Sorry but it would complicate the parsing quite a lot if something like \color{HTML(00aa52)} would have to be interpreted as \color[HTML]{00aa52} (and it would be error prone).

@tobiasBora
Copy link
Author

I think it is a bit sad to ask to each program using xcolor to implement it on his side because most of the time they will either forget to implement it, or use a syntax which will differ between programs.

Concerning the parsing, I guess you know better than me what you are talking about, but answers like this one suggests that we can easily define a simpler parser that can recognize something like HTML+00aa52 (if this syntax is easier to parse than HTML(...), I'm fine with that). Or to reduce errors, we could define a syntax like <HTML>00aa52, this way the parser would only need to check if the expression is starting with <, then cut the expression after the first > and pass the first and second part to \color. Or maybe I'm missing something?

@u-fischer
Copy link
Member

pass the first and second part to \color

Why do you think that the parts need only to be passed to \color?
Your problem is with colors given in key-val-arguments and you actually don't know what the package really does with the color value. hyperref doesn't use \color for link borders, coloring links use a different syntax and method. And tikz doesn't issue a simple \color either as it has to handle stroke and fill colors and does a lot of low-level manipulations.

@blefloch
Copy link
Member

Even if adding a syntax to xcolor might not make it available in all other packages, it would still help standardize how the color model should be supported.

Perhaps \color{[HTML]00aa52}?

@davidcarlisle
Copy link
Member

Even if adding a syntax to xcolor might not make it available in all other packages, it would still help standardize how the color model should be supported.

Perhaps \color{[HTML]00aa52}?

from the point of view of color and xcolor (and l3color and luacolor etc) that's not really an improvement, just adding a somewhat strained syntax duplicating \color[HTML]{00aa52}. For other interfaces, forcing the already complicated color mix syntax to support inline color models doesn't really seems that natural, eg I'd rather see

\whatever[color-model=HTML, color=00aa52]{zzz}

than

\whatever[color={[HTML]00aa52}]{zzz}

@blefloch
Copy link
Member

blefloch commented Jan 11, 2022 via email

@davidcarlisle
Copy link
Member

well perhaps but that's just user error: if you define a command that takes html colors only then you need to pass that in, no different to any other command you define that may have syntax requirements. If the model isn't fixed as HTML you should expose that as an argument of the command being defined.

@eg9
Copy link

eg9 commented Jan 11, 2022

Cooperation with all other packages that support color would probably be a nightmare.

But in my opinion, this thread starts from a wrong point of view. Colors should be defined by name before their usage, possibly in a special section of the preamble.

Coloring documents is not using whatever color pops out of mind at a given moment. They should be carefully chosen and weighed to mix with each other and in a small number. There's no such thing as “a color that's used only once” in a well formed document. Maybe in a small example one would not bother with defining names that carry some semantic about their usage.

And for a TikZ application, one can just do \definecolor{tempcolor1}[model]{<spec>} in the tikzpicture environment and use draw=tempcolor1. With some advantages. One can define the temporary colors with different models according to some switch, without changing the picture code.

It's possible that a brand new syntax might catch on and be supported in the future by packages such as TikZ/PGF, but I don't really expect it.

@lvjr
Copy link

lvjr commented Jan 11, 2022

In my opinion, the best and easiest solution is to provide only some hook to users and other packages. Then any one could write

\AddToHook{xcolor/undefined}{
  Do something you need
}

@u-fischer
Copy link
Member

For other interfaces, forcing the already complicated color mix syntax to support inline color models doesn't really seems that natural

color={[HTML]{00aa52}} or linkbordercolor=[rgb]{1,0,0} looks a bit strained but it is the syntax supported by hyperref (hycolor) and nicematrix since quite a long time and it follows the syntax of the various color commands.

, eg I'd rather see

\whatever[color-model=HTML, color=00aa52]{zzz}

That would introduce an order requirement into the key list and you would have to handle

`\whatever[color-model=HTML, fillcolor=00aa52, color-model=named, strokecolor=red,color-model=rgb,topcolor={1,0.5,1}]{zzz}`

I don't think that this is worth it. As @eg9 wrote in most cases one should define a color first anyway, and in the cases where using values can make sense like in a \hypersetup the existing syntax is imho ok.

@akloeckner
Copy link

While investigating #15, I browsed through the issues, found this one and thought: Hey, maybe the workaround might work for your use case, too...

I think, some colors can be given as extended expressions, e.g., TikZ seems to accept something like the following:

\documentclass{article}
\usepackage{tikz}

\begin{document}
\begin{tikzpicture}
	\draw[fill={rgb:red,100;green,50;blue,20}]      (5.0,0) rectangle ++(.4,.4);
\end{tikzpicture}
\end{document}

That might be somewhat lengthy, but could maybe be used to specify colors on-the-fly...

@u-fischer
Copy link
Member

I'm closing this as it is not an xcolor issue. xcolor allows to use colors "on-the-fly" with the mentioned syntax \color[rgb]{1,0,0}. Imho this is also a sensible syntax for keyval options (and hyperref supports e.g. linkcolor=[rgb]{0,1,0}) but it is up to packages like tikz to decide if they want to support it or not.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

8 participants