rmarkdown & kable/kableextra: Printing % symbol in Table when using escape = F - r

I want to create a table in a pdf-document using rmarkdwon and kable.
In the header there has to be a linebreak, so to do so i need to set escape = F.
The table itself contains percent-values as strings including the % symbol (for example: "13%").
I found here https://tex.stackexchange.com/questions/34580/escape-character-in-latex that % is a special character in La(Tex) and i have to exclude it using \%.
But how can i create and store a string "\%" in R?
I've tried the following but nothing worked for me:
gsub("%", "\%", c("14%", "15%", "16%"))
Error: '\%' is an unrecognized escape in character string starting ""\%"
gsub("%", "\\%", c("14%", "15%", "16%"))
[1] "14%" "15%" "16%"
> cat("\\%")
\%
gsub("%", cat("\\%"), c("14%", "15%", "16%"))
\%
Error in gsub("%", cat("\\%"), c("14%", "15%", "16%")) :
invalid 'replacement' argument
Does anybody know the solution for this problem?
Thanks in advance
edit:
Here is some example code for my problem:
edit of the edit:
in my made up data.frame testtable i forgot to set stringsAsFactors = F.
Thats what caused the differences to my real-data results.
I've added it to the code and updated the output-pictures
---
title: "Table with % and linbebreak"
output:
# html_document: default
pdf_document:
keep_tex: yes
fig_caption: yes
lang: de
---
```{r setup, include=FALSE}
knitr::opts_chunk$set(echo = FALSE, warning = FALSE, error = FALSE, dev=c('pdf','png'), dpi=500)
library(dplyr)
library(data.table)
library(reshape2)
library(knitr)
library(markdown)
library(kableExtra)
library(psych)
library(survey)
library(ggplot2)
set.seed(123)
testtable = data.frame(matrix(paste0(sample(1:100,16, replace = T), "%"), nrow = 4, byrow = T), stringsAsFactors = F)
testtable$group = c("Var1", "Var2", "Var3", "Var4")
testtable = testtable[c(5,1:4)]
colnames(testtable) = c("Variable","All\n(n = 300)", "Group1\n(n = 120)", "Group2\n(n = 100)", "Group3\n(n = 80)")
```
# Table including %-symbol, escape=F not set
```{r}
testtable %>% mutate_all(linebreak) %>%
kable(format = "latex", align = c("l", "c", "c", "c", "c"), caption = "Caption", booktabs = T, col.names = linebreak(names(testtable), align = "c")) %>%
kable_styling(position = "center", latex_options = c("hold_position")) %>%
footnote(general = "* This is a note to show what * shows in this table plus some addidtional words to make this string a bit longer. Still a bit more", threeparttable = T, general_title = "Anmerkung:", title_format = "italic")
```
# Table including %-symbol, escape=F
This leads to an Error, see pic below
```{r}
testtable %>% mutate_all(linebreak) %>%
kable(format = "latex", align = c("l", "c", "c", "c", "c"), caption = "Caption", booktabs = T, escape = F, col.names = linebreak(names(testtable), align = "c")) %>%
kable_styling(position = "center", latex_options = c("hold_position")) %>%
footnote(general = "* This is a note to show what * shows in this table plus some addidtional words to make this string a bit longer. Still a bit more", threeparttable = T, general_title = "Anmerkung:", title_format = "italic")
```
# Table without %-symbol, escape=F set
```{r}
# removing the %
testtable[,2:5] = apply(testtable[,2:5],2,function(f) gsub("%", "", f))
testtable %>% mutate_all(linebreak) %>%
kable(format = "latex", align = c("l", "c", "c", "c", "c"), caption = "Caption", booktabs = T, escape = F, col.names = linebreak(names(testtable), align = "c")) %>%
kable_styling(position = "center", latex_options = c("hold_position")) %>%
footnote(general = "* This is a note to show what * shows in this table plus some addidtional words to make this string a bit longer. Still a bit more", threeparttable = T, general_title = "Anmerkung:", title_format = "italic")
```
Somehow %-symbol does not get displayed.
I have no idea how it comes, since i got other table of the same style (just without a linebreak) and the %-symbol works great.

