1

I am completely new to r, and so I apologise in advance for any rookie mistakes.

I am working with a df containing a large number of TRUE/FALSE, and I want to colour them accordingly - TRUE = green and FALSE = no colour.

The table as of now

Any advice on how to accomplish this in simple, straight forward manner would be much appreciated!

This is as far as I got:

Kube_Liten %>% 
  select(-shape.size) %>% 
  gt() %>% 
  tab_header(
    title = 'Liten Kube',
    subtitle = 'True/False Comparison'
  ) %>% 
  opt_align_table_header(align = 'left')
Novice
  • 15
  • 2
  • 1
    Please read the help files laid out for your education. https://stackoverflow.com/help/how-to-ask; which has a link to https://meta.stackoverflow.com/a/285557 . Also: If you are expecting us to load libraries to support non-base R code, then `library` calls for needed packages should appear before your code blocks. – IRTFM Nov 04 '22 at 01:15

2 Answers2

2

The answer given by @Kat is excellent, but I think it will be somewhat difficult for a "Novice" to fully understand it. I think it will be easier for you to understand the use of a simple for loop.

Using the same table from @Kat's answer, you could do something like this:

df <- gt(df1)

for (i in seq_len(ncol(df1))) {
  df <- df %>%
    tab_style(
      style = cell_text(color = "green"),
      locations = cells_body(columns = names(df1[i]), rows = df1[i] == TRUE)
    )
}
df 

In case you would like to learn more about the !! operator, particularly in the context !!sym("x"), check out this answer: What does the !! operator mean in R, particularly in the context !!sym("x"). Here is another answer that explains this syntax.
When you feel ready for more advanced topics, a good place to start is this.

Brani
  • 6,454
  • 15
  • 46
  • 49
  • Thank you, Brani. I'm just getting into how to use for loops, so this made a little more sense. Just a follow up question: Suppose I wanted the function to ignore a specific column, would that mean I have to replace ncol() with something else? – Novice Nov 05 '22 at 20:07
  • Then, inside the for loop, add an `if` clause and put everything else in it. Say that you wanted to exclude column 3. `if (i!=3){...}`. Or, if you know the name of the column `if (names(df1[i])!="nensbjnktl"){...}` – Brani Nov 06 '22 at 07:36
1

It's really important to make your questions reproducible to get the best answers quickly. In lieu of your data, I created some.

library(gt)
library(tidyverse)

coln = stringi::stri_rand_strings(10, 10, pattern = "[a-z]")

df1 <- map_dfr(1:10, 
               function(j) {
                 set.seed(j)
                 res <- sample(rep(c(TRUE, FALSE), 10), 10) # random select 10
                 setNames(res, coln) # create a data frame row
               })

Right now my data fields all have logical values. If your TRUE is really a string, you'll need to use "TRUE" instead of TRUE.

Since you have multiple columns and any that have true are those you wanted to change, you can simplify it by selecting all columns individually and for each testing for rows that match TRUE. I used lapply to create the locations.

First, here's a function I'll use to create a list of column and row locations to test in my table for conditional formatting.

selector <- function(x, stng = TRUE) {
       cells_body(columns = !!sym(x), 
                  rows = !!sym(x) == stng)
}

Now I'll use the function tab_style to create the styles for my conditionally selected cells. You didn't specify whether you wanted to change the color of the text or the cell background. This first example sets the text colors, where coln is a list of my column names.

df1 %>% gt() %>% 
  tab_style(style = cell_text(color = "green"), # color text
            locations = lapply(coln, selector))

enter image description here

If the true/false values in your table are documented as strings, then in lapply, you need to add a string to replace the default value of stng, i.e., lapply(coln, selector, "TRUE")

If you wanted to set the cell background to green, you would change cell_text to cell_fill.

df1 %>% gt() %>% 
  tab_style(style = cell_fill(color = "green"), # color background
            locations = lapply(coln, selector))

enter image description here

If you don't have the names of your columns separated, there is no need to create another object, just use names() with your data frame. Here's an example of using names along with using alpha or opacity.

df1 %>% gt() %>% 
  tab_style(style = cell_fill(color = "green", alpha = .2),
            locations = lapply(names(df1), selector))

enter image description here

Kat
  • 15,669
  • 3
  • 18
  • 51
  • Thank you so much, for both your advice on how to produce better posts and the answer to my problem that turned out to work perfectly! – Novice Nov 04 '22 at 20:19