% File: hawkdraw-patterns.code.tex
% Copyright 2026 Jasper Habicht (mail(at)jasperhabicht.de).
%
% This work may be distributed and/or modified under the
% conditions of the LaTeX Project Public License version 1.3c,
% available at http://www.latex-project.org/lppl/.
%
% This file is part of the `hawkdraw' package (The Work in LPPL)
% and all files in that bundle must be distributed together.
%
% This work has the LPPL maintenance status `maintained'.
%
% BOF

% v0.3.0 2026-06-17

\msg_new:nnn { hawkdraw } { pattern-unknown } {
    Pattern ~ `#1` ~ unknown.
}

\prop_new:N \g_hawkdraw_pattern_default_keys_prop
\clist_new:N \l_hawkdraw_pattern_keys_clist
\box_new:N \l_hawkdraw_pattern_box

\dim_new:N \l_hawkdraw_pattern_xunit_dim
\dim_new:N \l_hawkdraw_pattern_yunit_dim

\keys_define:nn { hawkdraw / path } {
    fill ~ pattern          .code:n         = {
        \tl_put_right:Nn \l_hawkdraw_path_postactions_tl {
            \draw_scope_begin:
                \bool_set_true:N \l__hawkdraw_path_clip_bool
                \tl_trim_spaces_apply:nN { \g_hawkdraw_path_clip_tl } \__hawkdraw_path_process:o
                \draw_path_use_clear:n { clip }
                \hawkdraw_pattern_fill:nV {#1} \l_hawkdraw_pattern_keys_clist
                \bool_set_false:N \l__hawkdraw_path_clip_bool
                \bool_gset_false:N \g__hawkdraw_path_use_clip_bool
            \draw_scope_end:
        }
    } ,
    pattern ~ style ~ set   .clist_set:N    = \l_hawkdraw_pattern_keys_clist ,
    pattern ~ style ~ add   .code:n         = {
        \clist_put_right:Nn \l_hawkdraw_pattern_keys_clist {#1}
    } ,
    pattern ~ x             .dim_set:N     = \l_hawkdraw_pattern_xunit_dim ,
    pattern ~ x             .initial:n     = { 10pt } ,
    pattern ~ y             .dim_set:N     = \l_hawkdraw_pattern_yunit_dim ,
    pattern ~ y             .initial:n     = { 10pt } ,
}

\cs_new_protected:Npn \hawkdraw_pattern_fill:nn #1#2 {
    \pdfxform_if_exist:nF {
        hawkdraw_pattern_
        \str_mdfive_hash:n { #1 #2 }
    } {
        \hawkdraw_pattern_set:nn {#1} {#2}
    }
    \hbox_set:Nn \l_hawkdraw_pattern_box {
        \pdfxform_use:n {
            hawkdraw_pattern_
            \str_mdfive_hash:n { #1 #2 }
        }
    }
    \bool_set_false:N \l_draw_bb_update_bool
    \int_step_inline:nnn {
        \fp_to_int:n {
            floor( \g_draw_bb_xmin_dim / \l_hawkdraw_pattern_xunit_dim )
        }
    } {
        \fp_to_int:n {
            floor( \g_draw_bb_xmax_dim / \l_hawkdraw_pattern_xunit_dim )
        }
    } {
        \int_step_inline:nnn {
            \fp_to_int:n {
                floor( \g_draw_bb_ymin_dim / \l_hawkdraw_pattern_yunit_dim )
            }
        } {
            \fp_to_int:n {
                floor( \g_draw_bb_ymax_dim / \l_hawkdraw_pattern_yunit_dim )
            }
        } {
            \draw_box_use:Nn \l_hawkdraw_pattern_box {
                ##1 * \l_hawkdraw_pattern_xunit_dim
                ,
                ####1 * \l_hawkdraw_pattern_yunit_dim
            }
        }
    }
    \bool_set_true:N \l_draw_bb_update_bool
}
\cs_generate_variant:Nn \hawkdraw_pattern_fill:nn { nV }

\cs_new_protected:Npn \hawkdraw_pattern_set:nn #1#2 {
    \pdfxform_new:nnn { hawkdraw_pattern_ \str_mdfive_hash:n { #1 #2 } } { } {
        \draw_suspend_begin:
            \draw_begin:
                \clist_clear:N \l_hawkdraw_path_use_clist
                \keys_set:ne { hawkdraw / path } {
                    \prop_item:Nn \g_hawkdraw_pattern_default_keys_prop {#1}
                }
                \keys_set:nn { hawkdraw / path } {#2}
                \hawkdraw_path_set_options:
                \draw_path_rectangle:nn { 0pt , 0pt } {
                    \l_hawkdraw_pattern_xunit_dim , \l_hawkdraw_pattern_yunit_dim
                }
                \draw_path_replace_bb:
                \bool_set_false:N \l_draw_bb_update_bool
                \use:c { hawkdraw_pattern_ #1 : }
            \draw_end:
        \draw_suspend_end:
    }
}

\cs_new_protected:Npn \hawkdraw_pattern_create:nnn #1#2#3 {
    \prop_gput:Nnn \g_hawkdraw_pattern_default_keys_prop {#1} {#2}
    \cs_new_protected:cpn { hawkdraw_pattern_ #1 : } {
        #3
    }
}

% ===

\hawkdraw_pattern_create:nnn { lines } { } {
    \draw_path_moveto:n { 0pt , 5pt }
    \draw_path_lineto:n { 10pt , 5pt }
    \draw_path_use_clear:n { stroke }
}

\hawkdraw_pattern_create:nnn { hatch } { } {
    \draw_path_moveto:n { 0pt , 5pt }
    \draw_path_lineto:n { 10pt , 5pt }
    \draw_path_moveto:n { 5pt , 0pt }
    \draw_path_lineto:n { 5pt , 10pt }
    \draw_path_use_clear:n { stroke }
}

\hawkdraw_pattern_create:nnn { dots } { } {
    \draw_path_circle:nn { 5pt , 5pt } { 2.5pt }
    \draw_path_use_clear:n { fill }
}

%EOF