Use way 2 with gsub("%", "\\\\%", f)).
---
title: "Untitled"
author: "Stéphane Laurent"
date: "28 août 2018"
output:
pdf_document:
keep_tex: yes
editor_options:
chunk_output_type: console
---
```{r setup, include=FALSE}
knitr::opts_chunk$set(echo = FALSE, warning = FALSE, error = FALSE, dev=c('pdf','png'), dpi=500)
library(dplyr)
library(data.table)
library(reshape2)
library(knitr)
library(markdown)
library(kableExtra)
library(psych)
library(survey)
library(ggplot2)
set.seed(123)
testtable = data.frame(matrix(paste0(sample(1:100,16, replace = T), "%"), nrow = 4, byrow = T), stringsAsFactors = F)
testtable$group = c("Var1", "Var2", "Var3", "Var4")
testtable = testtable[c(5,1:4)]
colnames(testtable) = c("Variable","All\n(n = 300)", "Group1\n(n = 120)", "Group2\n(n = 100)", "Group3\n(n = 80)")
```
# Table including %-symbol, escape=F not set
```{r}
testtable %>% mutate_all(linebreak) %>%
kable(format = "latex", align = c("l", "c", "c", "c", "c"), caption = "Caption", booktabs = T, col.names = linebreak(names(testtable), align = "c")) %>%
kable_styling(position = "center", latex_options = c("hold_position")) %>%
footnote(general = "* This is a note to show what * shows in this table plus some addidtional words to make this string a bit longer. Still a bit more", threeparttable = T, general_title = "Anmerkung:", title_format = "italic")
```
# Table including %-symbol, escape=F
This leads to an Error, see pic below
```{r}
testtable[,2:5] = apply(testtable[,2:5],2,function(f) gsub("%", "\\\\%", f))
testtable %>% mutate_all(linebreak) %>%
kable(format = "latex", align = c("l", "c", "c", "c", "c"), caption = "Caption", booktabs = T, escape = F, col.names = linebreak(names(testtable), align = "c")) %>%
kable_styling(position = "center", latex_options = c("hold_position")) %>%
footnote(general = "* This is a note to show what * shows in this table plus some addidtional words to make this string a bit longer. Still a bit more", threeparttable = T, general_title = "Anmerkung:", title_format = "italic")
```
Isnt'it what you want? Otherwise I don't understand.

Another solution is to include the percent sign (or any other string of characters including characters you do want to escape) through custom LaTex commands defined before running kable.
```{r}
library(kableExtra)
library(tidyverse)
```
```{r}
test <- tibble(perc = c('4\\Perc', '34.2\\Perc'),
bla = c('bla','blabla'),
otherLatexCommand = c('\\RA', '\\RA'))
```
\newcommand\Perc{\%}
\newcommand\RA{$\Rightarrow$}
```{r}
test %>% kable('latex', escape=F)
```

Related

How to create a table with math symbols in R Markdown (pdf_document)

I am working on a paper in R Markdown, creating a pdf file. I'd like to create a table which contain math symbols. Below, it my simple code with a table:
```{r setup, include=FALSE}
knitr::opts_chunk$set(echo = TRUE)
```
## R Markdown
```{r echo=FALSE}
library(knitr); library(kableExtra)
df <- data.frame(A=c("Hello!", 100, "$x^2+100$"), L=c(10, "World!", "100+250*1"))
knitr::kable(df, escape = FALSE, booktabs = TRUE,
caption = "An example[note]",
col.names = c("Left", "Right")) %>%
add_indent(c(2, 3), level_of_indent = 1.5, all_cols = TRUE) %>%
add_footnote(c("Source: Book."), notation = "symbol")
```
As a result, every time I knit the file the same error appears:
! Extra alignment tab has been changed to \cr.
<recently read> \endtemplate
I will appreciate if very much if you help me to fix this error.
Using "Xtables" makes it more robust the alignment fallacies:
library(xtable)
df <- data.frame(A=c("Hello!", 100, "$x^2+100$"), L=c(10, "World!", "100+250*1"))
table <- xtable(df, caption = "An example", label = "tab:example", col.names = c("Left", "Right"))
footnote <- list(pos = list(-1), command = c('\\multicolumn{2}{r}{Source: Book.}'))
table <- add.to.row(table, footnote)
print(table, include.rownames = FALSE, floating = FALSE, hline.after = c(-1))
If it doesn't work try this:
library(xtable)
# your dataframe
df <- data.frame(A=c("Hello!", 100, "$x^2+100$"), L=c(10, "World!", "100+250*1"))
# Create the object
table <- xtable(df, caption = "An example", label = "tab:example", col.names = c("Left", "Right"))
# Print what you need
print(table, include.rownames = FALSE, floating = FALSE, hline.after = c(-1), footnote = 'Source: Book.')

