Skip to content

Commit b416a04

Browse files
committed
feat: further improvements for styling gene arrows showteeth#38
1 parent 859139c commit b416a04

File tree

6 files changed

+267
-118
lines changed

6 files changed

+267
-118
lines changed

R/geom_gene.R

Lines changed: 50 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -1,46 +1,50 @@
11
#' Add Gene Annotation to Coverage Plot.
22
#'
3-
#' @param gtf.gr Granges object of GTF, created with \code{\link{import.gff}}. Default: NULL.
3+
#' @param gtf.gr Granges object of GTF, created with \code{\link{import.gff}}.
4+
#' Default: NULL.
45
#' @param overlap.gene.gap The gap between gene groups. Default: 0.1.
5-
#' @param overlap.style The style of gene groups, choose from loose (each gene occupies single line)
6-
#' and tight (place non-overlap genes in one line). Default: loose.
7-
#' @param gene.size The line width of genes. Default: 1.
8-
#' @param utr.size The line width of UTRs. Default: 2.
9-
#' @param exon.size The line width of exons. Default: 3.
6+
#' @param overlap.style The style of gene groups, choose from loose (each gene
7+
#' occupies single line) and tight (place non-overlap genes in one line).
8+
#' Default: loose.
9+
#' @param gene.size Line width of genes. Default: 1.
10+
#' @param utr.size Line width of UTRs. Default: 2.
11+
#' @param exon.size Line width of exons. Default: 3.
1012
#' @param arrow.angle Angle of the arrow head. Default 35°
1113
#' @param arrow.length Length of arrows. Default: 1.5
1214
#' @param arrow.type Whether to draw "closed" or "open" (default) arrow heads
13-
14-
#' @param
15+
#' @param color.by Color the lines/arrows by variable. Default: "strand".
1516
#' @param arrow.gap The gap distance between intermittent arrows. Default: NULL.
1617
#' Set arrow.num and arrow.gap to NULL to suppress intermittent arrows.
17-
#' @param arrow.num Total number of intermittent arrows over whole region. Default: 50.
18-
#' Set arrow.num and arrow.gap to NULL to suppress intermittent arrows.
19-
#' @param color.by Color the line by. Default: strand.
18+
#' @param arrow.num Total number of intermittent arrows over whole region.
19+
#' Default: 50. Set arrow.num and arrow.gap to NULL to suppress intermittent
20+
#' arrows.
21+
#' @param arrow.size.im Line width of intermittent arrows. Default: 0.5
22+
#' @param arrow.length.im Length of intermittent arrows. Default: 1.5
23+
#' @param arrow.type.im Whether to draw "closed" (default) or "open" heads for
24+
#' intermittent arrows
25+
#' @param color.by.im Color the intermittent arrows by variable. Default: NULL
26+
#' (draws semi-transparent, white arrows)
2027
#' @param fill.color Color used for \code{color.by}.
21-
#' Default: blue for - (minus strand), green for + (plus strand).
28+
#' Default: blue for - (minus strand), green for + (plus strand).
2229
#' @param show.utr Logical value, whether to show UTR. Default: TRUE.
2330
#' @param label.size The size of gene label. Default: 3.
2431
#' @param label.vjust The vjust of gene label. Default: 2.
2532
#' @param plot.space Top and bottom margin. Default: 0.1.
26-
#' @param plot.height The relative height of gene annotation to coverage plot. Default: 0.2.
33+
#' @param plot.height The relative height of gene annotation to coverage plot.
34+
#' Default: 0.2.
2735
#'
28-
29-
arrow.gap = NULL,
30-
arrow.num = 50,
31-
arrow.size.im = 0.5,
32-
arrow.length.im = 1.5,
33-
arrow.type.im = "closed",
34-
color.by.im = NULL,
3536
#' @return Plot.
3637
#' @importFrom dplyr %>%
3738
#' @importFrom rlang .data
3839
#' @importFrom GenomicRanges GRanges makeGRangesFromDataFrame setdiff
3940
#' @importFrom IRanges IRanges subsetByOverlaps findOverlaps
4041
#' @importFrom dplyr filter select arrange
41-
#' @importFrom ggplot2 ggplot_add ggplot geom_segment aes_string arrow unit geom_text labs theme_classic theme element_blank
42-
#' element_text element_rect margin scale_y_continuous scale_color_manual scale_x_continuous coord_cartesian
42+
#' @importFrom ggplot2 ggplot_add ggplot geom_segment aes_string arrow unit
43+
#' geom_text labs theme_classic theme element_blank element_text element_rect
44+
#' margin scale_y_continuous scale_color_manual scale_x_continuous
45+
#' coord_cartesian
4346
#' @importFrom patchwork wrap_plots
47+
#' @importFrom grDevices grey
4448
#' @export
4549
#'
4650
#' @examples
@@ -69,8 +73,8 @@ color.by.im = NULL,
6973
#' gtf_gr <- rtracklayer::import.gff(con = gtf_file, format = "gtf")
7074
#'
7175
#' # plot coverage and gene annotation
72-
#' basic.coverage <- ggcoverage(data = track_df, range.position = "out")
73-
#' basic.coverage +
76+
#' basic_coverage <- ggcoverage(data = track_df, range.position = "out")
77+
#' basic_coverage +
7478
#' geom_gene(gtf.gr = gtf_gr)
7579
#'
7680
#'# plot with custom style
@@ -159,9 +163,28 @@ ggplot_add.gene <- function(object, plot, object_name) {
159163
ranges = IRanges::IRanges(plot.range.start, plot.range.end)
160164
)
161165
# get parameters
162-
for (ob in names(object)) {
163-
assign(x = ob, value = object[[ob]])
164-
}
166+
gtf.gr <- object$gtf.gr
167+
overlap.gene.gap <- object$overlap.gene.gap
168+
overlap.style <- object$overlap.style
169+
gene.size <- object$gene.size
170+
utr.size <- object$utr.size
171+
exon.size <- object$exon.size
172+
arrow.angle <- object$arrow.angle
173+
arrow.length <- object$arrow.length
174+
arrow.type <- object$arrow.type
175+
color.by <- object$color.by
176+
arrow.gap <- object$arrow.gap
177+
arrow.num <- object$arrow.num
178+
arrow.size.im <- object$arrow.size.im
179+
arrow.length.im <- object$arrow.length.im
180+
arrow.type.im <- object$arrow.type.im
181+
color.by.im <- object$color.by.im
182+
fill.color <- object$fill.color
183+
show.utr <- object$show.utr
184+
label.size <- object$label.size
185+
label.vjust <- object$label.vjust
186+
plot.space <- object$plot.space
187+
plot.height <- object$plot.height
165188

