rstudio / rmarkdown

Dynamic Documents for R
https://rmarkdown.rstudio.com
GNU General Public License v3.0
2.88k stars 974 forks source link

wrongly placed plot in html_notebook when markdown content is generated with R #2442

Open SamuelAllain opened 1 year ago

SamuelAllain commented 1 year ago

Hello, I try to dynamically generate markdown sections with plots and I have very weird behaviours both when I compare html_document and html_notebook and when I compare with a constant plot and with a variable plot. The reprex talks for itself :

---
title: "R Notebook"
output:
  html_document: default
  html_notebook: default
---

```{r, results='asis'}
for (i in 1:5) {
  # Section
  cat(sprintf("\n# Test %s\n", i))

  # plot(mtcars[,c(i, 3)])
  # Works well with html_document, not with html_notebook which has a weird behaviour, nothing in first section

  plot(mtcars[,c(2, 3)])
  # doesn't work with neither output :
  # - html_document keeps only one graphic, randomly putting it into section "test 2"
  # - html_notebook has the same weird behaviour as previous cas (c(i,3))

  cat("\n")
}

xfun::session_info('rmarkdown') gives

R version 4.2.1 (2022-06-23)
Platform: x86_64-pc-linux-gnu (64-bit)
Running under: Ubuntu 20.04.5 LTS, RStudio 2022.7.2.576

Locale:
  LC_CTYPE=en_US.UTF-8       LC_NUMERIC=C               LC_TIME=en_US.UTF-8       
  LC_COLLATE=en_US.UTF-8     LC_MONETARY=en_US.UTF-8    LC_MESSAGES=en_US.UTF-8   
  LC_PAPER=en_US.UTF-8       LC_NAME=C                  LC_ADDRESS=C              
  LC_TELEPHONE=C             LC_MEASUREMENT=en_US.UTF-8 LC_IDENTIFICATION=C       

Package version:
  base64enc_0.1.3 bslib_0.4.0     cachem_1.0.6    digest_0.6.30   evaluate_0.19   fastmap_1.1.0  
  fs_1.5.2        glue_1.6.2      graphics_4.2.1  grDevices_4.2.1 highr_0.10      htmltools_0.5.3
  jquerylib_0.1.4 jsonlite_1.8.3  knitr_1.41.9    magrittr_2.0.3  memoise_2.0.1   methods_4.2.1  
  R6_2.5.1        rappdirs_0.3.3  rlang_1.0.6     rmarkdown_2.17  sass_0.4.2      stats_4.2.1    
  stringi_1.7.8   stringr_1.4.1   tinytex_0.42    tools_4.2.1     utils_4.2.1     xfun_0.36      
  yaml_2.3.6     

Pandoc version: 2.19.2

Checklist

When filing a bug report, please check the boxes below to confirm that you have provided us with the information we need. Have you:

cderv commented 1 year ago

Thanks for opening the issue.

html_notebook() is a special format that does not knit but emulate knitr evaluation to get some in chunk preview which will be then shown in a HTML.

This mean that with Notebook you need to execute the chunk first in IDE , then it will be shown in the HTML preview. It seems there is indeed something off with where the plot are inserted and they get not assigned to the right section.

Modified version with title on plots ````markdown --- title: "R Notebook" output: html_notebook: default html_document: default --- ```{r, results='asis'} for (i in 1:5) { # Section cat(sprintf("\n# Test %s\n", i)) plot(mtcars[,c(i, 3)], main = sprintf("Test %s", i)) cat("\n") } ``` ````

I'll dig into that. Thanks for the report

  • html_document keeps only one graphic, randomly putting it into section "test 2"

This is just a edge case because you have one chunk only and plotting the same plot. I think;

Takes this simple example to reproduce

---
title: "R Notebook"
output:
  html_document: default
---

```{r}
plot(1)
plot(1)
plot(1)

@yihui is this suppose to give us 3 plots ? or evaluate in filtering out somehow plots because there are identical recorded plot ? 
Do we have a regression here ? 

## Note about creating mixed content from within R chunk

Regarding creating mix Rmd content with markdown text and code, from a chunk in R, our recommended way is to use `knit_child()`. Example 
````markdown
---
title: "R Notebook"
output:
  html_document: default
---

```{r, echo = FALSE, results='asis'}
res <- lapply(1:5, function(i) {
  knitr::knit_child(text = c(
    "# Test `r i`",
    "",
    "```{r}",
    "plot(mtcars[,c(i, 3)])",
    "```",
    "",
    "Some text"
  ), envir = environment(), quiet = TRUE)
})
cat(unlist(res), sep = '\n')


Unfortunately this requires to knit the file. More in the Cookbook https://bookdown.org/yihui/rmarkdown-cookbook/child-document.html
yihui commented 1 year ago

@yihui is this suppose to give us 3 plots ? or evaluate in filtering out somehow plots because there are identical recorded plot ? Do we have a regression here ?

We don't have a regression. Consecutive identical plots are removed by default. To keep all identical plots, use the chunk option fig.keep = 'all': https://yihui.org/knitr/options/#plots

However, I just tested your example and found the last plot would be removed. I don't know why yet. I can investigate it if it's truly desirable to be able to keep all identical plots.

cderv commented 1 year ago

However, I just tested your example and found the last plot would be removed. I don't know why yet. I can investigate it if it's truly desirable to be able to keep all identical plots.

Yes I tried also fig.keep = 'all' and it seems to me something was off. I don't think that is important as this is a non real example. Just wanted to check that it was expected to have only one plot kept. Thanks