Skip to content

Commit 3b8c33b

Browse files
committed
Feat: facet support, colour description
1 parent 91f0fad commit 3b8c33b

17 files changed

Lines changed: 253 additions & 61 deletions

.Rbuildignore

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,3 +6,5 @@
66
^docs$
77
^pkgdown$
88
^\.github$
9+
^\.positai$
10+
^\.claude$

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,3 +6,4 @@
66
.quarto
77
inst/doc
88
docs
9+
.positai

DESCRIPTION

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
Package: SuperPlotR
22
Title: Making SuperPlots in R
3-
Version: 0.1.1
3+
Version: 0.1.2
44
Authors@R:
55
person(given = "Stephen J",
66
family = "Royle",
@@ -22,10 +22,12 @@ Depends:
2222
Config/rcmdcheck/ignore-inconsequential-notes: true
2323
LazyData: true
2424
Imports:
25-
ggplot2,
25+
ColorNameR,
26+
cowplot,
2627
dplyr,
2728
ggforce,
28-
cowplot,
29+
ggplot2,
30+
patchwork,
2931
rlang
3032
URL: https://github.com/quantixed/SuperPlotR, https://quantixed.github.io/SuperPlotR/
3133
BugReports: https://github.com/quantixed/SuperPlotR/issues

NAMESPACE

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,9 +19,12 @@ import(cowplot)
1919
import(dplyr)
2020
import(ggforce)
2121
import(ggplot2)
22+
importFrom(ColorNameR,name)
23+
importFrom(grDevices,col2rgb)
2224
importFrom(grDevices,colors)
2325
importFrom(rlang,":=")
2426
importFrom(stats,TukeyHSD)
27+
importFrom(stats,as.formula)
2528
importFrom(stats,kruskal.test)
2629
importFrom(stats,median)
2730
importFrom(stats,qt)

NEWS.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,10 @@
11
# SuperPlotR
22

3+
## SuperPlotR 0.1.2
4+
* Ability to facet superplots
5+
* Added text description of colours used in information output
6+
* Documentation improvements
7+
38
## SuperPlotR 0.1.1
49

510
* Use of mean ± sd bars is now the default

R/get_sp_info.R

Lines changed: 22 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -27,18 +27,20 @@
2727
#' @import dplyr
2828
#' @importFrom stats sd median
2929
#' @importFrom rlang :=
30+
#' @importFrom ColorNameR name
31+
#' @importFrom grDevices col2rgb
3032
#'
3133
#' @returns none
3234
#' @keywords internal
3335

3436
# this function will take all the arguments sent from superplot
3537
get_sp_info <- function(df,
36-
meas, cond, repl,
38+
meas, cond, repl, facet,
3739
pal, xlab, ylab, datadist, size, alpha, bars,
3840
linking, rep_summary, shapes, fsize, gg,
3941
stats, stats_test,
4042
...) {
41-
ncond <- nrepl <- NULL
43+
ncond <- nrepl <- nfacet <- NULL
4244
rep_mean <- rep_median <- NULL
4345

4446
# args are already validated
@@ -52,13 +54,21 @@ get_sp_info <- function(df,
5254
pull(!!sym(repl)) %>%
5355
unique() %>%
5456
length()
57+
if (!is.null(facet)) {
58+
nfacet <- df %>%
59+
pull(!!sym(facet)) %>%
60+
unique() %>%
61+
length()
62+
}
5563

5664
# calculate summary statistics
5765
summary_df <- get_sp_summary(df = df,
58-
meas = meas, cond = cond, repl = repl)
66+
meas = meas, cond = cond, repl = repl, facet = facet)
5967

6068
# get colour values for the repl column
6169
sp_colours <- get_sp_colours(nrepl, pal)
70+
sp_colours_words <- ColorNameR::name(t(col2rgb(sp_colours)) / 255,
71+
colorspace = "sRGB")
6272
sp_shapes <- get_sp_shapes(nrepl, shapes)
6373

6474
# add repl from summary_df to sp_colour and sp_shapes
@@ -84,6 +94,9 @@ get_sp_info <- function(df,
8494
message("Number of replicates: ", nrepl)
8595
message("Number of data points: ", nrow(df))
8696
message("Number of summary points: ", nrow(summary_df))
97+
if( !is.null(facet)) {
98+
message("Number of facets: ", nfacet)
99+
}
87100
message("=====================")
88101
message("Colour palette: ", pal)
89102
message("Data distribution: ", datadist)
@@ -112,8 +125,12 @@ get_sp_info <- function(df,
112125
message("No statistics")
113126
}
114127
message("=====================")
115-
message("Colours for replicates: ", paste(sp_colours, collapse = ", "))
116-
message("Shapes for replicates: ", paste(sp_shapes, collapse = ", "))
128+
message("Colours for replicates: ",
129+
paste(sp_colours, collapse = ", "))
130+
message("Colour names for replicates: ",
131+
paste(sp_colours_words, collapse = ", "))
132+
message("Shapes for replicates: ",
133+
paste(sp_shapes, collapse = ", "))
117134

118135
if (nrow(summary_df) != ncond * nrepl) {
119136
s_summary_df <- summary_df %>%

R/get_sp_summary.R

Lines changed: 24 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -9,12 +9,14 @@
99
#' get the correct data frame to work with.
1010
#'
1111
#' @param df A data frame containing the experimental data
12-
#' @param meas Character string specifying the name of the column containing
13-
#' the measurements/values to summarize (e.g., "intensity", "speed")
14-
#' @param cond Character string specifying the name of the column containing
15-
#' the experimental conditions (e.g., "Treatment", "Genotype")
16-
#' @param repl Character string specifying the name of the column containing
17-
#' the replicate identifiers (e.g., "Replicate", "Experiment")
12+
#' @param meas Character string specifying the name of the column containing the
13+
#' measurements/values to summarize (e.g., "intensity", "speed")
14+
#' @param cond Character string specifying the name of the column containing the
15+
#' experimental conditions (e.g., "Treatment", "Genotype")
16+
#' @param repl Character string specifying the name of the column containing the
17+
#' replicate identifiers (e.g., "Replicate", "Experiment")
18+
#' @param facet Character string specifying the name of the column to facet by
19+
#' (e.g. further grouping variable, default is NULL)
1820
#' @param ... Additional arguments (ignored)
1921
#'
2022
#' @return A data frame with columns for condition, replicate, rep_mean
@@ -29,7 +31,7 @@
2931
#' # Using the built-in dataset
3032
#' get_sp_summary(lord_jcb, "Speed", "Treatment", "Replicate")
3133
#'
32-
get_sp_summary <- function(df, meas, cond, repl, ...) {
34+
get_sp_summary <- function(df, meas, cond, repl, facet = NULL, ...) {
3335
# Validate inputs
3436
if (!is.data.frame(df)) {
3537
stop("df must be a data frame")
@@ -47,14 +49,28 @@ get_sp_summary <- function(df, meas, cond, repl, ...) {
4749
stop("repl column '", repl, "' not found in data frame")
4850
}
4951

52+
if (!is.null(facet) && !facet %in% names(df)) {
53+
stop("facet column '", facet, "' not found in data frame")
54+
}
55+
5056
# Calculate summary statistics grouped by condition and replicate
57+
if (is.null(facet)) {
58+
sdf <- df %>%
59+
group_by(!!sym(cond), !!sym(repl)) %>%
60+
summarise(
61+
rep_mean = mean(!!sym(meas), na.rm = TRUE),
62+
rep_median = median(!!sym(meas), na.rm = TRUE),
63+
.groups = "drop"
64+
)
65+
} else {
5166
sdf <- df %>%
52-
group_by(!!sym(cond), !!sym(repl)) %>%
67+
group_by(!!sym(cond), !!sym(repl), !!sym(facet)) %>%
5368
summarise(
5469
rep_mean = mean(!!sym(meas), na.rm = TRUE),
5570
rep_median = median(!!sym(meas), na.rm = TRUE),
5671
.groups = "drop"
5772
)
73+
}
5874

5975
return(sdf)
6076
}

R/superplot.R

Lines changed: 39 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88
#' @param cond character name of column with condition (e.g. Control, WT)
99
#' @param repl character name of column with replicate (e.g. unique experiment
1010
#' identifiers)
11+
#' @param facet character name of column to facet by (default is NULL)
1112
#' @param pal name of colour palette to use (default is "tol_bright")
1213
#' @param xlab string for x label (default is empty)
1314
#' @param ylab string for y label (default is "Measurement")
@@ -38,7 +39,7 @@
3839
#' @import dplyr
3940
#' @import ggforce
4041
#' @import cowplot
41-
#' @importFrom stats sd median
42+
#' @importFrom stats sd median as.formula
4243
#'
4344
#' @export
4445
#'
@@ -49,6 +50,7 @@
4950
#'
5051
superplot <- function(df,
5152
meas, cond, repl,
53+
facet = NULL,
5254
pal = "tol_bright",
5355
xlab = "", ylab = "Measurement",
5456
datadist = "sina",
@@ -73,7 +75,7 @@ superplot <- function(df,
7375
gg = gg, stats = stats, stats_test = stats_test, info = info)
7476

7577
# verify that the data frame to make sure that it is suitable for SuperPlot
76-
if (verify_sp_columns(df, meas, cond, repl) == FALSE) {
78+
if (verify_sp_columns(df, meas, cond, repl, facet) == FALSE) {
7779
return(NULL)
7880
}
7981

@@ -89,6 +91,13 @@ superplot <- function(df,
8991
df[[repl]] <- as.character(df[[repl]])
9092
}
9193

94+
# if facet is not NULL, check that it is character and convert to factor if not already
95+
if (!is.null(facet)) {
96+
if (!is.character(df[[facet]]) && !is.factor(df[[facet]])) {
97+
df[[facet]] <- as.character(df[[facet]])
98+
}
99+
}
100+
92101
# how many unique values in cond and repl?
93102
ncond <- df %>%
94103
pull(!!sym(cond)) %>%
@@ -98,17 +107,32 @@ superplot <- function(df,
98107
pull(!!sym(repl)) %>%
99108
unique() %>%
100109
length()
110+
if (!is.null(facet)) {
111+
nfacet <- df %>%
112+
pull(!!sym(facet)) %>%
113+
unique() %>%
114+
length()
115+
}
101116

102117
# calculate summary statistics
103118
summary_df <- get_sp_summary(df = df,
104-
meas = meas, cond = cond, repl = repl)
119+
meas = meas, cond = cond, repl = repl,
120+
facet = facet)
105121

106122
# generate a warning if NROW of summary_df doesn't equal the product of
107123
# unique values in cond and repl
108-
if (nrow(summary_df) != ncond * nrepl && info == FALSE) {
109-
warning("Summary statistics were not calculated for all combinations of
124+
if (!is.null(facet)) {
125+
if (nrow(summary_df) != ncond * nrepl * nfacet & info == FALSE) {
126+
warning("Summary statistics were not calculated for all combinations of
127+
condition, replicate, and facet.\nCheck for missing data.\n
128+
Call again with `info = TRUE` to see more details.")
129+
}
130+
} else {
131+
if (nrow(summary_df) != ncond * nrepl & info == FALSE) {
132+
warning("Summary statistics were not calculated for all combinations of
110133
condition and replicate.\nCheck for missing data.\n
111134
Call again with `info = TRUE` to see more details.")
135+
}
112136
}
113137
# get colour values for the repl column
114138
sp_colours <- get_sp_colours(nrepl, pal)
@@ -117,7 +141,7 @@ superplot <- function(df,
117141
# if info is TRUE, print information about the plot
118142
if (info == TRUE) {
119143
get_sp_info(df = df,
120-
meas = meas, cond = cond, repl = repl,
144+
meas = meas, cond = cond, repl = repl, facet = facet,
121145
pal = pal, xlab = xlab, ylab = ylab,
122146
datadist = datadist, size = size, alpha = alpha,
123147
bars = bars, linking = linking,
@@ -193,6 +217,10 @@ superplot <- function(df,
193217
} else {
194218
# plot is scaled automatically
195219
}
220+
# facet if requested
221+
if (!is.null(facet)) {
222+
p <- p + facet_wrap(as.formula(paste("~", facet)))
223+
}
196224
# theme
197225
p <- p + theme_cowplot(fsize)
198226
# info is FALSE hide legend
@@ -203,7 +231,11 @@ superplot <- function(df,
203231

204232
# add stats if requested
205233
if (stats == TRUE) {
206-
get_sp_stats(as.data.frame(summary_df), rep_summary, cond, repl, ncond, nrepl, stats_test)
234+
if (!is.null(facet)) {
235+
warning("Statistical tests are not currently implemented for faceted SuperPlots.")
236+
} else {
237+
get_sp_stats(as.data.frame(summary_df), rep_summary, cond, repl, ncond, nrepl, stats_test)
238+
}
207239
}
208240

209241
return(p)

R/verify.R

Lines changed: 26 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,21 +4,33 @@
44
#' @param meas character name of column with measurement (e.g. intensity)
55
#' @param cond character name of column with condition (e.g. Control, WT)
66
#' @param repl character name of column with replicate (e.g. unique experiment
7-
#' identifiers)
7+
#' identifiers)
8+
#' @param facet character name of column to facet by (e.g. further grouping
9+
#' variable, default is NULL)
810
#'
911
#' @return logical to allow plot to go ahead
1012
#' @keywords internal
11-
verify_sp_columns <- function(df, meas, cond, repl) {
13+
verify_sp_columns <- function(df, meas, cond, repl, facet = NULL) {
1214
# check that meas, cond and repl are character
1315
if (!is.character(meas) | !is.character(cond) | !is.character(repl)) {
1416
message("meas, cond and repl must be character")
1517
return(FALSE)
1618
}
19+
# check that facet is character or NULL
20+
if (!is.null(facet) & !is.character(facet)) {
21+
message("facet must be character or NULL")
22+
return(FALSE)
23+
}
1724
# verify the data frame - check if the required columns are present
1825
if (!cond %in% colnames(df) | !repl %in% colnames(df) | !meas %in% colnames(df)) {
1926
message("The data frame does not contain the required columns")
2027
return(FALSE)
2128
}
29+
# if facet was not NULL, check that the facet column is present
30+
if (!is.null(facet) && !facet %in% colnames(df)) {
31+
message("The data frame does not contain the facet column")
32+
return(FALSE)
33+
}
2234
# check that column meas is numeric
2335
if (!is.numeric(df[[meas]])) {
2436
message("The column ", meas, " is not numeric")
@@ -53,3 +65,15 @@ verify_fp_columns <- function(df, meas, cond) {
5365
}
5466
return(TRUE)
5567
}
68+
69+
70+
#' Ignore unused imports
71+
#'
72+
#' Currently patchwork is used in the documentation but not in the package
73+
#' itself. This function is a workaround to avoid warnings about unused imports
74+
#' when building the package.
75+
#'
76+
#' @keywords keyword
77+
ignore_unused_imports <- function() {
78+
patchwork::wrap_plots
79+
}

_pkgdown.yml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ articles:
1010
contents:
1111
- SuperPlotR
1212
- advanced
13+
- facets
1314
- limitations
1415
- flatplot
1516
- pieplot

0 commit comments

Comments
 (0)