166189
# get gene in region
167190
gtf.df.used <- IRanges::subsetByOverlaps(x = gtf.gr, ranges = plot.range.gr) %>% as.data.frame()

R/geom_transcript.R

Lines changed: 104 additions & 47 deletions
Original file line numberDiff line numberDiff line change
@@ -1,25 +1,37 @@
11
#' Add Transcript Annotation to Coverage Plot.
22
#'
3-
#' @param gtf.gr Granges object of GTF, created with \code{\link{import.gff}}. Default: NULL.
3+
#' @param gtf.gr Granges object of GTF, created with \code{\link{import.gff}}.
4+
#' Default: NULL.
45
#' @param gene.name Gene name of all transcripts. Default: HNRNPC.
56
#' @param overlap.tx.gap The gap between transcript groups. Default: 0.1.
6-
#' @param overlap.style The style of transcript groups, choose from loose (each transcript occupies single line)
7-
#' and tight (place non-overlap transcripts in one line). Default: loose.
8-
#' @param tx.size The line size of transcript. Default: 1.
9-
#' @param utr.size The line size of UTR. Default: 2.
10-
#' @param exon.size The line size of exon. Default: 3.
11-
#' @param arrow.size The line size of arrow. Default: 1.5.
7+
#' @param overlap.style The style of transcript groups, choose from loose (each
8+
#' transcript occupies single line) and tight (place non-overlap transcripts
9+
#' in one line). Default: loose.
10+
#' @param tx.size Line size of transcript. Default: 1.
11+
#' @param utr.size Line size of UTR. Default: 2.
12+
#' @param exon.size Line size of exon. Default: 3.
13+
#' @param arrow.angle Angle of the arrow head. Default 35°
14+
#' @param arrow.length Length of arrows. Default: 1.5
15+
#' @param arrow.type Whether to draw "closed" or "open" (default) arrow heads
16+
#' @param color.by Color the line by. Default: strand.
1217
#' @param arrow.gap The gap distance between intermittent arrows. Default: NULL.
1318
#' Set arrow.num and arrow.gap to NULL to suppress intermittent arrows.
14-
#' @param arrow.num Total number of intermittent arrows over whole region. Default: 50.
15-
#' Set arrow.num and arrow.gap to NULL to suppress intermittent arrows.
16-
#' @param color.by Color the line by. Default: strand.
17-
#' @param fill.color Color used for \code{color.by}.
18-
#' Default: blue for - (minus strand), green for + (plus strand).
19+
#' @param arrow.num Total number of intermittent arrows over whole region.
20+
#' Default: 50. Set arrow.num and arrow.gap to NULL to suppress intermittent
21+
#' arrows.
22+
#' @param arrow.size.im Line width of intermittent arrows. Default: 0.5
23+
#' @param arrow.length.im Length of intermittent arrows. Default: 1.5
24+
#' @param arrow.type.im Whether to draw "closed" (default) or "open" heads for
25+
#' intermittent arrows
26+
#' @param color.by.im Color the intermittent arrows by variable. Default: NULL
27+
#' (draws semi-transparent, white arrows)
28+
#' @param fill.color Color used for \code{color.by}. Default: blue for - (minus
29+
#' strand), green for + (plus strand).
1930
#' @param label.size The size of transcript label. Default: 3.
2031
#' @param label.vjust The vjust of transcript label. Default: 2.
2132
#' @param plot.space Top and bottom margin. Default: 0.1.
22-
#' @param plot.height The relative height of transcript annotation to coverage plot. Default: 0.2.
33+
#' @param plot.height The relative height of transcript annotation to coverage
34+
#' plot. Default: 0.2.
2335
#'
2436
#' @return Plot.
2537
#' @importFrom dplyr %>%
@@ -30,6 +42,7 @@
3042
#' @importFrom ggplot2 ggplot_add ggplot geom_segment aes_string arrow unit geom_text labs theme_classic theme element_blank
3143
#' element_text element_rect margin scale_y_continuous scale_color_manual scale_x_continuous coord_cartesian
3244
#' @importFrom patchwork wrap_plots
45+
#' @importFrom grDevices grey
3346
#' @export
3447
#'
3548
#' @examples
@@ -58,9 +71,24 @@
5871
#' gtf_gr <- rtracklayer::import.gff(con = gtf_file, format = "gtf")
5972
#'
6073
#' # plot coverage and gene annotation
61-
#' basic.coverage <- ggcoverage(data = track_df, range.position = "out")
62-
#' basic.coverage +
74+
#' basic_coverage <- ggcoverage(data = track_df, range.position = "out")
75+
#' basic_coverage +
6376
#' geom_transcript(gtf.gr = gtf_gr, label.vjust = 1.5)
77+
#'
78+
#' # plot with custom style
79+
#' basic_coverage +
80+
#' geom_transcript(
81+
#' gtf.gr = gtf_gr,
82+
#' exon.size = 2.0,
83+
#' arrow.size.im = 1.0,
84+
#' arrow.length.im = 5,
85+
#' arrow.type.im = "open",
86+
#' color.by.im = "strand",
87+
#' fill.color = c(
88+
#' "-" = "darkblue",
89+
#' "+" = "darkgreen"
90+
#' )
91+
#' )
6492
geom_transcript <-
6593
function(gtf.gr,
6694
gene.name = "HNRNPC",
@@ -69,10 +97,16 @@ geom_transcript <-
6997
tx.size = 1,
7098
utr.size = 2,
7199
exon.size = 3,
72-
arrow.size = 3,
100+
arrow.angle = 35,
101+
arrow.length = 1.5,
102+
arrow.type = "open",
103+
color.by = "strand",
73104
arrow.gap = NULL,
74105
arrow.num = 50,
75-
color.by = "strand",
106+
arrow.size.im = 0.5,
107+
arrow.length.im = 1.5,
108+
arrow.type.im = "closed",
109+
color.by.im = NULL,
76110
fill.color = c(
77111
"-" = "cornflowerblue",
78112
"+" = "darkolivegreen3"
@@ -81,33 +115,37 @@ geom_transcript <-
81115
label.vjust = 2,
82116
plot.space = 0.1,
83117
plot.height = 1) {
84-
structure(
85-
list(
86-
gtf.gr = gtf.gr,
87-
gene.name = gene.name,
88-
overlap.tx.gap = overlap.tx.gap,
89-
overlap.style = overlap.style,
90-
tx.size = tx.size,
91-
utr.size = utr.size,
92-
exon.size = exon.size,
93-
arrow.size = arrow.size,
94-
arrow.gap = arrow.gap,
95-
arrow.num = arrow.num,
96-
color.by = color.by,
97-
fill.color = fill.color,
98-
label.size = label.size,
99-
label.vjust = label.vjust,
100-
plot.space = plot.space,
101-
plot.height = plot.height
102-
),
103-
class = "transcript"
104-
)
105-
}
118+
structure(
119+
list(
120+
gtf.gr = gtf.gr,
121+
gene.name = gene.name,
122+
overlap.tx.gap = overlap.tx.gap,
123+
overlap.style = overlap.style,
124+
tx.size = tx.size,
125+
utr.size = utr.size,
126+
exon.size = exon.size,
127+
arrow.angle = arrow.angle,
128+
arrow.length = arrow.length,
129+
arrow.type = arrow.type,
130+
color.by = color.by,
131+
arrow.gap = arrow.gap,
132+
arrow.num = arrow.num,
133+
arrow.size.im = arrow.size.im,
134+
arrow.length.im = arrow.length.im,
135+
arrow.type.im = arrow.type.im,
136+
color.by.im = color.by.im,
137+
fill.color = fill.color,
138+
label.size = label.size,
139+
label.vjust = label.vjust,
140+
plot.space = plot.space,
141+
plot.height = plot.height
142+
),
143+
class = "transcript"
144+
)
145+
}
106146

