FredHutch / VISCtemplates

Tools for writing reproducible reports at VISC
Other
4 stars 3 forks source link

Guidance on how to generate figures and tables in a for loop (DRY principle) #156

Open kelliemac opened 1 month ago

kelliemac commented 1 month ago

To follow the DRY (don't repeat yourself) principle, it is sometimes helpful to generate figures and tables in a for loop. For example, in the B-cell reports we are usually generating the same tables and figures repeatedly for different endpoints.

I think this challenge probably also applies in other assays. One approach is as follows:

``{r prepare-for-iterating-over-endpoints, results='asis'}

insert_fig_subchunk <- function(fig, fig_chunk_name, fig_caption_short, fig_caption_long) {

  fig_deparsed <- paste0(deparse(function(){fig}), collapse = '')
  fig_sub_chunk <- paste0(
    "\n```{r fig-", fig_chunk_name, ', ', 
    "fig.scap='", fig_caption_short, "', ",
    "fig.cap='", fig_caption_long, "'}",
    "\n(", fig_deparsed, ")()", "\n```\n")
  cat(knit(text = knit_expand(text = fig_sub_chunk), quiet = TRUE))

}

fig_caption_common_text <- 'Some description of the figure content that applies to every figure, such as the color schemes/shapes/methods used'

endpoint_list <- c('Percent of IgG B-cells that are antigen-specific', 'Percent of IgG B-cells that are VRC01-class')
``

``{r iterate-over-endpoints, results='asis'}

  for (endpoint in endpoint_list) {

    cat('## ', endpoint, ' \n') # subsection title

    # main figure
    fig_caption_short <- endpoint
    fig_caption_long <- paste0(endpoint, ". ", fig_caption_common_text)
    fig <- plot_responses(endpoint) # this function defined elsewhere
    fig_chunk_name <- gsub(' ', '-', endpoint)
    insert_fig_subchunk(fig, fig_chunk_name, fig_caption_short, fig_caption_long)

    cat("\n\n\\pagebreak\n")

    # tables  
    tabulate_response_timepoint_comparisons(endpoint) # this function defined elsewhere
    tabulate_response_group_comparisons(endpoint) # this function defined elsewhere

    cat("\n\n\\pagebreak\n")

  }
``

Is this broadly applicable enough that it would be helpful to incorporate some version of this into the report template?

If so, any improvements to suggest?

kelliemac commented 1 month ago

@mayerbry we discussed this yesterday, would be great to have your thoughts.