% \iffalse meta-comment
%
% Copyright (C) 2011,2012,2013 Zvi Gilboa (zgilboa@virginia.edu)
% 
% This file is part of the `HebrewX' system.
% ------------------------------------------
%
% \def\hebrewxDtxTmp{hebxcore.sty}
% \subsubsection*{\hebrewxDtxTmp}
% \addcontentsline{toc}{subsubsection}{\hebrewxDtxTmp}
% \fi
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%
% \paragraph{Debugging}
%
%   \begin{macro}{*}
% To debug this package, define \cs{if@hebrewx@debug} in
% your document preamble and set it to true prior 
% to loading \texttt{babel}.
%   \end{macro}
%
%    \begin{macrocode}
\def\hebrewx@tmp@newif{\newif\if@hebrewx@debug}
\ifcsname if@hebrewx@debug\endcsname
% (is already defined, do nothing)
\else
    \hebrewx@tmp@newif
\fi
%    \end{macrocode}
%
%    \begin{macrocode}
\if@hebrewx@debug
    \typeout{hebxcore.sty: debugging is on}
\fi
%    \end{macrocode}
%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%
% \paragraph{Package Identification and Prerequisites}
%
% \subparagraph{Load Package Once}
%
%   \begin{macro}{*}
% Check whether the package has already been loaded. If
% it has not, announce file on terminal and proceed.
%   \end{macro}
%
%    \begin{macrocode}
\if@hebrewx@debug
    \typeout{hebxcore.sty: Load Package Once}
\fi
%    \end{macrocode}
%
%    \begin{macrocode}
\csname HebrewXCoreLoaded\endcsname
\let\HebrewXCoreLoaded\endinput
%    \end{macrocode}
%
% \subparagraph{Log Package Information}
%
%    \begin{macrocode}
\def\hebrewx@fileversion{0.1}
\def\hebrewx@filedate{2012/06/01}
\message{\space\space HebrewX Core switching commands 
         v\hebrewx@fileversion\space\space\hebrewx@filedate}
\message{\space\space (Development version:))\space\space}
%    \end{macrocode}
%
%    \begin{macrocode}
\if@hebrewx@debug
    \typeout{hebxcore.sty: (Load Package Once)}
\fi
%    \end{macrocode}
%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%
% \subparagraph{Require a TeX--XeT/eTeX E}
%
%    \begin{macrocode}
\if@hebrewx@debug
    \typeout{hebxcore.sty: Require a TeX--XeT/eTeX Engine}
\fi
%    \end{macrocode}
%
%    \begin{macrocode}
\AtBeginDocument{%
    \ifcsname TeXXeTstate\endcsname
%    \end{macrocode}
%
% Ensure that TeX--XeT/eTeX  is active
%
%    \begin{macrocode}
        \TeXXeTstate=1 
    \fi
%    \end{macrocode}
%
% verify that \cs{beginL} is present
%
%    \begin{macrocode}
    \ifcsname beginL\endcsname
        \typeout{HebrewX: proper TeX--XeT/eTeX engine 
                 has been verified.}
    \else
        \newlinechar`\^^J
%    \end{macrocode}
%
% terminal message
%
%    \begin{macrocode}
        \typeout{^^JTo avoid this error message,^^J%
                run TeX--XeT or e-TeX engine 
                instead of regular TeX.^^J}
%    \end{macrocode}
%
% error message
%
%    \begin{macrocode}
        \errmessage{Right-to-Left Support Error: 
                    use TeX--XeT or e-TeX engine}%
    \fi
}
%    \end{macrocode}
%
%    \begin{macrocode}
\if@hebrewx@debug
    \typeout{hebxcore.sty: (Require a TeX--XeT/eTeX Engine)}