107147
#' @export
108148
ggplot_add.transcript <- function(object, plot, object_name) {
109-
# get plot data
110-
# track.data <- plot$layers[[1]]$data
111149
# get plot data, plot data should contain bins
112150
if ("patchwork" %in% class(plot)) {
113151
track.data <- plot[[1]]$layers[[1]]$data
@@ -135,11 +173,17 @@ ggplot_add.transcript <- function(object, plot, object_name) {
135173
tx.size <- object$tx.size
136174
utr.size <- object$utr.size
137175
exon.size <- object$exon.size
138-
arrow.size <- object$arrow.size
176+
arrow.angle <- object$arrow.angle
177+
arrow.length <- object$arrow.length
178+
arrow.type <- object$arrow.type
139179
color.by <- object$color.by
140-
fill.color <- object$fill.color
141180
arrow.gap <- object$arrow.gap
142181
arrow.num <- object$arrow.num
182+
arrow.size.im <- object$arrow.size.im
183+
arrow.length.im <- object$arrow.length.im
184+
arrow.type.im <- object$arrow.type.im
185+
color.by.im <- object$color.by.im
186+
fill.color <- object$fill.color
143187
label.size <- object$label.size
144188
label.vjust <- object$label.vjust
145189
plot.space <- object$plot.space
@@ -202,17 +246,17 @@ ggplot_add.transcript <- function(object, plot, object_name) {
202246

203247
# create basic plot
204248
tx.plot <- ggplot() +
205-
geom_arrows(gene.tx.df.tx, color.by, tx.size, arrow.size)
249+
geom_arrows(gene.tx.df.tx, color.by, tx.size, arrow.length, arrow.angle, arrow.type)
206250

207251
# deal with missing UTR
208252
if (is.null(gene.tx.df.utr)) {
209253
warning("No UTR detected in provided GTF!")
210254
} else {
211255
tx.plot <- tx.plot +
212-
geom_arrows(gene.tx.df.utr, color.by, utr.size, arrow.size)
256+
geom_arrows(gene.tx.df.utr, color.by, utr.size, arrow.length, arrow.angle, arrow.type)
213257
}
214258
tx.plot <- tx.plot +
215-
geom_arrows(gene.tx.df.exon, color.by, exon.size, arrow.size) +
259+
geom_arrows(gene.tx.df.exon, color.by, exon.size, arrow.length, arrow.angle, arrow.type) +
216260
theme_classic()
217261

218262
if (is.null(arrow.gap)) {
@@ -258,9 +302,22 @@ ggplot_add.transcript <- function(object, plot, object_name) {
258302
arrow.df$start <- as.numeric(arrow.df$start)
259303
arrow.df$end <- as.numeric(arrow.df$end)
260304
arrow.df$group <- as.numeric(arrow.df$group)
305+
if (is.null(color.by.im)) {
306+
color.by.im <- color.by
307+
arrow.df[[color.by]] <- "im"
308+
fill.color["im"] <- grDevices::grey(1, alpha = 0.5)
309+
} else if (color.by.im %in% colnames(arrow.df)) {
310+
stopifnot(unique(arrow.df[[color.by.im]]) %in% names(fill.color))
311+
} else {
312+
stop(paste0(
313+
"The selected variable '",
314+
color.by.im ,
315+
"' for 'color.by.im' is not available in the data"
316+
))
317+
}
261318
# add arrow
262319
tx.arrow.plot <- tx.plot +
263-
geom_arrows(arrow.df, color.by, tx.size / 2, arrow.size, 35, TRUE)
320+
geom_arrows(arrow.df, color.by.im, arrow.size.im, arrow.length.im, arrow.angle, arrow.type.im)
264321

265322
# prepare label dataframe
266323
label.df <- data.frame(

R/utils.R

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -357,7 +357,6 @@ GetPlotData <- function(plot, layer.num = 1) {
357357
#' @param arrow_size size of the arrow
358358
#' @param arrow_angle angle of the arrow in degrees
359359
#' @param arrow_type type of arrow, either 'open' or 'closed'
360-
#' @importFrom grDevices grey
361360
#' @return A geom layer for ggplot2 objects.
362361
#' @export
363362
geom_arrows <-

man/geom_arrows.Rd

Lines changed: 3 additions & 11 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)