Background color for column in kableExtra does not work

A column in a table should have a background color. Somehow with my code this doesn't work. Here a (hopefully) reproducable example:
---
title: "Untitled"
output: pdf_document
---
```{r}
library(dplyr)
data(mtcars)
temp2 <- mtcars[1:5, 1:3]
```
```{r, results='asis'}
cat(
kableExtra::kbl(
x = temp2,
format = "latex",
digits = 2,
col.names = NULL,
booktabs = TRUE,
position = "h",
toprule = NULL,
bottomrule = NULL,
linesep = ""
) %>%
kableExtra::kable_styling(full_width = TRUE) %>%
kableExtra::column_spec(column = 2, background = "green") %>%
kableExtra::row_spec(row = nrow(temp2) - 2, hline_after = TRUE) %>%
kableExtra::row_spec(row = nrow(temp2) - 1, bold = TRUE, extra_latex_after = "\\hline \\hline")
)
```
As you can see in the output the cells are marked with \cellcolor{green} but in the pdf output the column is not green. Also I can see in the output that the first row of the colored column has not this tag \cellcolor{green}, which will be most likely my next problem. Does anybody have a suggestion how I can make this code work? Thanks in advance.

angled column header and width

Please see the rmd file below. I'd like to angle some column headers and have widths be respected.
In the first table without row_spec() the widths are respected but when row_spec() is added to angle a few column headers the widths no longer hold. Any idea how to angle and have the widths remain?
rmd file
---
title: "Untitled"
output: pdf_document
---
```{r setup, include=FALSE}
knitr::opts_chunk$set(echo = TRUE)
library(kableExtra)
```
```{r table1, echo= FALSE, comment = FALSE, message= FALSE, warning = FALSE,results='asis'}
dt <- mtcars[1:5, 1:6]
rownames(dt) = NULL
colnames(dt)= c("long col 1","long col 12","long col 13","long col 14","long col 15","long col 16")
kable(
dt,
format ="latex",
caption = "No angle",
booktabs = T,
longtable = T,
escape = F,
align = "c",
linesep=""
) %>%
kable_styling(latex_options = c("repeat_header" ), font_size=8)%>%
collapse_rows(columns = 1, latex_hline = "major", valign = "middle") %>%
column_spec(c(1,2,3,4,5,6), width = c("8em","5em","6em","3em","3em","3em" ) )
```
```{r table2, echo= FALSE, comment = FALSE, message= FALSE, warning = FALSE,results='asis'}
kable(
dt,
format ="latex",
caption = "With Angled columns",
booktabs = T,
longtable = T,
escape = F,
align = "c",
linesep=""
) %>%
kable_styling(latex_options = c("repeat_header" ), font_size=8)%>%
collapse_rows(columns = 1, latex_hline = "major", valign = "middle") %>%
row_spec(0, angle = c(rep(0,2),rep(90,2),rep(0,2) ) )%>%
column_spec(c(1,2,3,4,5,6), width = c("8em","5em","6em","3em","3em","3em" ) )
```

Map cell colors to data values in kableExtra to create a heatmap table

