Как использовать pagedown и kable в R для печати таблицы с последующим разрывом страницы

Несколько дней ломал голову над этим.

Я использую пакет pagedown для написания отчета с таблицами переменной длины. Я больше всего знаком и доволен работой с таблицами kableExtra. Однако, поскольку существует переменная длина, а параметры longtable (насколько я могу судить) ориентированы на латекс, а не на html-страницу, я пытаюсь сгруппировать и распечатать фрагменты таблиц. Упрощенный пример: каждые 10 строк записывается таблица и вставляется эквивалент разрыва страницы.

Вот минимальный пример. В этом примере содержимое может выходить за поля, и это нормально, меня просто беспокоит вертикальный интервал.

---
output: 
  pagedown::html_paged:
    toc: false
---

```{r setup, include=FALSE}
knitr::opts_chunk$set(echo = FALSE)

library(ggplot2)
library(kableExtra)
library(dplyr)
```

```{r, results='asis'}
tabs <- 
  ggplot2::mpg %>%
    dplyr::group_by(grp = ceiling(row_number()/20)) %>%
    summarise(tables = list(
      kable(cur_data()) %>%
        kable_styling() %>%
        collapse_rows(1, valign = 'top'))) %>%
      select(tables) %>%
      unlist()
  
for (i in 1:length(tabs)) {
  cat(tabs[i])
  cat('\newpage  ')
}
```

person Kent Orr    schedule 21.09.2020    source источник
comment
Почему бы не получить вывод как html_document?   -  person Daniel Jachetta    schedule 22.09.2020
comment
Конечная цель — вывод на печать. вывод pagedown html_paged дает (в основном) надежный вывод, который можно просмотреть в браузере, а также распечатать.   -  person Kent Orr    schedule 22.09.2020


Ответы (2)


Обычно вы определяете разрывы страниц для своих элементов в пользовательской таблице стилей. Таблицы, созданные с помощью knitr::kable, представляют собой классические table элементы HTML. Если мы хотим иметь разрыв страницы после каждой таблицы, мы должны определить его в таблице стилей (например, custom.css), например

table {
  font-size: 0.5em;  /* table width would extent the page margins otherwise */
  break-after: page; /* move the content following a table to the next page */
}

В нашем документе rmarkdown нам нужно будет только включить дополнительные стили CSS:

---
output: 
  pagedown::html_paged:
    toc: false
    css: [default, default-page, default-fonts, custom.css]
---

Обратите внимание, что мы сначала включаем три таблицы стилей по умолчанию, а затем добавляем наши.

Полный документ будет выглядеть так:

---
output: 
  pagedown::html_paged:
    toc: false
    css: [default, default-page, default-fonts, test.css]
---
  
```{r setup, include=FALSE}
knitr::opts_chunk$set(echo = FALSE)

library(ggplot2)
library(kableExtra)
library(dplyr)
library(knitr)
```

```{r, results = 'asis', message=F, warning=F}
tabs <- 
  ggplot2::mpg %>%
  dplyr::group_by(grp = ceiling(row_number()/20)) %>%
  summarise(tables = list(
    kable(cur_data()) %>%
      kable_styling() %>%
      collapse_rows(1, valign = 'top'))) %>%
  select(tables) 

invisible(lapply(tabs$tables, cat))
```

где я использовал invisible, чтобы скрыть нежелательный вывод от lapply, который оценивает каждый элемент списка, используя cat.

Результат выглядит следующим образом:

введите здесь описание изображения

person Martin Schmelzer    schedule 29.09.2020
comment
Я понятия не имел, что ты можешь использоватьkable() внутри summarise(). @MartinSchmelzer Престижность! - person Julie; 13.05.2021

Итак, я изо всех сил пытался определить правила css, которые вызывали разрывы страниц и т. Д., Которые, как я полагаю, связаны с функционированием paged.js при рендеринге документа pagedown.

Pagedown создает класс css .page-break-before, который, как вы уже догадались, отображает разрыв страницы.

Мое решение состояло в том, чтобы обернуть div с классом page-break-before вокруг содержимого цикла for.

for (i in 1:length(tabs)) {
  htmltools::HTML(
    cat(
      paste0(
        div(class = 'page-break-before', tabs[i])
        )
      )
    )
}

И пусть pagedown обрабатывает разрывы страниц для меня.

person Kent Orr    schedule 23.09.2020