Search code examples
r

Is there a way to add superscript and subscript to the same element using ggtext,<sub>&<sup>?


I have a necessary reason to use 'ggtext'

This is not the result I want,You can see that there is a big gap between '2-' and 'O'

library(ggtext)
library(tidyverse)
df <- tibble(
  label = c(
    'SO<sub>4</sub><sup>2-</sup>'
  ),
  x = c(.5),
  y = c(.5),
)
ggplot(df) +
  aes(
    x, y, label = label
  ) +
  geom_richtext() +
  xlim(0, 1)+ 
  ylim(0, 1)

enter image description here

This is the result I want, but this is not achieved with ggtext's html tags sub and sup

enter image description here


Solution

  • I can't find any reference that suggests HTML or markdown support the "atop" notion (aka vertical alignment of superscript and subscript); some answers have even said "not possible", though I can't say with certainty that that's the case.

    This is possible using the basic geom_label and plotmath-expressions.

    Since you said that you have reason to use ggtext, is it possible to separate the labels with this feature?

    df <- tibble(
      label = c(
        'SO<sub>4</sub><sup>2-</sup>',
        "'SO'[4]^'2-'"
      ),
      x = c(.5, .5),
      y = c(.4, .6),
      parse = c(FALSE, TRUE)
    )
    ggplot(df) +
      aes( x, y, label = label ) +
      geom_richtext(data = ~ filter(., !parse)) +
      geom_label(data = ~ filter(., parse), parse=TRUE) +
      xlim(0, 1) + ylim(0, 1)
    

    ggplot with two labels, the first has the superscript and subscript properly aligned vertically, the second is the original and has the subscript first and the superscript slightly to the right

    If desired, you can add some space after the SO to make it a little less cramped; for instance, "'SO '[4]^'2-'" results in

    same plot as above, with a little more horizontal space between the "SO" and the superscript/subscript