4

I am trying to learn expl3 by re-implementing some macros and little packages to take advantage of it.

I am now wondering if there is a more latex3-ish way of doing something like

\raisebox{-\height+\baselineskip}{#1}

which requires calc, given that the ability to make computations on dimensions should be present in expl3.

  • \raisebox{\dimexpr-\height+\baselineskip\relax}{#1}, and as expl3 requires e-TeX.... Here is a private joke, already 20 years ago, physicists were saying that if a "supersymmetric particle" was discovered at CERN (i.e. a particle whose mass is in expected range), then this would "prove" String Theory, because String Theory implements supersymmetry. Based on this physicist reasoning, my remark is expl3 coding. – user4686 Dec 19 '18 at 18:19
3

Here's a possible redefinition, using a key-value interface instead of multiple optional argument for setting the final height and depth.

\documentclass{article}
\usepackage{xparse}

\ExplSyntaxOn
\NewDocumentCommand{\xraisebox}{O{}mm}
 {
  \leavevmode
  \group_begin:
  \keys_set:nn { x/raisebox }
   {
    height=,
    depth=,
    #1
   }
  \x_raisebox:nn { #2 } { #3 }
  \group_end:
 }

\keys_define:nn { x/raisebox }
 {
  height .tl_set:N = \l__x_raisebox_ht_tl,
  depth  .tl_set:N = \l__x_raisebox_dp_tl,
 }

\box_new:N \l__x_raisebox_in_box
\box_new:N \l__x_raisebox_out_box
\dim_new:N \l__x_raisebox_height_dim
\dim_new:N \l__x_raisebox_depth_dim
\dim_new:N \l__x_raisebox_totalheight_dim
\dim_new:N \l__x_raisebox_width_dim

\cs_new_protected:Nn \x_raisebox:nn
 {
  \hbox_set:Nn \l__x_raisebox_in_box { #2 }
  \cs_set_eq:NN \height \l__x_raisebox_height_dim
  \cs_set_eq:NN \depth \l__x_raisebox_depth_dim
  \cs_set_eq:NN \totalheight \l__x_raisebox_totalheight_dim
  \cs_set_eq:NN \width \l__x_raisebox_width_dim
  \dim_set:Nn \l__x_raisebox_height_dim { \box_ht:N \l__x_raisebox_in_box }
  \dim_set:Nn \l__x_raisebox_depth_dim { \box_dp:N \l__x_raisebox_in_box }
  \dim_set:Nn \l__x_raisebox_totalheight_dim { \height+\depth }
  \dim_set:Nn \l__x_raisebox_width_dim { \box_wd:N \l__x_raisebox_in_box }
  \hbox_set:Nn \l__x_raisebox_out_box
   {
    \box_move_up:nn { #1 } { \box_use_drop:N \l__x_raisebox_in_box }
   }
  \tl_if_empty:NF \l__x_raisebox_ht_tl
   {
    \box_set_ht:Nn \l__x_raisebox_out_box { \dim_eval:n { \l__x_raisebox_ht_tl } }
   }
  \tl_if_empty:NF \l__x_raisebox_dp_tl
   {
    \box_set_dp:Nn \l__x_raisebox_out_box { \dim_eval:n { \l__x_raisebox_dp_tl } }
   }
  \box_use_drop:N \l__x_raisebox_out_box
 }

\ExplSyntaxOff

\begin{document}

x\raisebox{3pt}{y\raisebox{3pt}{z}}

x\xraisebox{3pt}{y\xraisebox{3pt}{z}}

\setlength{\fboxsep}{0pt}

\fbox{\xraisebox{3pt}{y}}

\fbox{x\xraisebox{3pt}{y\xraisebox{3pt}{z}}}
\fbox{x\xraisebox{3pt}{y\xraisebox[height=0pt]{3pt}{z}}}
\fbox{x\xraisebox{3pt}{y\xraisebox[height=3pt+0.5\height]{3pt}{z}}}

\fbox{x\xraisebox{-3pt}{y\xraisebox{-3pt}{z}}}
\fbox{x\xraisebox{-3pt}{y\xraisebox[depth=0pt]{-3pt}{z}}}
\fbox{x\xraisebox{-3pt}{y\xraisebox[depth=20pt]{-3pt}{z}}}

\end{document}

The commands \height, \depth, \totalheight and \width are set locally to equate some internal dimensions. Each box is built inside a group to allow nesting.

enter image description here

  • Would using coffins help provide an alternate solution? – Callegar Dec 22 '18 at 23:16
  • @Callegar Most likely. – egreg Dec 22 '18 at 23:18
0

Looks like coffins can help, for instance, the following function can provide different types of vertical alignment:

\NewDocumentCommand { \Vadj } { O{m} m }
  {
    % Beware, this gets out of math mode, so if you are in math mode, you need
    % to re-enter it.
    \hcoffin_set:Nn \l_tmpa_coffin { #2 }
    \str_case:nn { #1 }
      {
        { t }
          {
            \coffin_typeset:Nnnnn \l_tmpa_coffin {l}{H}{0pt}
              { -\coffin_ht:N \l_tmpa_coffin }
          }
        { m }
          {
            \coffin_typeset:Nnnnn \l_tmpa_coffin {l}{H}{0pt}
              { -0.5\coffin_ht:N \l_tmpa_coffin + 0.5\coffin_dp:N
                \l_tmpa_coffin }
          }
        { b }
          {
            \coffin_typeset:Nnnnn \l_tmpa_coffin {l}{H}{0pt}
              { \coffin_dp:N \l_tmpa_coffin }
          }
      }
  }

Just like \risebox, this gets you out of math mode, so if you are in math mode, you need to re-enter it.

It is not 100% clear if this is proper expl3 code, as I have just started learning it, but it seems to do the job.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.