\fi
%    \end{macrocode}
%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%
% \paragraph{Tracing and Language Flags}
%
%   \begin{macro}{\if@rl}
%
% Shared flag between \texttt{Arabi} and \texttt{HebrewX} 
% to record whether we are typesetting in 
% RTL (right-to-left) mode.
%
% As this is a real-time tracing flag, it may be 
% defined more than once (which is the case when 
% \texttt{babel} loads both \oarg{arabic} and
% \oarg{hebrewx}.
%
%    \begin{macrocode}
\if@hebrewx@debug
    \typeout{hebxcore.sty: Tracing and Language Flags}
\fi
%    \end{macrocode}
%
%    \begin{macrocode}
\newif\if@rl
%    \end{macrocode}
%   \end{macro}
%
%   \begin{macro}{\if@hebrew}
%
% Flag to distinguish between the different languages
% that use the Hebrew alphabet and are supported by
% this package.\footnote{%
% While Modern Hebrew \oarg{hebrewx} is the only
% language currently supported by \texttt{HebrewX},
% support may be easily extended to both Yiddish
% and Aramaic.  In terms of functionality, it is 
% already possible to use \texttt{HebrewX} to 
% typeset texts in the two aforementioned languages,
% as all of the relevant glyphs are included in
% the HX8 font encoding, as well as supported by the
% package's Ghost Glyph mechanism.}
%
%    \begin{macrocode}
\newif\if@hebrew
%    \end{macrocode}
%   \end{macro}
%
%   \begin{macro}{\hebrewx@gobbleone}
%
% A small programming utility\ldots
%
%    \begin{macrocode}
\providecommand{\hebrewx@gobbleone}[1]{\relax}
%    \end{macrocode}
%   \end{macro}
%
%    \begin{macrocode}
\if@hebrewx@debug
    \typeout{hebxcore.sty: (Tracing and Language Flags)}
\fi
%    \end{macrocode}
%% 
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%
% \paragraph{Hebrew Font Encoding}
%
%   \begin{macro}{*}
% \texttt{HebrewX} provides the font encoding HX8, 
% an encoding which -- similar to HE8 -- corresponds to
% input code page \textsc{cp1255}.  The advantage of HX8 over
% HE8 is that it implements the slots normally allocated 
% for special Latin symbols (e.g. \emph{macron}) as
% Ghost Glyphs, a mechanism used for the automatic kerning 
% of Hebrew vowels (Nikud).\footnote{%
%   As of the current version, the automatic kerning of 
%   Hebrew cantillation marks should be considered experiemntal.}
%
% In addition to supporting code page \textsc{cp1255}, 
% \texttt{HebrewX} automatically makes the necessary 
% definitions for HX8 to be used with the
% \textsc{utf8} input encoding, and provides a command 
% which loads similar definitions for the HE8 
% font encoding.
%   \end{macro}
%
%    \begin{macrocode}
\if@hebrewx@debug
    \typeout{hebxcore.sty: Hebrew Font Encoding}
\fi
%    \end{macrocode}
%
%   \begin{macro}{\hebrewencoding}
%
% Define HX8 as the default Hebrew encoding.
%
%    \begin{macrocode}
\def\hebrewencoding{HE8}
%    \end{macrocode}
%   \end{macro}
%
%   \begin{macro}{\HebrewEncoding}
%
% Command to make the default Hebrew encoding
% the current font encoding.
%
%    \begin{macrocode}
\newcommand{\HebrewEncoding}{%
            \fontencoding{\hebrewencoding}\selectfont}
%    \end{macrocode}
%   \end{macro}
%
%   \begin{macro}{\@hebrew@R}
%
% Command to print a single (expanded) text argument 
% from right to left in the default Hebrew encoding,
% and enclose it in explicit grouping and text-direction 
% commands.
%
%    \begin{macrocode}
\DeclareRobustCommand{\@hebrew@R}[1]{%
                      \bgroup\beginR\HebrewEncoding 
                        #1\endR\egroup}
%    \end{macrocode}
%   \end{macro}
%
%   \begin{macro}{\@ensure@hebrew}
%
% Similar to \cs{@hebrew@R}, but will only add 
% \cs{beginR} and \cs{endR} commands
% (yet without explicit grouping)
% if not already in right-to-left mode.
%
%    \begin{macrocode}
\DeclareRobustCommand{\@ensure@hebrew}[1]{%
                      \if@rl{%
                        {\HebrewEncoding #1}}%
                      \else%
                        \beginR\HebrewEncoding #1\endR%
                      \fi}
%    \end{macrocode}
%   \end{macro}
%
%   \begin{macro}{\AtEndOfPackage}
%
% As a measure of good at-end-of-package practice,
% ensure that the value stored in \texttt{babel}'s
% \cs{latinencoding} is (reset to) \cs{cf@encoding}.
%
%    \begin{macrocode}
\AtEndOfPackage{\edef\latinencoding{\cf@encoding}}
%    \end{macrocode}
%   \end{macro}
%
%    \begin{macrocode}
\if@hebrewx@debug
    \typeout{hebxcore.sty: (Hebrew Font Encoding)}
\fi
%    \end{macrocode}
%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%% 
% \paragraph{Incidental Insertion of Hebrew or Latin Text}
%
%   \begin{macro}{*}
% Here we handle the insertion of Hebrew text into a
% left-to-right paragraph and vice versa.  In order to
% simplify side-by-side usage of \texttt{Arabi} and 
% \texttt{HebrewX}, we share the commands used for 
% the insertion of incidental Latin (left-to-right) 
% text.  Definitions of these commands should accordingly
% remain identical in both packages.
%   \end{macro}
%
%   \begin{macro}{(\textRL)}
% Note that we do NOT define \cs{textRL},
% specifically since that command is already defined in 
% \texttt{Arabi}.  The \enquote{generic} \cs{textRL}
% is hence used to typeset Arabic (using the \texttt{Arabi} 
% package), whereas the explicit \cs{textHE} should be used 
% to typeset incidental Hebrew.
%   \end{macro}
%
%    \begin{macrocode}
\if@hebrewx@debug
    \typeout{hebxcore.sty: Incidental Insertion of Hebrew or Latin Text}
\fi
%    \end{macrocode}
%
%   \begin{macro}{\textLR}
%
% Command to typeset incidental \enquote{Latin} 
% (that is, left-to-right) text while in right-to-left mode.
% The single (expanded) text argument is enclosed in grouping
% and text-direction commands.
%
%    \begin{macrocode}
\def\textLR#1{\bgroup\beginL\latintext 
              #1\endL\egroup}
%    \end{macrocode}
%   \end{macro}
%
%
% \begin{macro}{\EncodedLatinText}
%
% Similar to \cs{textLR}, but we also explicitly specify
% which font encoding should be used.
%
%    \begin{macrocode}
\def\EncodedLatinText#1#2{\bgroup\beginL%
                            \protect\fontencoding{#1}%
                            \selectfont #2%
                          \endL\egroup}
%    \end{macrocode}
% \end{macro}
%
%
% \begin{macro}{\@ensure@L}
% 
% Similar to \cs{textLR}, but will only add 
% \cs{beginL} and \cs{endL} commands
% (yet without explicit grouping)
% if currently in right-to-left mode.
%
%    \begin{macrocode}
\def\@ensure@L#1{\if@rl\textLR{#1}\else#1\fi}
%    \end{macrocode}
% \end{macro}
%
%
%   \begin{macro}{\LRmbox}
%
% Command to make a left-to-right \cs{mbox}
% using \cs{textLR}
%
%    \begin{macrocode}
\providecommand{\LRmbox}[1]{\mbox{\textLR{#1}}}
%    \end{macrocode}
%   \end{macro}
%
%
%   \begin{macro}{\textHE}
%
% User interface command for the incidental typing 
% of a single text argument using the 
% Hebrew alphabet.
%
%    \begin{macrocode}
\def\textHE#1{\expandafter\@hebrew@R{#1}}
%    \end{macrocode}
%   \end{macro}
%
%
%   \begin{macro}{\@ensure@H}
%
% Similar to \cs{textHE}, however, if we are
% already in right-to-left mode the text argument
% will \textit{not} be surrounded by any grouping, 
% text-direction, or font-encoding commands.
%
%    \begin{macrocode}
\def\@ensure@H#1{\if@rl#1\else\textHE{#1}\fi}
%    \end{macrocode}
%   \end{macro}
%
%
%   \begin{macro}{\HEmbox}
%
% Command to make a Hebrew \cs{mbox}
% using \cs{textHE}
%
%    \begin{macrocode}
\providecommand{\HEmbox}[1]{\mbox{\textHE{#1}}}
%    \end{macrocode}
%   \end{macro}
%
%    \begin{macrocode}
\if@hebrewx@debug
    \typeout{hebxcore.sty: (Incidental Insertion of Hebrew or Latin Text)}
\fi
%    \end{macrocode}
%% 
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%% 
% \paragraph{Ensuring Proper Paragraph Construction}
%
%   \begin{macro}{*}
% In order to allow right-to-left paragraphs to be properly
% constructed, the core \LaTeX\ commands \cs{everypar}, 
% \cs{raggedleft} and \cs{raggedright} must be made
% aware of the paragraph direction.\footnote{%
%   The patch for \cs{everypar} is adapted from the 
%   \texttt{Arabi} package by Youssef Jabri.  The patch
%   for \cs{raggedleft} and {raggedright} is adapted from
%   \texttt{rlbabel.def} by Boris Lavva.}
%
% In order to ensure that patches take place only once 
% (in the case of \cs{raggedleft} and \cs{raggedright} 
% this is indeed crucial, for the new macro definitions 
% refer to the old ones, saved under different names), 
% we define (if necessary) and share with the
% \texttt{Arabi} package the appropriate status flags.
%   \end{macro}
%
% \begin{macro}{\if@rlEveryParPatch}
% Flag (shared with the \texttt{Arabi} package) 
% to record whether \cs{if@rlEveryParPatch}
% has already been patched. \\
%
% Define \cs{if@rlEveryParPatch} if it is yet undefined.
%
%    \begin{macrocode}
\def\hebrewx@tmp@newif{\newif\if@rlEveryParPatch}
%    \end{macrocode}
%
% Check whether the flag has already been defined\ldots
%
%    \begin{macrocode}
\ifcsname if@rlEveryParPatch\endcsname
%    \end{macrocode}
%
% \ldots and define it as needed.
%
%    \begin{macrocode}
\else
    \hebrewx@tmp@newif
\fi
%    \end{macrocode}
%   \end{macro}
%
%
%   \begin{macro}{\everypar}
% 
% Check whether the patch has already been applied,
% and display an appropriate terminal message.
%
%    \begin{macrocode}
\if@rlEveryParPatch
    \typeout{HebrewX: no need to patch everypar}%
%    \end{macrocode}
%
% Even if the patch has already been applied, 
% we still need to define \cs{HebrewX@rl@everypar} 
% as a low-level command.
%
%    \begin{macrocode}
    \def\HebrewX@rl@everypar{\if@rl{\setbox\z@\lastbox%
                                    \beginR\usebox\z@}%
                             \fi} 
\else
    \typeout{HebrewX: patching everypar}%
%    \end{macrocode}
%   \end{macro}
%
%   \begin{macro}{\HebrewX@rl@everypar}
%
% This is the macro which makes \cs{everypar} direction-aware. \\
%
% When \cs{everypar} is redefined for some reason
% (in lists for example), \cs{HebrewX@rl@everypar} will ensure 
% that proper state is restored.
%
% In order for the paragraph indentation to work properly,
% we have to enhance the \cs{everypar} defintion a little.
% Given that a paragraph indent is created by the insertion of
% a \cs{box} at the start of the horizontal list for the paragraph 
% (before \cs{everypar} is called), all we need to do is move that box 
% so that it follows the \cs{beginR} command.
%
%    \begin{macrocode}
    \def\HebrewX@rl@everypar{\if@rl{\setbox\z@\lastbox%
                                    \beginR\usebox\z@}%
                             \fi} 
%    \end{macrocode}
%
% Store the original \cs{everypar}.
%
%    \begin{macrocode}
    \let\o@everypar=\everypar 
%    \end{macrocode}
%
% Create new token register and make necessary adjustments.
%
%    \begin{macrocode}
    \newtoks\n@everypar 
    \n@everypar\expandafter{\the\o@everypar}  
    \o@everypar{\HebrewX@rl@everypar\the\n@everypar} 
%    \end{macrocode}
%
% Update the definition of \cs{everypar}.
%
%    \begin{macrocode}
    \let\everypar=\n@everypar
\fi
%    \end{macrocode}
%   \end{macro}
%
% Record that the patch has now already been applied.
%
%    \begin{macrocode}
\@rlEveryParPatchtrue
%    \end{macrocode}
%
%
%
%   \begin{macro}{\if@rlRaggedPatch}
%
% Flag (shared with the \texttt{Arabi} package) 
% to record whether \cs{raggedleft} and \cs{raggedright}
% have already been patched. \\
%
% Define \cs{if@rlRaggedPatch} if it is yet undefined.
%
%    \begin{macrocode}
\def\hebrewx@tmp@newif{\newif\if@rlRaggedPatch}
%    \end{macrocode}
%
% Check whether the flag has already been defined\ldots
%
%    \begin{macrocode}
\ifcsname if@rlRaggedPatch\endcsname    
%    \end{macrocode}
%
% \ldots and define it as needed.
%
%    \begin{macrocode}
\else
    \hebrewx@tmp@newif
\fi
%    \end{macrocode}
%   \end{macro}
%
%
%   \begin{macro}{\raggedleft}
%   \begin{macro}{\raggedright}
% 
% Check whether the patch has already been applied,
% and display an appropriate terminal message.
%
%    \begin{macrocode}
\if@rlRaggedPatch
    \typeout{HebrewX: no need to patch raggedright and raggedleft}%
\else
    \typeout{HebrewX: patching raggedright and raggedleft}%
%    \end{macrocode}
%
% Here we make \cs{raggedleft} and \cs{raggedright} direction-aware.
% The first step is to (re)create \cs{raggedright} as a
% \enquote{mirror} of \cs{raggedleft} (as defined in \texttt{latex.ltx}),
% namely by switching between the respective calls to \cs{leftskip} 
% and \cs{rightskip} within the control sequence.
% As the next step, we store the (new) definitions of 
% \cs{raggedleft} and \cs{raggedright} in \cs{@@raggedleft}
% and \cs{@@raggedright}, respectively.  Having done that, we 
% redefine \cs{raggedleft} by telling it to execute \cs{@@raggedleft} 
% when in left-to-right mode, but \cs{@@raggedright} when in 
% right-to-left mode.  In conclusion, we instruct \cs{raggedright} to 
% execute either \cs{@@raggedright} or \cs{@@raggedleft} using 
% the very same logic.
%
%    \begin{macrocode}
    \def\raggedright{%
      \let\\\@centercr
      \leftskip\z@skip\rightskip\@flushglue
      \parindent\z@\parfillskip\z@skip}
    \let\@@raggedleft=\raggedleft
    \let\@@raggedright=\raggedright
    \renewcommand\raggedleft{\if@rl\@@raggedright%
                             \else\@@raggedleft\fi}
    \renewcommand\raggedright{\if@rl\@@raggedleft%
                              \else\@@raggedright\fi}
\fi
%    \end{macrocode}
%   \end{macro}
%   \end{macro}
%
% Record that the patch has now already been applied.
%
%    \begin{macrocode}
\@rlRaggedPatchtrue
%    \end{macrocode}
%
%
% \Finale
\endinput
