diff options
Diffstat (limited to 'macros/latex/contrib/l3experimental/l3color.dtx')
-rw-r--r-- | macros/latex/contrib/l3experimental/l3color.dtx | 130 |
1 files changed, 116 insertions, 14 deletions
diff --git a/macros/latex/contrib/l3experimental/l3color.dtx b/macros/latex/contrib/l3experimental/l3color.dtx index 9438e8110f..c7addda60b 100644 --- a/macros/latex/contrib/l3experimental/l3color.dtx +++ b/macros/latex/contrib/l3experimental/l3color.dtx @@ -46,7 +46,7 @@ % }^^A % } % -% \date{Released 2020-05-18} +% \date{Released 2020-06-03} % % \maketitle % @@ -61,7 +61,9 @@ % space. In contrast, various proprietary models are available which define % \emph{spot} colors. % -% The models supported here are +% Core models are used to pass color information to output; these are +% \enquote{native} to \pkg{l3color}. Core models use real numbers in the range +% $[0,1]$ to represent values. The core models supported here are % \begin{itemize} % \item \texttt{gray} Grayscale color, with a single axis running from % $0$ (fully black) to $1$ (fully white) @@ -73,7 +75,24 @@ % (see \url{https://helpx.adobe.com/indesign/using/spot-process-colors.html} % for details of the use of spot colors in print) % \end{itemize} -% +% There are also interface models: these are convenient for users but have +% to be manipulated before storing/passing to the backend. Interface models +% are primarily integer-based: see below for more detail. The supported +% interface models are +% \begin{itemize} +% \item \texttt{Hsb} Hue-saturation-brightness color, with three axes, integer +% in the range $[0,360]$ for hue, real values in the range $[0,1]$ for +% saturation and brightness +% \item \texttt{HSB} Hue-saturation-brightness color, with three axes, integer +% in the range $[0,360]$ for hue, integer values in the range $[0,255]$ for +% saturation and brightness +% \item \texttt{HTML} HTML format representation of RGB color given as a +% single six-digit hexadecimal number +% \item \texttt{RGB} Red-green-blue color, with three axes, one for each of +% the components, values as integers from $0$ to $255$ +% \end{itemize} +% All interface models are internally stored as |rgb|. +% % Additional models may be created to allow mixing of spot colors % with each other or with those from other models. See % Section~\ref{l3color:sec:spot} for more detail of spot color support. @@ -267,7 +286,7 @@ % % \begin{macrocode} %<*package> -\ProvidesExplPackage{l3color}{2020-05-18}{} +\ProvidesExplPackage{l3color}{2020-06-03}{} {L3 Experimental color support} %</package> % \end{macrocode} @@ -643,22 +662,28 @@ % \begin{macro}[EXP]{\@@_parse_spot_aux:w} % Turn the input into internal form, also tidying up the number quickly. % \begin{macrocode} -\cs_new:Npn \@@_parse_model_gray:w #1 , #2 \s_@@_stop { \@@_parse_number:n {#1} } +\cs_new:Npn \@@_parse_model_gray:w #1 , #2 \s_@@_stop + { gray ~ \@@_parse_number:n {#1} } \cs_new:Npn \@@_parse_model_rgb:w #1 , #2 , #3 , #4 \s_@@_stop { + rgb ~ \@@_parse_number:n {#1} ~ \@@_parse_number:n {#2} ~ \@@_parse_number:n {#3} } \cs_new:Npn \@@_parse_model_cmyk:w #1 , #2 , #3 , #4 , #5 \s_@@_stop { + cmyk ~ \@@_parse_number:n {#1} ~ \@@_parse_number:n {#2} ~ \@@_parse_number:n {#3} ~ \@@_parse_number:n {#4} } \cs_new:Npn \@@_parse_model_spot:w #1 , #2 \s_@@_stop - { \@@_parse_spot_aux:w #1 ! 100 ! \s_@@_stop } + { + spot ~ + \@@_parse_spot_aux:w #1 ! 100 ! \s_@@_stop + } \cs_new:Npn \@@_parse_spot_aux:w #1 ! #2 ! #3 \s_@@_stop { #1 ~ \fp_eval:n { #2 / 100 } } \cs_new:Npn \@@_parse_number:n #1 @@ -671,6 +696,83 @@ % \end{macro} % \end{macro} % +% \begin{macro}[EXP] +% { +% \@@_parse_model_Hsb:w, \@@_parse_model_HSB:w, +% \@@_parse_model_HTML:w, \@@_parse_model_RGB:w +% } +% \begin{macrocode} +\cs_new:Npn \@@_parse_model_Hsb:w #1 , #2 , #3 , #4 \s_@@_stop + { + \exp_args:Ne \@@_parse_model_hsb:nnn { \fp_eval:n { #1 / 360 } } + {#2} {#3} + } +% \end{macrocode} +% The conversion here is non-trivial but is described at length +% in the \pkg{xcolor} manual. For ease, we calculate the integer +% and fractional parts of the hue first, then use them to work out the +% possible values for $r$, $g$ and $b$ before putting them in the correct +% places. +% \begin{macrocode} +\cs_new:Npn \@@_parse_model_hsb:nnn #1#2#3 + { + rgb ~ + \exp_args:Ne \@@_parse_model_hsb_aux:nnn + { \fp_eval:n { 6 * #1 } } {#2} {#3} + } +\cs_new:Npn \@@_parse_model_hsb_aux:nnn #1#2#3 + { + \exp_args:Nee \@@_parse_model_hsb_aux:nnnn + { \fp_eval:n { floor(#1) } } { \fp_eval:n { #1 - floor(#1) } } + {#2} {#3} + } +\cs_new:Npn \@@_parse_model_hsb_aux:nnnn #1#2#3#4 + { + \use:e + { + \exp_not:N \@@_parse_model_hsb_aux:nnnnn + { \@@_parse_number:n {#4} } + { \fp_eval:n { round(#4 * (1 - #3) ,5) } } + { \fp_eval:n { round(#4 * ( 1 - #3 * #2 ) ,5) } } + { \fp_eval:n { round(#4 * ( 1 - #3 * (1 - #2) ) ,5) } } + {#1} + } + } +\cs_new:Npn \@@_parse_model_hsb_aux:nnnnn #1#2#3#4#5 + { \use:c { @@_parse_model_hsb_ #5 :nnnn } {#1} {#2} {#3} {#4} } +\cs_new:cpn { @@_parse_model_hsb_0:nnnn } #1#2#3#4 { #1 ~ #4 ~ #2 } +\cs_new:cpn { @@_parse_model_hsb_1:nnnn } #1#2#3#4 { #3 ~ #1 ~ #2 } +\cs_new:cpn { @@_parse_model_hsb_2:nnnn } #1#2#3#4 { #2 ~ #1 ~ #4 } +\cs_new:cpn { @@_parse_model_hsb_3:nnnn } #1#2#3#4 { #2 ~ #3 ~ #1 } +\cs_new:cpn { @@_parse_model_hsb_4:nnnn } #1#2#3#4 { #4 ~ #2 ~ #1 } +\cs_new:cpn { @@_parse_model_hsb_5:nnnn } #1#2#3#4 { #1 ~ #2 ~ #3 } +\cs_new:cpn { @@_parse_model_hsb_6:nnnn } #1#2#3#4 { #1 ~ #2 ~ #2 } +\cs_new:Npn \@@_parse_model_HSB:w #1 , #2 , #3 , #4 \s_@@_stop + { + \exp_args:Neee \@@_parse_model_hsb:nnn + { \fp_eval:n {#1 / 360} } + { \fp_eval:n {#2 / 255} } + { \fp_eval:n {#3 / 255} } + } +\cs_new:Npn \@@_parse_model_HTML:w #1 , #2 \s_@@_stop + { \@@_parse_model_HTML_aux:w #1 0 0 0 0 0 0 \s_@@_stop } +\cs_new:Npn \@@_parse_model_HTML_aux:w #1#2#3#4#5#6#7 \s_@@_stop + { + rgb ~ + \fp_eval:n { round(\int_from_hex:n {#1#2} / 255,5) } ~ + \fp_eval:n { round(\int_from_hex:n {#3#4} / 255,5) } ~ + \fp_eval:n { round(\int_from_hex:n {#5#6} / 255,5) } + } +\cs_new:Npn \@@_parse_model_RGB:w #1 , #2 , #3 , #4 \s_@@_stop + { + rgb ~ + \fp_eval:n { round(#1 / 255,5) } ~ + \fp_eval:n { round(#2 / 255,5) } ~ + \fp_eval:n { round(#3 / 255,5) } + } +% \end{macrocode} +% \end{macro} +% % \subsection{Selecting colors (and color models)} % % \begin{variable}{\l_color_fixed_model_tl} @@ -750,11 +852,11 @@ \cs_if_exist:cTF { @@_parse_model_ #1 :w } { \tl_set:Nx #3 - { #1 ~ \use:c { @@_parse_model_ #1 :w } #2 , 0 , 0 , 0 , 0 \s_@@_stop } + { \use:c { @@_parse_model_ #1 :w } #2 , 0 , 0 , 0 , 0 \s_@@_stop } \@@_check_model:N #3 } { - \__kernel_msg_error:nnn { color } { invalid-model } {#1} + \__kernel_msg_error:nnn { color } { unknown-model } {#1} } } % \end{macrocode} @@ -878,18 +980,18 @@ % \subsection{Messages} % % \begin{macrocode} -\__kernel_msg_new:nnnn { color } { invalid-model } - { Invalid~color~model~'#1'. } - { - LaTeX~has~been~asked~to~use~a~color~model~called~'#1',~ - but~this~model~is~not~set~up. - } \__kernel_msg_new:nnnn { color } { unknown-color } { Unknown~color~'#1'. } { LaTeX~has~been~asked~to~use~a~color~named~'#1',~ but~this~has~never~been~defined. } +\__kernel_msg_new:nnnn { color } { unknown-model } + { Unknown~color~model~'#1'. } + { + LaTeX~has~been~asked~to~use~a~color~model~called~'#1',~ + but~this~model~is~not~set~up. + } % \end{macrocode} % % \begin{macrocode} |