% \iffalse     ---!!! FIRST META-COMMENT !!!---
% 
% 
% This file is ascii-emoticon-code.dtx from version 1.0
% of the free and open-source LaTeX package "ascii-emoticon,"
% released August 2026.
% 
% Running Plain TeX on ascii-emoticon-code.dtx will
% produce the following files:
% 
%   (1) the package file ascii-emoticon.sty;
% 
%   (2) the derived files ascii-emoticon-heading.tex
%       and ascii-emoticon-user-guide.tex, which are
%       used for typesetting documentation;
% 
%     and
% 
%   (3) a number of other derived files.
% 
% Running LaTeX on ascii-emoticon-code.dtx will produce the
% files listed above as well as the following:
% 
%   (4) the pdf documentation file ascii-emoticon-code.pdf;
% 
%     and
% 
%   (5) a number of other derived files.
% 
% To install emoticon on your computer, run this file
% through Plain TeX or LaTeX and move emoticon.sty
% to a directory searchable by TeX. See the associated
% README.txt file for installation information.
% 
% 
% \fi
% \iffalse     ---!!! SECOND META-COMMENT !!!---
% 
% 
% This file is from version 1.0 of the free and open-source
% LaTeX package "emoticon," released August 2026.
% 
% Copyright 2026 Conrad Kosowsky
% 
% This file may be distributed and modified under the terms 
% of the LaTeX Public Project License, version 1.3c or any 
% later version. The most recent version of this license is 
% available online at
% 
%            https://www.latex-project.org/lppl/
% 
% This Work has the LPPL status "maintained," and the current
% maintainer is the package author, Conrad Kosowsky. He can 
% be reached at kosowsky.latex@gmail.com. The Work consists 
% of the following items:
% 
%   (1) the base file ascii-emoticon-code.dtx;
% 
%   (2) the package file ascii-emoticon.sty;
% 
%   (3) the pdf documentation files ascii-emoticon-code.pdf
%       and ascii-emoticon-user-guide.pdf;
% 
%   (4) the derived file emoticon_heading.tex;
% 
%   (4) all other files created through the configuration 
%       process;
% 
%     and
% 
%   (5) the associated README.txt file.
%
% PLEASE KNOW THAT THIS FREE SOFTWARE IS PROVIDED WITHOUT
% ANY WARRANTY. SPECIFICALLY, THE "NO WARRANTY" SECTION OF
% THE LATEX PROJECT PUBLIC LICENSE STATES THE FOLLOWING:
% 
% THERE IS NO WARRANTY FOR THE WORK. EXCEPT WHEN OTHERWISE
% STATED IN WRITING, THE COPYRIGHT HOLDER PROVIDES THE WORK
% `AS IS’, WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
% OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
% WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
% PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE
% OF THE WORK IS WITH YOU. SHOULD THE WORK PROVE DEFECTIVE,
% YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR, OR
% CORRECTION.
% 
% IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED
% TO IN WRITING WILL THE COPYRIGHT HOLDER, OR ANY AUTHOR
% NAMED IN THE COMPONENTS OF THE WORK, OR ANY OTHER PARTY
% WHO MAY DISTRIBUTE AND/OR MODIFY THE WORK AS PERMITTED
% ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL,
% SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT
% OF ANY USE OF THE WORK OR OUT OF INABILITY TO USE THE WORK
% (INCLUDING, BUT NOT LIMITED TO, LOSS OF DATA, DATA BEING
% RENDERED INACCURATE, OR LOSSES SUSTAINED BY ANYONE AS A
% RESULT OF ANY FAILURE OF THE WORK TO OPERATE WITH ANY
% OTHER PROGRAMS), EVEN IF THE COPYRIGHT HOLDER OR SAID
% AUTHOR OR SAID OTHER PARTY HAS BEEN ADVISED OF THE
% POSSIBILITY OF SUCH DAMAGES.
% 
% For more information, see the LaTeX Project Public License.
% Derivative works based on this software may come with their
% own license or terms of use, and the package author is not
% responsible for any third-party software.
% 
% Happy TeXing!
% 
% 
% \fi
% \iffalse
% 
% The installation and driver files are incorporated into 
% ascii-emoticon-code.dtx, so we do not need to generate them
% separately. The <batchfile> and <driver> tags are for
% reference.
% 
%<*batchfile>
\begingroup
\input docstrip.tex
\keepsilent
\askforoverwritefalse
\preamble

This file is from version 1.0 of the free and open-source
LaTeX package "ascii-emoticon," released August 2026.

Copyright 2026 Conrad Kosowsky

This file may be distributed and modified under the terms 
of the LaTeX Public Project License, version 1.3c or any 
later version. The most recent version of this license is 
available online at

          https://www.latex-project.org/lppl/

This work has the LPPL status "maintained," and the current
maintainer is the package author, Conrad Kosowsky. He can 
be reached at kosowsky.latex@gmail.com.

PLEASE KNOW THAT THIS FREE SOFTWARE IS PROVIDED WITHOUT
ANY WARRANTY. SPECIFICALLY, THE "NO WARRANTY" SECTION OF
THE LATEX PROJECT PUBLIC LICENSE STATES THE FOLLOWING:

THERE IS NO WARRANTY FOR THE WORK. EXCEPT WHEN OTHERWISE
STATED IN WRITING, THE COPYRIGHT HOLDER PROVIDES THE WORK
`AS IS’, WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE
OF THE WORK IS WITH YOU. SHOULD THE WORK PROVE DEFECTIVE,
YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR, OR
CORRECTION.

IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED
TO IN WRITING WILL THE COPYRIGHT HOLDER, OR ANY AUTHOR
NAMED IN THE COMPONENTS OF THE WORK, OR ANY OTHER PARTY
WHO MAY DISTRIBUTE AND/OR MODIFY THE WORK AS PERMITTED
ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL,
SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT
OF ANY USE OF THE WORK OR OUT OF INABILITY TO USE THE WORK
(INCLUDING, BUT NOT LIMITED TO, LOSS OF DATA, DATA BEING
RENDERED INACCURATE, OR LOSSES SUSTAINED BY ANYONE AS A
RESULT OF ANY FAILURE OF THE WORK TO OPERATE WITH ANY
OTHER PROGRAMS), EVEN IF THE COPYRIGHT HOLDER OR SAID
AUTHOR OR SAID OTHER PARTY HAS BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.

For more information, see the LaTeX Project Public License.
Derivative works based on this software may come with their
own license or terms of use, and the package author is not
responsible for any third-party software.

Happy TeXing!

\endpreamble
\generate{\file{ascii-emoticon.sty}
         {\from{ascii-emoticon-code.dtx}{package}}
  \file{ascii-emoticon-user-guide.tex}
    {\from{ascii-emoticon-code.dtx}{user}}
  \file{ascii-emoticon-heading.tex}
    {\from{ascii-emoticon-code.dtx}{heading}}
  \file{ascii-emoticon-doc-patch.tex}
    {\from{ascii-emoticon-code.dtx}{doc}}}
