ms-wordquartocaptiongtcross-reference

Cross-references and captions not working when using gt in Quarto with Word output


I have been struggling with this off-and-on for a long time. I keep looking at gt() github, stackoverflow, etc... but just end up more confused. I seem to find posts suggesting gt() is working properly with Word. But when I try it, that does not seem to be true.

The issue is that I want to

  1. use Quarto,
  2. have MS Word output,
  3. use gt() to generate tables,
  4. be able to cross-reference those tables, and
  5. (optional) have or suppress captions.

Below is my qmd file contents:

---
title: "Test"
format: docx
---

## Try with gt package 

I want to reference my table (@tbl-test), and either have a caption or suppress the missing caption.


```{r}
#| label: tbl-test
#| tbl-cap: "This is a test caption"

library(gt)

tbl <- 
  gt(
    head(mtcars),
    caption = "This is a caption"
  ) |>
  tab_header(title = "This is a Title")

tbl

```

## Try with kable package 

Does it work to reference (@tbl-iris)?

```{r}
#| label: tbl-iris
#| tbl-cap: "Iris Data"

library(knitr)

kable(head(iris))
```

When I run this code, I get the following Word output. Please notice the following:

  • cross reference NOT working for gt() but IS working for kable
  • (?caption) added by gt(). I truncated the output, but kable doesn't do this

Any help would be greatly appreciated (and usual apologies if this has been answered - I searched pretty extensively and couldn't find it).


docx output from qmd file


Solution

  • I have been in your shoes before.
    See the hacky solution below, where we using a hidden dummy table:

    ---
    title: "Hacky cross-references and captions when using gt in Quarto with Word output"
    format: docx
    ---
    
    I want to reference my table (@tbl-test) and have a caption.
    
    ```{r}
    #| label: tbl-test
    #| tbl-cap: "This is a test caption"
    #| message: false
    #| echo: false
    
    # hidden dummy table
    knitr::kable(x = NULL, 
                 format = "html" #, 
                 # caption = "This is a test caption {#tbl-test}" # disable 'caption' after version v1.4.404
                 )
    ```
    
    ```{r}
    #| message: false
    #| echo: false
    tbl <- 
      gt::gt(head(mtcars)) |>
      gt::tab_header(title = gt::md("This is a Title"),   # title = gt::md("")
                     subtitle = gt::md("This is a Subtitle")) |>
      gt::tab_caption(caption = gt::md("This is a test caption"))
    
    tbl
    ```
    
    Referencing (@tbl-iris)
    
    ```{r}
    #| label: tbl-iris
    #| tbl-cap: "Iris Data"
    #| message: false
    #| echo: false
    knitr::kable(head(iris))
    ```
    
    See @tbl-test and @tbl-iris
    

    Output:
    enter image description here

    Also, see discussion in Quarto#6838 with another hacky solution and the reason why it happens, if interested.