I have a table below and would like to apply ROW-level heat maps.
(1) Any idea how? Right now the heat map is the same for both values in the single row below.
(2) Is there a way to make the header for the group column NOT be angled 90 degrees? Right now all headers are angled but for the group column it be better without angle=90.
here is the rmd file.
---
title: "Untitled"
output: pdf_document
---
```{r setup, include=FALSE}
knitr::opts_chunk$set(echo = TRUE)
library(dplyr)
library(kableExtra)
#d = data.frame(group= c("A","b"),cat1=c(2,50),cat2=c(100,2))
d = data.frame(group= c("A"),cat1=c(2),cat2=c(NA))
d = d %>%
mutate_if(is.numeric, function(x) {
cell_spec(x, "latex", bold = F, background = spec_color(x,option="C", begin=.5, end = 0.99))
})
```
```{r table , echo= FALSE, comment = FALSE, message= FALSE, warning = FALSE, fig.height=3, fig.width = 8}
kable(
d, format ="latex",
caption = "",
booktabs = T,
longtable = T,
escape = F ,
align = "c"
) %>% kable_styling(latex_options = c(
"striped",
"repeat_header"
)
)%>% row_spec( 0,angle = 90)
```
Note: Ideally it'd be good to have this done with the kableExtra functionality so they color schemes match exactley to other kableExtra tables.
I'm actually not sure how to get the desired color mapping from spec_color. As an alternative, in the code below I've generated the color mapping using the colorRamp function and a palette-generating function, which can be adjusted as desired. The code also deals with missing values by coloring them light gray.
---
output: pdf_document
---
```{r setup, include=FALSE}
knitr::opts_chunk$set(echo = TRUE)
library(viridis)
library(dplyr)
library(kableExtra)
set.seed(2)
d = data_frame(group = sample(LETTERS[1:5], 10, replace=TRUE), cat1=runif(10, 0, 100), cat2=runif(10, 0, 100))
d[5,2] = NA
max.val = max(d[ , sapply(d, is.numeric)], na.rm=TRUE)
#pal.fnc = colorRamp(viridis_pal(option="C")(2))
pal.fnc = colorRamp(c("red", "yellow", "green"))
d = d %>%
mutate_if(is.numeric, function(x) {
cell_spec(round(x,1), "latex", bold = F, color=grey(.3),
background = rgb(pal.fnc(x/max.val) %>% replace(., is.na(.), 200), maxColorValue=255))
})
```
```{r table , echo= FALSE, comment = FALSE, message= FALSE, warning = FALSE, fig.height=3, fig.width = 8}
kable(
d, format ="latex",
linesep="",
caption = "",
booktabs = T,
longtable = T,
escape = F ,
align = "c"
) %>% kable_styling(latex_options = c(
"striped",
"repeat_header"
)
)
```

kableExtra how to use cell_spec from a user defined range?

First, the package kableExtra indeed produces awesome table. I just have an additional request :
When running this example ( from the manual)
iris[1:10, ] %>% select(-Species) %>%
mutate_if(is.numeric, function(x) {
cell_spec(x, "latex", bold = T, color = spec_color(x, end = 0.9),
font_size = spec_font_size(x))
}) %>%
kable("latex", escape = F, booktabs = T, linesep = "", align = "c")
The cells are formated in each column. (1) How to adjust them to the entire table ? (2) Or to a user defined scale ? I noticed that both kableExtra::spec_color and
kableExtra::cell_spec make use of the scales::rescale function which does take a from argument but it's not used in the functions.
Below code of reproducible .Rnw script.
\documentclass{article}
\usepackage[usenames,dvipsnames,svgnames,table]{xcolor}
\usepackage{booktabs}
\usepackage{float}
\usepackage{colortbl}
\begin{document}
<<tab10, echo=FALSE, results="as.is">>=
require(knitr)
require(kableExtra)
require(tidyverse)
#
<<tab1, echo=FALSE, results="as.is">>=
require(knitr)
require(kableExtra)
require(tidyverse)
iris[1:10, ] %>% select(-Species) %>%
mutate_if(is.numeric, function(x) {
cell_spec(x, "latex", bold = T, color = spec_color(x, end = 0.9),
font_size = spec_font_size(x))
}) %>%
kable("latex", escape = F, booktabs = T, linesep = "", align = "c")
#
\end{document}
Okay, with the latest dev ver, you can use scale_from in spec_color, spec_font_size & spec_angle.
library(kableExtra)
library(dplyr)
library(knitr)
iris[1:10, ] %>%
select(-Species) %>%
mutate_if(is.numeric, function(x) {
cell_spec(x, "latex", bold = T,
color = spec_color(x, end = 0.9, scale_from = range(unlist(iris[1:10, ]))),
font_size = spec_font_size(x, scale_from = range(unlist(iris[1:10, ]))))
}) %>%
kable("latex", escape = F, booktabs = T, linesep = "", align = "c")

Resources