\catcode`\ =12\relax
\immediate\write0{^^J%
*******************************************************^^J%
* Step 1 of the ascii-emoticon installation complete! *^^J%
*******************************************************^^J^^J%
*******************************************************^^J%
* To finish the installation, move ascii-emoticon.sty *^^J%
*       into a directory searchable by TeX once       *^^J%
*     ascii-emoticon_code.dtx is done typesetting     *^^J%
*******************************************************^^J}
\endgroup
\ifx\LaTeX\undefined
  \immediate\write0{Plain TeX format used; quitting now.}
  \immediate\write0{To create ascii-emoticon-code.pdf, run^^J%
    ascii-emoticon-code.dtx through LaTeX.^^J^^J}
  \expandafter\end
\fi
%</batchfile>
%<*driver>
\makeatletter
\documentclass[12pt,doc2,letterpaper]{ltxdoc}
\usepackage[margin=1in]{geometry}
\usepackage[factor=700,stretch=14,shrink=14,step=1]{microtype}
\usepackage{booktabs}
\usepackage{tabularx}
\usepackage{enumitem}
\setlist{topsep=\smallskipamount,itemsep=\smallskipamount,
  parsep=\z@}
\MacroIndent=1.3em

% index stuff
\c@IndexColumns=2
\columnsep=20pt
\let\index@prologue\relax
\EnableCrossrefs\CodelineIndex
\newwrite\@emoticonindex
\immediate\openout\@emoticonindex=\jobname.idxe

\begin{document}
  \def\documentname{Implementation}
  \input ascii-emoticon-heading.tex
  \input ascii-emoticon-doc-patch.tex
  \DocInput{ascii-emoticon-code.dtx}
  
  \vfil\eject
  
  % make the ind files
  \immediate\closeout\@indexfile
  \immediate\closeout\@emoticonindex
  \ifx\directlua\@undefined
    \immediate\write18{makeindex -s gind.ist ascii-emoticon-code.idx}
    \immediate\write18{makeindex -s gind.ist -o
      ascii-emoticon-code.inde ascii-emoticon-code.idxe}
  \else
    \directlua{os.execute("makeindex -s gind.ist
      ascii-emoticon-code.idx")}
    \directlua{os.execute("makeindex -s gind.ist -o
      ascii-emoticon-code.inde ascii-emoticon-code.idxe")}
  \fi
  
  % Load the index
  \section*{Code Index}
  
  Entries refer to lines in the code, and bold means a
  definition.
  
  \input ascii-emoticon-code.ind
  
  \vfill\eject
  
  \section*{Emoticon Index}
  
  Entries refer to lines in the code where a given emoticon
  name appears in |\@emoticonlist|.
  
  \input ascii-emoticon-code.inde
  
\end{document}
%</driver>
%<*package>
% 
% \fi
% 
% 
% \CheckSum{613}
% \init@checksum
% 
% \makeatother
% \CharacterTable
%   {Upper-case   \A\B\C\D\E\F\G\H\I\J\K\L\M\N\O\P\Q\R\S\T\U\V\W\X\Y\Z
%   Lower-case    \a\b\c\d\e\f\g\h\i\j\k\l\m\n\o\p\q\r\s\t\u\v\w\x\y\z
%   Digits        \0\1\2\3\4\5\6\7\8\9
%   Exclamation     \!      Double quote   \"      Hash (number)   \#
%   Dollar          \$      Percent        \%      Ampersand       \&
%   Acute accent    \'      Left paren     \(      Right paren     \)
%   Asterisk        \*      Plus           \+      Comma           \,
%   Minus           \-      Point          \.      Solidus         \/
%   Colon           \:      Semicolon      \;      Less than       \<
%   Equals          \=      Greater than   \>      Question mark   \?
%   Commercial at   \@      Left bracket   \[      Backslash       \\
%   Right bracket   \]      Circumflex     \^      Underscore      \_
%   Grave accent    \`      Left brace     \{      Vertical bar    \|
%   Right brace     \}      Tilde          \~}
% \makeatletter
% 
% 
% ^^A Because of how doc package stores control sequences in
% ^^A the \DoNotIndex list, we have to turn the standard special
% ^^A characters into type "other" inside \MakePrivateLetters;
% ^^A otherwise the package doesn't realize that we are trying
% ^^A to avoid indexing them
% 
% \def\MakePrivateLetters{\makeatletter
%   \@makeother\#
%   \@makeother\$
%   \@makeother\%
%   \@makeother\&
%   \@makeother\^
%   \@makeother\_
%   \@makeother\|
%   \@makeother\~
%   \@makeother\,}
% 
% 
% \DoNotIndex{\NeedsTeXFormat,\ProvidesPackage,\def,\ifx,\PackageError,
%   \@gobble,\@spaces,\space,\string,\bgroup,\egroup,
%   \@ne,\tw@,\thr@@,\relax,\expandafter,\@nil,\noexpand,\let,\edef,
%   \protected,\csname,\endcsname,\ifmmode,\else,\fi,\hbox,\leavevmode,
%   \wlog,\@for,\@i,\do,\@gobbletwo,\count@,\z@,\escapechar,\m@ne,\ifcat,
%   \@nnil,\in@,\ifin@,\@expandtwoargs,\ifcsname,\ifcase,\or,\@tempa,
%   \@onelevel@sanitize,\@firstofone,\@firstofoneQ,\!,\",\#,\$,\%,\&,
%   \',\(,\),\*,\+,\,,\-,\.,\/,\:,\;,\<,\=,\>,\?,\[,\],\`,\^,\_,\|,\~,
%   \cs,\ttcs,\expandafterQA,\toks@,\the,\selectfont,\@onlypreamble,
%   \begingroup,\endgroup,\long,\@gobblethree,\@tempb,\@undefined}
% \DoNotIndexMain{\@backslashchar,\@charlb,\@charrb}
% 
% 
% \noindent This file documents the code for the \textsf{emoticon} package. It is not a user guide! For instructions on adding emoticons to your documents, see |ascii-emoticon-user-guide.pdf|, which is included in the \textsf{emoticon} installation and is available on \textsc{ctan}. Section~1 includes the package declaration and error messages. Section~2 defines the built-in emoticons, and Section~3 lays out the interface for defining new emoticons. Version history, code index, and emoticon index appear at the end of the document.
% 
% 
% 
% \section{Setup and Errors}
% 
% First, the package should declare itself.
%  
% \begin{figure}[b]
% \centerline{\bfseries Table 1: Error Messages\strut}
% \noindent\begin{tabularx}{\textwidth}
%   {lp{2in}<{\raggedright\arraybackslash}X<{\raggedright\arraybackslash}}\toprule
% Error Name & Arguments & Use \\\midrule
% |DefinedError| & |#1|: Emoticon name\break |#2|: |\string|\texttt{\@backslashchar}\meta{command} & If \texttt{\@backslashchar}\meta{command} or |\tt|\meta{command} is already defined\\\midrule
% |MultiTokensError| & |#1|: Multiple (unexpandable) tokens & If should be single token\\\midrule
% |ExtractMathError| & None & If |\emoticon| appears in math mode\\\midrule
% |NotCSError| & |#1|: One (unexpandable) token & If the token is not a control sequence\\\bottomrule
% \end{tabularx}
% \end{figure}
% 
% 
%    \begin{macrocode}
\NeedsTeXFormat{LaTeX2e}
\ProvidesPackage{ascii-emoticon}[2026/08/24 v. 1.0]
%    \end{macrocode}
% We define four error messages as laid out in Table~1. 
%    \begin{macrocode}
\def\EmoticonDefinedError#1#2{\PackageError{ascii-emoticon}
  {Bad emoticon^^Jname "#1."\@gobble}
  {Your \string\DeclareEmoticon\space command was ignored. I^^J%
  can't use "#1" as an emoticon name because^^J%
  the control sequence #2 has already been^^J%
  defined. To resolve this error, make sure^^J%
  your emoticon name does not correspond to^^J%
  a control sequence currently in use.^^J}}
\def\EmoticonMultiTokensError#1{\PackageError{ascii-emoticon}
  {Bad emoticon^^Jname "#1."\@gobble}
  {Your \string\DeclareEmoticon\space command was ignored. I^^J%
  can't use "#1" as an emoticon name because^^J%
  it contains multiple tokens. To resolve this^^J%
  error, make sure your first argument of^^J%
  \string\DeclareEmoticon\space is a single control sequence.^^J}}
\def\EmoticonExtractMathError{\PackageError{ascii-emoticon}
  {Command \string\emoticon^^Jignored in math mode}
  {It looks like you tried to use \string\emoticon\space in^^J%
  math mode, but the command doesn't work inside^^J%
  equations. To resolve this error, call \string\emoticon^^J%
  only in vertical or horizontal mode.^^J}}
\def\EmoticonNotCSError#1{\PackageError{ascii-emoticon}
  {Bad emoticon^^Jname "#1."\@gobble}
  {Your \string\DeclareEmoticon\space command was ignored. I^^J%
  can't use "#1" as an emoticon name because^^J%
  it isn't a control sequence. To resolve this^^J%
  error, make sure to use a control sequence^^J%
  as your emoticon name.^^J}}
%    \end{macrocode}
% A definition macro to create robust macros.
%    \begin{macrocode}
\ifx\protected\@undefined
  \def\emoticon@robust{\DeclareRobustCommand}
\else
  \def\emoticon@robust{\protected\def}
\fi
%    \end{macrocode}
% 
% 
% \section{Built-in Emoticons}
% 
% We need to make sure that when we scan emoticon definitions in what is essentially a verbatim environment. Specifically, we want all the ascii punctuation marks to have catcode 11 or 12. I'm assuming all letters have catcode 11---if not, we'll have bigger problems. This is mostly an issue for the usual special characters, but some packages turn other punction marks into active characters. We also avoid the possibility of \textsf{emoticon} breaking from a more exotic catcode change. We use |\makeatletter| so that we can use a few internal \LaTeX\ macros when we define |\@emoticonlist|.
%    \begin{macrocode}
\def\emoticon@catcodes{%
  \@makeother\!
  \@makeother\"
  \@makeother\#
  \@makeother\$
  \@makeother\%
  \@makeother\&
  \@makeother\'
  \@makeother\(
  \@makeother\)
  \@makeother\*
  \@makeother\+
  \@makeother\,
  \@makeother\-
  \@makeother\.
  \@makeother\/
  \@makeother\:
  \@makeother\;
  \@makeother\<
  \@makeother\=
  \@makeother\>
  \@makeother\?
  \@makeother\[
  \@makeother\]
  \@makeother\^
  \@makeother\_
  \@makeother\`
  \@makeother\|
  \@makeother\~
  \makeatletter}
%    \end{macrocode}
% We come to the built-in emoticon definitions. We call |\emoticon@catcodes| inside a group and set |{| and |}| to catcode 12 because we have a few emoticons that use braces. We still need begin and end group characters, so we set |Q| and |R| to catcodes 1 and 2 respectively. In honor of \textsf{doc}'s use of |^^A| as the comment character, we also set |A| to catcode 14. These settings are okay because none of the emoticons contain |A|, |Q|, or |R|.
% \begingroup
% \expandafter\def\expandafter\MakePrivateLetters\expandafter{^^A
%   \MakePrivateLetters\@makeother\A\@makeother\Q\@makeother\R}
%    \begin{macrocode}
\bgroup
\catcode`\Q=\@ne     % new (temporary) left brace
\catcode`\R=\tw@     % new (temporary) right brace
\catcode`\A=14\relax % new (temporary) percent char
\emoticon@catcodes
\@makeother\{
\@makeother\}
%    \end{macrocode}
% Now scan |\@emoticonlist| with |\@firstofone|. We use |\@backslashchar| with manual expansion because it's an easy way to get a |\| inside |\@emoticonlist|.
%    \begin{macrocode}
\expandafter\egroup
\@firstofoneQ
  \expandafter\def\expandafter\@emoticonlist\expandafterQ\expandafter
