I am trying to do a chart like this one:
The idea is to plot 3 amounts, in this mixed stacked bar chart we have a dataframe which has one row for a negative value and two rows for the positive value, however i need to stack the negative with the first positive bar, i also need 3 colors. The code I have so far is as follows: (the dataframe already has the desired shape):
df3 <- read.table(
text =
"region group metric somevalue
blue T1 epsilon 63
blue T2 epsilon -40
red T1 epsilon 100
blue T1 kappa 19
blue T2 kappa -30
red T1 kappa 75
blue T1 zulu 50
blue T2 zulu -18
red T1 zulu 68", header=TRUE)
p2 <- ggplot(df3, aes(x = metric, y = somevalue, fill=region))+
geom_col(aes(fill = group), width = 0.7) + geom_bar(position = 'dodge', stat='identity')
p2
please help me out, if you think the dataframe has to be modified please let me know. thanks
Stacking and dodging is always a bit tricky. In your case this could be achieved like so:
region
to a factor
. (This makes sure that step 3 works) position="dodge"
. I added na.rm = TRUE
to remove the missing values we added via complete
.
library(ggplot2)
library(dplyr)
library(tidyr)
df3$region <- factor(df3$region)
df3_neg <- filter(df3, somevalue < 0) %>%
tidyr::complete(region, group, metric)
df3_pos<- filter(df3, somevalue > 0) %>%
tidyr::complete(region, group, metric)
p2 <- ggplot(df3, aes(somevalue, metric)) +
geom_col(aes(alpha = group, fill=region), data = df3_pos, position = "dodge", na.rm = TRUE) +
geom_col(aes(alpha = group, fill=region), data = df3_neg, position = "dodge", na.rm = TRUE) +
scale_fill_identity() +
scale_alpha_manual(values = c(T2 = .6, T1 = 1)) +
guides(alpha = FALSE)
p2
EDIT Adding annotations could be achieved the same way, eg my code below uses two geom_text
to add the values next to the bar where I make use of position_dodge2(.9)
so that the labels align nicely with the bars:
p2 <- ggplot(df3, aes(somevalue, metric)) +
geom_col(aes(alpha = group, fill=region), data = df3_pos, position = "dodge", na.rm = TRUE) +
geom_col(aes(alpha = group, fill=region), data = df3_neg, position = "dodge", na.rm = TRUE) +
geom_text(aes(x = somevalue + 1, label = somevalue), data = df3_pos, position = position_dodge2(width = .9), hjust = 0, na.rm = TRUE) +
geom_text(aes(x = somevalue - 1, label = somevalue), data = df3_neg, , position = position_dodge2(width = .9), hjust = 1, na.rm = TRUE) +
scale_fill_identity() +
scale_alpha_manual(values = c(T2 = .6, T1 = 1)) +
guides(alpha = FALSE)
p2
EDIT2 Adding a table is indeed a different thing. In that case I would go for patchwork
which means making plots to mimic the table layout. To make the dodging work or to make sure that the table rows align with the bars you have make a plot for each table column. The basic approach may look like so:
library(patchwork)
# 1. Make a dataframe with all combinations of region and metric using expand_grid
d_table <- expand_grid(region = unique(df3$region), metric = unique(df3$metric))
# 2. Add columns with the table content
d_table$column1 <- LETTERS[1:6]
d_table$column2 <- letters[1:6]
# 3. Make a plot for each column of the table
p_column1 <- ggplot(d_table, aes(y = metric, x = 1, label = column1)) +
geom_text(aes(group = region), position = position_dodge2(width = .9), na.rm = TRUE) +
scale_x_continuous(position = "top", breaks = 1, labels = "column1") +
labs(y = NULL, x = "") +
theme(axis.text.y = element_blank(),
axis.text.x.bottom = element_blank(),
axis.ticks = element_blank(),
plot.margin = unit(rep(0, 4), "pt"),
panel.background = element_rect(fill = NA))
p_column2 <- ggplot(d_table, aes(y = metric, x = 1, label = column2)) +
geom_text(aes(group = region), position = position_dodge2(width = .9), na.rm = TRUE) +
scale_x_continuous(position = "top", breaks = 1, labels = "column2") +
labs(y = NULL, x = "") +
theme(axis.text.y = element_blank(),
axis.text.x.bottom = element_blank(),
axis.ticks = element_blank(),
plot.margin = unit(rep(0, 4), "pt"),
panel.background = element_rect(fill = NA))
# 4. Add the table columns via patchwork
p2 + p_column1 + p_column2 + plot_layout(widths = c(1, .1, .1))
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.