%    \end{macrocode}
% \endgroup
% \begingroup
% ^^A We put the emoticon names in a separate index file.
% ^^A That way we can have two indexes, one for control
% ^^A sequences in the document and one for the emoticon
% ^^A names.
% \DoNotIndex{\@backslashchar}^^A
% \let\@indexfile\@emoticonindex
% \noindent The raw emoticon definitions.
%    \begin{macrocode}
    \woot           \@backslashchar(^o^)/,A
    \rabbit         !_!,A
    \tictactoe      #,A
    \payday         $_$,A
    \confused       %),A
    \confusedn      %-),A
    \varbouquet     %>-,A
    \steampunk      %_%,A
    \unphased       '-',A
    \bang           (!),A
    \ppayday        ($_$),A
    \psteampunk     (%_%),A
    \shrine         (&),A
    \punphased      ('-'),A
    \salute         ('-')>,A
    \pufferfish     (*),A
    \lovely         (*^.^*),A
    \pcrazy         (*_*),A
    \psoporific     (--_--),A
    \pderp          (-_-),A
    \pawake         (._.),A
    \calling        (._.)?,A
    \bandage        (::[]::),A
    \ptears         (;_;),A
    \fatcat         (=^.^=)~,A
    \psleepy        (=_=),A
    \asleep         (=_=)zzz,A
    \hug            (>._.)>,A
    \pugh           (>_<),A
    \riddle         (?),A
    \pquestioning   (?_?),A
    \mollusk        (@),A
    \pamazed        (@_@),A
    \punsure        (^_^'),A
    \phappy         (^_^),A
    \beercup        (_)3,A
    \teacup         (_)>,A
    \peyebags       (i_i),A
    \eyeball        (O),A
    \phello         (o_o),A
    \puhoh          (o_O),A
    \pmonocle       (o_q),A
    \pglasses       (p_q),A
    \pteyes         (T_T),A
    \pdead          (x_x),A
    \pworried       (~_~),A
    \star           *,A
    \marge          ****:-),A
    \barbell        *-*,A
    \troll          *8:,A
    \rooster        *:>,A
    \santa          *<]:),A
    \santan         *<]:-),A
    \crazy          *_*,A
    \bola           *~*,A
    \anchor         +-3,A
    \twig           -,A
    \wine           -(,A
    \flower         -*,A
    \horseshoecrab  -*D,A
    \stick          --,A
    \soporific      --_--,A
    \trident        --E,A
    \hammer         -;,A
    \antibody       -<,A
    \cottoncandy    -<>,A
    \luminaire      -<D,A
    \knife          -=,A
    \derp           -_-,A
    \fork           -E,A
    \spoon          -O,A
    \lollipop       -o,A
    \martini        -{,A
    \rocket         .^.,A
    \awake          ._.,A
    \cry            :'(,A
    \cryn           :'-(,A
    \sad            :(,A
    \monkey         :(|),A
    \smiley         :),A
    \mosquito       :-,A
    \sadn           :-(,A
    \monkeyn        :-(|),A
    \smileyn        :-),A
    \mehn           :-/,A
    \catn           :-3,A
    \branch         :-:,A
    \grinn          :-D,A
    \tonguen        :-P,A
    \keepsecretn    :-X,A
    \meh            :/,A
    \cat            :3,A
    \logs           :=:,A
    \bird           :>,A
    \beetle         :@:,A
    \grin           :D,A
    \bug            :O:,A
    \tongue         :P,A
    \keepsecret     :X,A
    \winky          ;),A
    \winkyn         ;-),A
    \jokeyn         ;-D,A
    \tears          ;_;,A
    \jokey          ;D,A
    \duckling       <"=,A
    \wow            <('O')>,A
    \amazing        <(^o^)>,A
    \gah            <(`^`)>,A
    \sunburst       <*>,A
    \batling        <+>,A
    \broken         </3,A
    \heart          <3,A
    \mouse          <:3(_)~~,A
    \penguin        <@>,A
    \paperhat       <],A
    \goose          <^>,A
    \evileye        <O>,A
    \witch          <|:,A
    \stingray       <|>,A
    \satellite      =+=,A
    \comet          =-*,A
    \sleepy         =_=,A
    \plug           =D~,A
    \gnat           >,A
    \crabling       >"<,A
    \bonbon         >*<,A
    \chalice        >-{,A
    \mole           >.<,A
    \mad            >:(,A
    \evil           >:),A
    \madn           >:-(,A
    \eviln          >:-),A
    \devious        >;),A
    \deviousn       >;-),A
    \fish           ><))v)'>,A
    \gnu            >>,A
    \python         >>>,A
    \ugh            >_<,A
    \dragonfly      >j<,A
    \questioning    ?_?,A
    \snail          @,A
    \potato         @-*,A
    \nettle         @-3,A
    \weevil         @->,A
    \lion           @.?,A
    \frog           @:,A
    \squid          @:-,A
    \peacock        @:>,A
    \phage          @=C,A
    \bouquet        @>-,A
    \rose           @>-->--,A
    \owl            @@,A
    \caterpillar    @@:,A
    \eggs           @@@,A
    \lizard         @^>,A
    \amazed         @_@,A
    \varrose        @}->->-,A
    \jellyfish      @~,A
    \fishbones      @~<,A
    \demon          @~>,A
    \office         [&],A
    \moth           [+],A
    \vartiefighter  [-o-],A
    \robot          [:],A
    \powerup        [?],A
    \sandwich       [],A
    \bee            ^*^,A
    \coatl          ^?^,A
    \dragon         ^@^,A
    \happy          ^_^,A
    \unsure         ^_^',A
    \sunglasses     B),A
    \sunglassesn    B-),A
    \mushroom       c-,A
    \pear           C>-,A
    \bell           D-,A
    \plunger        D--,A
    \sconce         D>-,A
    \bread          E3,A
    \toast          E3~,A
    \eyebags        i_i,A
    \varkilroy      m('u')m,A
    \kilroy         m(._.)m,A
    \bat            n(.m.)n,A
    \human          o+<,A
    \angel          O:),A
    \angeln         O:-),A
    \hello          o_o,A
    \uhoh           o_O,A
    \monocle        o_q,A
    \skateboard     o{-<],A
    \glasses        p_q,A
    \teyes          T_T,A
    \crab           V.v.V,A
    \campfire       X*~,A
    \laughingn      X-D,A
    \dead           x_x,A
    \laughing       XD,A
    \dragonfruit    {*},A
    \tiefighter     |-o-|,A
    \street         |:|,A
    \bridge         |=|,A
    \chandelier     }-3,A
    \worm           ~,A
    \homer          ~(_:-(|),A
    \polyp          ~*,A
    \mouseling      ~*:,A
    \rat            ~*>,A
    \alligator      ~*X,A
    \fox            ~:>,A
    \candle         ~=,A
    \dog            ~=*,A
    \wolf           ~=>,A
    \gulper         ~=[,A
    \hammerhead     ~=I,A
    \shark          ~^>,A
    \worried        ~_~,A
    \tea            ~D,A
    \tadpole        ~o,A
    \snake          ~~,A
    \viper          ~~<,A
    \soup           ~~DRR
%    \end{macrocode}
% \endgroup
% \noindent The |\process@emoticon| command defines emoticons. The |#1| argument should a single control sequence, and the |#2| argument should be the emoticon itself. The command defines |#1| to be a |\protected| macro containing (1) a |\relax| to stop any scanning; (2) a check for math mode; and (3) an |\hbox| with the |#2| argument. In math mode, we use |\mathchoice| to select the appropriate font size, and we need braces around the construction to mark it as a single subformula. For example, \TeX\ complains if we say |$^|\meta{emoticon}|$| without the braces around |\mathchoice|. The |\leavevmode| is there in case the user calls the emoticon in vertical mode.
%    \begin{macrocode}
\def\process@emoticon#1#2\@nil{%
  \emoticon@robust#1{\relax
    \ifmmode
      {\mathchoice{\hbox{\fontsize{\tf@size}{\tf@size}\selectfont #2}}%
        {\hbox{\fontsize{\tf@size}{\tf@size}\selectfont #2}}%
        {\hbox{\fontsize{\sf@size}{\sf@size}\selectfont #2}}%
        {\hbox{\fontsize{\ssf@size}{\ssf@size}\selectfont #2}}}%
    \else
      \leavevmode\hbox{#2}%
    \fi}%
%    \end{macrocode}
% Same thing except with a monospaced font. We expand the |\csname| and hence the |\string| when |\escapechar| is $-1$ to avoid an extra |\| inside the control sequence name. We don't need a |\selectfont| inside the |\hbox| this time because |\ttfamily| contains one already.
%    \begin{macrocode}
  \begingroup
    \escapechar\m@ne
    \expandafter
  \endgroup
  \expandafter\emoticon@robust\csname tt\string#1\endcsname{\relax
    \ifmmode
      {\mathchoice{\hbox{\fontsize{\tf@size}{\tf@size}\ttfamily #2}}%
        {\hbox{\fontsize{\tf@size}{\tf@size}\ttfamily #2}}%
        {\hbox{\fontsize{\sf@size}{\sf@size}\ttfamily #2}}%
        {\hbox{\fontsize{\ssf@size}{\ssf@size}\ttfamily #2}}}%
    \else
      \leavevmode\hbox{\ttfamily #2}%
    \fi}}
%    \end{macrocode}
% And then we actually define the emoticons. We loop through |\@emoticonlist| and, for each entry, call |\process@emoticon|.
%    \begin{macrocode}
\wlog{Package emoticon info: Defining emoticons.}
\@for\@i:=\@emoticonlist\do{\expandafter\process@emoticon\@i\@nil}
%    \end{macrocode}
% The |\emoticon| macro expects the following token to be a control sequence defined above or through |\process@emoticon|. It checks if \TeX\ is currently in math mode and if so raises an error. If not, we play a fun game of expansion and gobbling tokens from |\process@emoticon| to leave us with just the contents of the |\hbox|. In order, |\emoticon| needs to
%   \begin{itemize}
%   \item Expand the next token/emoticon control sequence
%   \item Gobble the initial |\relax|
%   \item Expand |\ifmmode|
%   \item Gobble the |\leavevmode| and |\hbox|
%   \item Use |\@firstoftwo| to remove the braces from the emoticon and get rid of the final |\fi| (which would expand to nothing on its own but no reason to avoid doing it now)
%   \end{itemize}
% As mentioned in the user guide, |\emoticon| is not compatible with the |\tt| emoticon control sequences. Using it with them will add an extra |\ttfamily| to whatever you're doing, which is probably bad if you needed to use |\emoticon| in the first place. It would be great to add some error checking here to make sure that |#1| is actually an emoticon control sequence, but I'm not sure how to do that easily and still leave |\emoticon| fully expandable.
%    \begin{macrocode}
\def\emoticon#1{%
  \ifmmode
    \expandafter\EmoticonExtractMathError
  \else
    \expandafter\expandafter\expandafter
      \@extract@emoticon\expandafter\@gobble#1%
  \fi}
\def\@extract@emoticon{\expandafter\expandafter\expandafter
  \@firstoftwo\expandafter\@gobbletwo}
%    \end{macrocode}
% 
% 
% \section{New Emoticons}
% 
% Before anything else, we define a helper macro. This command appears in recent versions of the $2_\epsilon$ kernel, but less recent versions may not have it.
%    \begin{macrocode}
\long\def\@gobblethree#1#2#3{}
%    \end{macrocode}
% The |\DeclareEmoticon| command allows the user to define new emoticons. It takes two arguments:
%   \begin{itemize}
%   \item |#1|: a single control sequence
%   \item |#2|: a string of (ascii) characters
%   \end{itemize}
% Technically, the definition only has a |#1| argument because we scan what would be the |#2| argument later with the correct catcodes using |\sc@nem@tic@n| (or gobble it if there's a problem). Because the package is non-$\epsilon$-\TeX\ friendly, the parameter specification for |\DeclareEmoticon| is different depending on the engine. We store |[1]| or |##1| in |\@tempa| and then expand it as parameter text before defining |\DeclareEmoticon|.
%    \begin{macrocode}
\edef\@tempa{\ifx\protected\@undefined[1]\else##1\fi}
\expandafter\emoticon@robust\expandafter\DeclareEmoticon\@tempa{%
%    \end{macrocode}
% First is error checking, which uses |\count@|. When |\count@| stays 0, that means we can use |#1| for a new emoticon, and when |\count@| ends up positive, that means we encountered an error. We start by checking that |#1| is a single control sequence.
%    \begin{macrocode}
  \count@\z@
  \expandafter\ifx\expandafter\@nnil\@gobble#1\@nnil % is single token?
    \ifcat\relax\noexpand#1% is a cs?
%    \end{macrocode}
% If |#1| is a single control sequence, we can use |\ifin@| to check whether it appears in |\@emoticonlist|. If yes, we are redefining an emoticon that already exists, and that's fine. If no, we check whether |#1| and |\tt#1| are both undefined because the package should not automatically overwrite any definitions, and if both control sequences are free, we are good to go.
%    \begin{macrocode}
      \expandafter\in@\expandafter#1\expandafter{\@emoticonlist}
      \ifin@ % is \cs already an emoticon?
        \wlog{Package emoticon info: Redefining the \string#1 emoticon.}
      \else % \cs is not an emoticon
        \ifx#1\@undefined % is \cs undefined?
%    \end{macrocode}
% If |#1| is not already an emoticon or a defined control sequence, we need to check that |\tt#1| is undefined to prevent something like |\family| or |\default| from becoming an emoticon. We extract the name of |#1| by expanding |\string#1| inside |\@tempa| when |\escapechar| is $-1$, and then we redefine |\@tempa| to contain |\tt#1|.
%    \begin{macrocode}
          \begingroup
            \escapechar\m@ne
            \expandafter
          \endgroup
          \expandafter\def\expandafter\@tempa\expandafter{\string#1}
          \edef\@tempa{\expandafter\noexpand\csname tt\@tempa\endcsname}
          \expandafter\ifx\@tempa\@undefined % is \ttcs undefined?
            \wlog{Package emoticon info: Defining the 
              \string#1\space emoticon.}
%    \end{macrocode}
% Update |\@emoticonlist| with the new emoticon control sequence.
%    \begin{macrocode}
            \expandafter\def\expandafter\@emoticonlist\expandafter
              {\@emoticonlist#1}
%    \end{macrocode}
% Now we set |\count@| to the correct value depending on how the previous sequence of ifs played out.
%    \begin{macrocode}
          \else % \ttcs already defined
            \count@\@ne
          \fi
        \else % \cs already defined
          \count@\tw@
        \fi
      \fi
    \else % not a cs
      \count@\thr@@
    \fi
  \else % cs has multiple tokens
    \count@=4\relax
  \fi
%    \end{macrocode}
% The last part of |\DeclareEmoticon| sets up code to process the emoticon. Inside a group, we set |\emoticon@catcodes| and check the value of |\count@|. If |\count@| is 0, we're okay to define the new emoticon. We (temporarily) redefine |\\|, |\{|, and |\}| to contain catcode-12 versions of each character, and then we call |\sc@nem@tic@n|, which scans and defines the new emoticon.
%    \begin{macrocode}
  \bgroup
    \emoticon@catcodes
    \ifcase\count@
      \let\\\@backslashchar
      \let\{\@charlb
      \let\}\@charrb
      \def\@tempa{#1}
%    \end{macrocode}
% And here's where the magic happens. We store the control sequence that will become the emoticon name in |\@tempa|. We hit the |\or| with an |\expandafter| first, then gobble the last three tokens in the definition of |\DeclareEmoticon|, so |\sc@nem@tic@n| can process the emoticon definition.
%    \begin{macrocode}
      \expandafter\expandafter\expandafter
        \sc@nem@tic@n\expandafter\@gobblethree
%    \end{macrocode}
% For all other cases, we raise an error message and then (1)~finish expanding the |\ifcase|; (2)~gobble what would be the |#2| argument of |\DeclareEmoticon|; and (3)~close the group. Gobbling happens outside the conditional, and it must be before |\egroup| so that |%| has the right catcode. Cases 1 and 2 are when |\tt#1| or |#1| is already defined.
%    \begin{macrocode}
    \or % if \count@ = 1
      \EmoticonDefinedError{\string#1}
        {\expandafter\string\@tempa}
    \or % if \count@ = 2
      \EmoticonDefinedError{\string#1}
        {\string#1}
%    \end{macrocode}
% Cases 3 and 4 are, respectively, if |#1| is not a control sequence or if |#1| contains multiple tokens.
%    \begin{macrocode}
    \or % if \count@ = 3
      \EmoticonNotCSError{\string#1}
    \or % if \count@ = 4
      \def\@tempa{#1}
      \@onelevel@sanitize\@tempa
      \EmoticonMultiTokensError{\@tempa}
    \fi
  \expandafter\egroup\@gobble}
%    \end{macrocode}
% The command to scan the new emoticon. Here |#1| is what would be the second argument of |\DeclareEmoticon|. The macro expands |#1| inside an |\edef| in case it contains |\\|, |\{|, or |\}| (with their temporary new definitions from |\DeclareEmoticon|) and includes an |\egroup| to close the group from |DeclareEmoticon|. Would it be better to use |\scantokens| in the scanning macro in case someone declares an emoticon inside a macro? Maybe, but I think it's okay to not support that functionality. (Currently |\@tempa| holds the control sequence that will be the emoticon name.)
%    \begin{macrocode}
\def\sc@nem@tic@n#1{\egroup
  \edef\@tempb{%
    \noexpand\process@emoticon
    \expandafter\noexpand\@tempa
    #1\noexpand\@nil}
  \@tempb}
%    \end{macrocode}
% Things will probably be fine if we don't restrict |\DeclareEmoticon| to the preamble, but it has the flavor of a preamble-only command.
%    \begin{macrocode}
\@onlypreamble\DeclareEmoticon
\@onlypreamble\process@emoticon
\@onlypreamble\sc@nem@tic@n
%    \end{macrocode}
% Done!
% 
% \vfill\eject
% 
% \section*{Version History}
% 
% New features and changes from each version. Listed in no particular order.
% 
% \begin{multicols*}{2}
% \raggedright\parskip\z@\parindent\z@\leftskip1em\obeylines
% \setbox0\hbox{\hskip 1pt.\hskip 1pt}
% \def\version#1#2{\bigskip\hbox to \hsize{\textbf{#1} \cleaders\copy0\hfill\ #2}\par}
% \def\item{\leavevmode\raise0.5ex\hbox{\vrule height 1pt width 0.5em}\kern1pt}
% \def\item{---\kern0.2ex\relax}^^A
% 
% \version{1.0}{August 2026}
% \item initial release
% 
% 
% \end{multicols*}
% 
% 
% 
% 
% 
% \check@checksum
% 
% \iffalse
%</package>
%<*user>
\makeatletter
\documentclass[12pt]{article}
\usepackage[margin=1in]{geometry}
\usepackage[factor=700,stretch=14,shrink=14,step=1]{microtype}
\usepackage{booktabs}
\usepackage{tabularx}
\usepackage{shortvrb}

\MakeShortVerb{|}
\edef\pipe{\string|}
\let\sectionname\relax

\tabcolsep=3pt

\def\meta#1{$\langle$\textit{#1}$\rangle$}

% \mybox is 8 characters wide in monospece font
\newbox\mybox
\setbox\mybox\hbox{\ttfamily--------}
\def\colwd{\wd\mybox}

\begin{document}

\def\documentname{User Guide}
\input ascii-emoticon-heading.tex


\noindent The \textsf{ascii-emoticon} package defines control sequences for 222 ASCII emoticons. This package does not provide access to emojis---other packages can accomplish that task. The package provides two modest advantages over typing emoticons by hand. First, control sequences can shorten the names of long emoticons. For example, |\fish| is easier to type than |><))v)'>|. Second, \textsf{ascii-emoticon} handles catcodes automatically, which saves the user from having to type |\verb| or use unexpandable control sequence such as |\$| or |\%|, which can be relevant for certain niche use cases. I divided the control sequences into ``standard'' emoticons, which I've seen before or found references to, and ``nonstandard'' emoticons, which are short strings that vaguely resemble their meaning. Emoticons work in regular text and math mode.

Users who want to create their own emoticons or redefine the commands in this package should use |\DeclareEmoticon|. It should appear only in the preamble, and its syntax is
\begin{code}
|\DeclareEmoticon{|\meta{control sequence}|}{|\meta{emoticon}|}|
\end{code}
This command defines \textit{control sequence} to expand to \textit{emoticon}. The emoticon can contain any special characters other than |\|, |{|, and |}|. To include these characters in the \textit{emoticon}, users should type |\\|, |\{|, or |\}| respectively. The package will not redefine control sequences that already have meanings if those meanings are not emoticons. If you must redefine a control sequence, say |\mycs|, to be an emoticon, you should undefine it by typing
\begin{code}
|\let\mycs\undefined|
\end{code}
before using |\DeclareEmoticon|.

Control sequence names are straightforward. A |p| at the beginning of the control sequence means parentheses, and an |n| at the end means ``nose'' (in the case of face-like emoticons). Each emoticon control sequence typesets the characters normally, and you can add |tt| to the beginning of the control sequence to convert the characters to the current fixed-width font. For example, |\smiley| produces :), and |\ttsmiley| produces |:)|.

For advanced users: emoticon control sequences are not expandable, but if you need the list of characters that form the emoticon, for example to include inside an |\edef| or |\write|, you should preface the emoticon name with |\emoticon|. For example,
\begin{code}
|\immediate\write\mywrite{\winkyn}|
\end{code}
writes |\winkyn| to |\mywrite|, but
\begin{code}
|\immediate\write\mywrite{\emoticon\winkyn}|
\end{code}
writes |;-)| to |\mywrite|. If you use |\emoticon| with a |tt| emoticon name, you will end up with an extra |\ttfamily|. The |\emoticon| command is not valid in math mode.




\begin{figure}[t]
\centerline{\bfseries Standard Emoticons\strut}
\noindent\begin{tabularx}\textwidth{p{\colwd}Xp{\colwd}Xp{\colwd}X}\toprule
Mark & Control Sequence & Mark & Control Sequence & Mark & Control Sequence\\\midrule
|$_$| & |\payday| & |*<]:)| & |\santa| & |>:)| & |\evil| \\
\texttt{\@percentchar)} & |\confused| & |*<]:-)| & |\santan| & |>:-(| & |\madn| \\
\texttt{\@percentchar-)} & |\confusedn| & |*_*| & |\crazy| & |>:-)| & |\eviln| \\
\texttt{\@percentchar\string_\@percentchar} & |\steampunk| & |--_--| & |\soporific| & |>;)| & |\devious| \\
|'-'| & |\unphased| & |-_-| & |\derp| & |>;-)| & |\deviousn| \\
|($_$)| & |\ppayday| & |._.| & |\awake| & |><))v)'>| & |\fish| \\
\texttt{(\@percentchar\string_\@percentchar)} & |\psteampunk| & |:'(| & |\cry| & |>_<| & |\ugh| \\
|('-')| & |\punphased| & |:'-(| & |\cryn| & |?_?| & |\questioning| \\
|('-')>| & |\salute| & |:(| & |\sad| & |@>-->--| & |\rose| \\
|(*^.^*)| & |\lovely| & \texttt{:(\pipe)} & |\monkey| & |@_@| & |\amazed| \\
|(*_*)| & |\pcrazy| & |:)| & |\smiley| & \texttt{@\@charrb->->-} & |\varrose| \\
|(--_--)| & |\psoporific| & |:-(| & |\sadn| & |[-o-]| & |\vartiefighter| \\
|(-_-)| & |\pderp| & \texttt{:-(\pipe)} & |\monkeyn| & |[:]| & |\robot| \\
|(._.)| & |\pawake| & |:-)| & |\smileyn| & \texttt{\@backslashchar(\string^o\string^)/} & |\woot| \\
|(._.)?| & |\calling| & |:-/| & |\mehn| & |^_^| & |\happy| \\
|(::[]::)| & |\bandage| & |:-3| & |\catn| & |^_^'| & |\unsure| \\
|(;_;)| & |\ptears| & |:-D| & |\grinn| & |B)| & |\sunglasses| \\
|(=^.^=)~| & |\fatcat| & |:-P| & |\tonguen| & |B-)| & |\sunglassesn| \\
|(=_=)| & |\psleepy| & |:-X| & |\keepsecretn| & |i_i| & |\eyebags| \\
|(=_=)zzz| & |\asleep| & |:/| & |\meh| & |m('u')m| & |\varkilroy| \\
|(>._.)>| & |\hug| & |:3| & |\cat| & |m(._.)m| & |\kilroy| \\
|(>_<)| & |\pugh| & |:D| & |\grin| & |n(.m.)n| & |\bat| \\
|(?_?)| & |\pquestioning| & |:P| & |\tongue| & |O:)| & |\angel| \\
|(@_@)| & |\pamazed| & |:X| & |\keepsecret| & |O:-)| & |\angeln| \\
|(^_^')| & |\punsure| & |;)| & |\winky| & |o_o| & |\hello| \\
|(^_^)| & |\phappy| & |;-)| & |\winkyn| & |o_O| & |\uhoh| \\
|(_)3| & |\beercup| & |;-D| & |\jokeyn| & |o_q| & |\monocle| \\
|(_)>| & |\teacup| & |;_;| & |\tears| & \texttt{o\@charlb-<]} & |\skateboard| \\
|(i_i)| & |\peyebags| & |;D| & |\jokey| & |p_q| & |\glasses| \\
|(o_o)| & |\phello| & |<('O')>| & |\wow| & |T_T| & |\teyes| \\
|(o_O)| & |\puhoh| & |<(^o^)>| & |\amazing| & |V.v.V| & |\crab| \\
|(o_q)| & |\pmonocle| & |<(`^`)>| & |\gah| & |X-D| & |\laughingn| \\
|(p_q)| & |\pglasses| & |</3| & |\broken| & |x_x| & |\dead| \\
|(T_T)| & |\pteyes| & |<3| & |\heart| & |XD| & |\laughing| \\
|(x_x)| & |\pdead| & |<:3(_)~~| & |\mouse| & \texttt{\pipe-o-\pipe} & |\tiefighter| \\
|(~_~)| & |\pworried| & |=_=| & |\sleepy| & \texttt{\string~(\_:-(\pipe)} & |\homer| \\
|****:-)| & |\marge| & |>:(| & |\mad| & |~_~| & |\worried| \\
\bottomrule
\end{tabularx}
\end{figure}









\begin{figure}[t]
\centerline{\bfseries Nonstandard Emoticons\strut}
\noindent\begin{tabularx}\textwidth{p{\colwd}Xp{\colwd}Xp{\colwd}X}\toprule
Mark & Control Sequence & Mark & Control Sequence & Mark & Control Sequence\\\midrule
|!_!| & |\rabbit| & |<"=| & |\duckling| & |[&]| & |\office| \\
|#| & |\tictactoe| & |<*>| & |\sunburst| & |[+]| & |\moth| \\
\texttt{\@percentchar>-} & |\varbouquet| & |<+>| & |\batling| & |[?]| & |\powerup| \\
|(!)| & |\bang| & |<@>| & |\penguin| & |[]| & |\sandwich| \\
|(&)| & |\shrine| & |<]| & |\paperhat| & |^*^| & |\bee| \\
|(*)| & |\pufferfish| & |<^>| & |\goose| & |^?^| & |\coatl| \\
|(?)| & |\riddle| & |<O>| & |\evileye| & |^@^| & |\dragon| \\
|(@)| & |\mollusk| & \texttt{<\pipe:} & |\witch| & |c-| & |\mushroom| \\
|(O)| & |\eyeball| & \texttt{<\pipe>} & |\stingray| & |C>-| & |\pear| \\
|*| & |\star| & |=+=| & |\satellite| & |D-| & |\bell| \\
|*-*| & |\barbell| & |=-*| & |\comet| & |D--| & |\plunger| \\
|*8:| & |\troll| & |=D~| & |\plug| & |D>-| & |\sconce| \\
|*:>| & |\rooster| & |>| & |\gnat| & |E3| & |\bread| \\
|*~*| & |\bola| & |>"<| & |\crabling| & |E3~| & |\toast| \\
|+-3| & |\anchor| & |>*<| & |\bonbon| & |o+<| & |\human| \\
|-| & |\twig| & \texttt{>-\@charlb} & |\chalice| & |X*~| & |\campfire| \\
|-(| & |\wine| & |>.<| & |\mole| & \texttt{\@charlb*\@charrb} & |\dragonfruit| \\
|-*| & |\flower| & |>>| & |\gnu| & \texttt{\pipe:\pipe} & |\street| \\
|-*D| & |\horseshoecrab| & |>>>| & |\python| & \texttt{\pipe=\pipe} & |\bridge| \\
|--| & |\stick| & |>j<| & |\dragonfly| & \texttt{\@charrb-3} & |\chandelier| \\
|--E| & |\trident| & |@| & |\snail| & |~| & |\worm| \\
|-;| & |\hammer| & |@-*| & |\potato| & |~*| & |\polyp| \\
|-<| & |\antibody| & |@-3| & |\nettle| & |~*:| & |\mouseling| \\
|-<>| & |\cottoncandy| & |@->| & |\weevil| & |~*>| & |\rat| \\
|-<D| & |\luminaire| & |@.?| & |\lion| & |~*X| & |\alligator| \\
|-=| & |\knife| & |@:| & |\frog| & |~:>| & |\fox| \\
|-E| & |\fork| & |@:-| & |\squid| & |~=| & |\candle| \\
|-O| & |\spoon| & |@:>| & |\peacock| & |~=*| & |\dog| \\
|-o| & |\lollipop| & |@=C| & |\phage| & |~=>| & |\wolf| \\
\texttt{-\@charlb} & |\martini| & |@>-| & |\bouquet| & |~=[| & |\gulper| \\
|.^.| & |\rocket| & |@@| & |\owl| & |~=I| & |\hammerhead| \\
|:-| & |\mosquito| & |@@:| & |\caterpillar| & |~^>| & |\shark| \\
|:-:| & |\branch| & |@@@| & |\eggs| & |~D| & |\tea| \\
|:=:| & |\logs| & |@^>| & |\lizard| & |~o| & |\tadpole| \\
|:>| & |\bird| & |@~| & |\jellyfish| & |~~| & |\snake| \\
|:@:| & |\beetle| & |@~<| & |\fishbones| & |~~<| & |\viper| \\
|:O:| & |\bug| & |@~>| & |\demon| & |~~D| & |\soup| \\
\bottomrule
\end{tabularx}
\end{figure}




\end{document}
%</user>
%<*heading>

\csname count@\endcsname\catcode`\@
\makeatletter

% identifying macros
\def\packageversion{1.0}
\def\packagedate{August 2026}

% dimens and registers
\baselineskip=\the\baselineskip plus 0.3pt minus 0.3pt\relax
\c@topnumber\@ne

% section, header, and footer commands
\let\@@section\section
\def\section{\@ifstar\star@sect\no@star@sect}
\def\star@sect#1{\sectionhook{#1}\@@section*{#1}}
\def\no@star@sect#1{\sectionhook{#1}\@@section{#1}}


\def\sectionhook#1{%
  \ifdim\dimexpr\pagegoal-\pagetotal-3pt\relax<6\bigskipamount
    \vfill\eject
  \fi
  \def\sectionname{#1}}

\def\@oddhead{%
  \ifnum\count0>1\relax
    \ifodd\c@page
      \rlap{\textit{\sectionname}}\hfil
      \hbox to 0pt{\hss\documentname\hss}\hfil
      \llap{\the\count0}%
    \else
      \rlap{\the\count0}\hfil
      \hbox to 0pt{\hss\documentname\hss}\hfil
      \llap{\textit{\sectionname}}%
    \fi
  \fi}
\def\@oddfoot{\hfil\ifnum\count0=1\relax1\fi\hfil}


% penalties
\pretolerance=-1
\hyphenpenalty=20
\exhyphenpenalty=15
\brokenpenalty=0
\clubpenalty=0
\widowpenalty=0
\finalhyphendemerits=500
\doublehyphendemerits=2000


% code environment
\let\code\@undefined
\let\endcode\@undefined
\newenvironment{code}
 {\strut\vadjust\bgroup\medskip\parindent\z@\leftskip=4em\relax
   \noindent\strut\ignorespaces}
 {\strut\par\medskip\egroup\hfill\break\strut\ignorespacesafterend}
\def\argtext#1{\ensuremath{\langle$\textit{#1}$\rangle}}
\def\vrb#1{\expandafter\texttt\expandafter{\string#1}}
\def\clap@math#1{\hb@xt@\z@{\hss$\displaystyle#1$\hss}}


% title line
{\large
\parindent=0pt
\leftskip=0pt plus 1 fil
\rightskip=0pt plus 1fil
\parfillskip=0pt
{\strut\Large Package \textsf{ascii-emoticon} v.\ \packageversion\space\documentname}\par
\strut Conrad Kosowsky\par
\strut \packagedate\par
\strut\texttt{kosowsky.latex@gmail.com}\par}

\bigskip

% abstract
{\small
\leftskip=0.5in
\rightskip=0.5in
\centerline{\bfseries Overview\strut}
\noindent The \textsf{ascii-emoticon} package provides control sequences for 222 \textsc{ASCII} emoticons (not emojis) and an interface to define even more. Emoticons work in both regular text and math mode.\par}

\bigskip\bigskip\nointerlineskip
\centerline{\vrule height 0.5pt width 2.5in}\bigskip\bigskip
\nointerlineskip

\catcode`\@\count@


%</heading>
%<*doc>

% definitions and a new toks
\let\?\SpecialUsageIndex
\expandafter\newif\csname if@def\endcsname
\newtoks\index@nomainlist
\index@nomainlist{}
\MacrocodeTopsep=2.5pt plus 3pt minus 1pt
\def\@defname{def}
\def\@edefname{edef}
\def\@letname{let}
\let\main\textbf



% choose macros not to index by definition
\def\DoNotIndexMain{\bgroup
  \catcode`\\=12\relax
  \do@not@index@main}
\def\do@not@index@main#1{\egroup
  \index@nomainlist\expandafter{\the\index@nomainlist#1,}}


% the patch
% 
% \macro@finish gets called at the end of a macro name in
% the macrocode. The first thing we check is if \def, \let, or \edef
% turned on the definition switch. If yes, we add the current
% macro@namepart of the index with SpecialMainIndex, and otherwise
% we add macro@namepart to the SpecialIndex, assuming \macro@namepart
% isn't on the DoNotIndex list

\def\macro@finish{\macro@namepart
  \expandafter\ifx\csname if@def\expandafter\endcsname\csname iftrue\endcsname
    \@deffalse
    \@expandtwoargs\in@{\macro@namepart}{\the\index@excludelist}\relax
    \ifin@
    \else
      \@expandtwoargs\in@{\macro@namepart}{\the\index@nomainlist}\relax
      \ifin@
        \edef\@tempa{\noexpand\SpecialIndex{\bslash\macro@namepart}}\relax
        \@tempa
      \else
        \edef\@tempa{\noexpand\SpecialMainIndex{\bslash\macro@namepart}}\relax
        \@tempa
      \fi
    \fi
  \else
    \ifx\macro@namepart\@defname
      \@deftrue
    \else
      \ifx\macro@namepart\@edefname
        \@deftrue
      \else
        \ifx\macro@namepart\@letname
          \@deftrue
        \fi
      \fi
    \fi
    \@expandtwoargs\in@{\macro@namepart}{\the\index@excludelist}\relax
    \ifin@
    \else
      \edef\@tempa{\noexpand\SpecialIndex{\bslash\macro@namepart}}\relax
      \@tempa
    \fi
  \fi}

% the other patch (just one change: \parskip\z@ to \parskip 0pt plus 0.2pt)
\def\macro@code{%
   \topsep \MacrocodeTopsep
   \@beginparpenalty0% \predisplaypenalty
   \if@inlabel\leavevmode\fi
   \trivlist \parskip 0pt plus 0.2pt \item[]%
   \macro@font
   \leftskip\@totalleftmargin \advance\leftskip\MacroIndent
   \rightskip\z@ \parindent\z@ \parfillskip\@flushglue
   \blank@linefalse \def\par{\ifblank@line
                             \leavevmode\fi
                             \blank@linetrue\@@par
                             \penalty\interlinepenalty}
   \obeylines
   \let\do\do@noligs \verbatim@nolig@list
   \let\do\@makeother \dospecials
   \global\@newlistfalse
   \global\@minipagefalse
   \ifcodeline@index
     \everypar{\global\advance\c@CodelineNo\@ne
               \llap{\theCodelineNo\ \hskip\@totalleftmargin}%
               \check@module}%
   \else \everypar{\check@module}%
   \fi
   \init@crossref}

%</doc>
% 
% \fi
% 
\endinput