How can I add a legend to this graph in R - r

I have made a graph from 2 different tables, red is users and blue is non users. How can I create a legend.
structure(list(Attribute = c("Nscore", "Escore", "Oscore", "Ascore",
"Cscore", "Impulsivity", "SS"), Mean = c(0.519519745762712, -0.224147033898305,
0.345051694915254, -0.542761016949153, -0.432290169491526, 0.573723898305084,
0.625454406779661), lower_bound = c(0.345515567755788, -0.421929253136834,
0.173007836159723, -0.743825778750619, -0.620318735695037, 0.417301607369938,
0.461852381381636), upper_bound = c(0.693523923769636, -0.0263648146597761,
0.517095553670785, -0.341696255147686, -0.244261603288014, 0.730146189240231,
0.789056432177685)), class = c("tbl_df", "tbl", "data.frame"), row.names = c(NA,
-7L))
structure(list(Attribute = c("Nscore", "Escore", "Oscore", "Ascore",
"Cscore", "Impulsivity", "SS"), Mean = c(-0.0346437351443125,
0.014794833050368, -0.0236125863044712, 0.0359841765704582, 0.0284564233163561,
-0.0306152461799648, -0.0452792359932086), lower_bound = c(-0.0809079532901976,
-0.0313902162687121, -0.0700665170072849, -0.00972637107557454,
-0.0176800056429342, -0.0748829267378616, -0.089769617527101),
upper_bound = c(0.0116204830015727, 0.0609798823694481, 0.0228413443983426,
0.0816947242164909, 0.0745928522756465, 0.0136524343779321,
-0.000788854459316299)), class = c("tbl_df", "tbl", "data.frame"
), row.names = c(NA, -7L))
ggplot(UserCI, aes(Attribute, Mean)) +
geom_point() + geom_errorbar(aes(ymin = lower_bound, ymax = upper_bound), colour="red") +
geom_point(data = NonUserCI, aes(Attribute, Mean)) +
geom_errorbar(aes(ymin =NonUserCI$lower_bound, ymax = NonUserCI$upper_bound), colour = "blue")

If you want to get a legend then map on aesthetics, i.e. map on the color aes inside aes() and set your desired colors via scale_color_manual:
library(ggplot2)
ggplot(UserCI, aes(Attribute, Mean)) +
geom_point() +
geom_errorbar(aes(ymin = lower_bound, ymax = upper_bound, color = "user")) +
geom_point(data = NonUserCI, aes(Attribute, Mean)) +
geom_errorbar(data = NonUserCI, aes(ymin = lower_bound, ymax = upper_bound, color = "nonuser")) +
scale_color_manual(
values = c("user" = "red", "nonuser" = "blue"),
labels = c("user" = "User", "nonuser" = "Non-User")
)

Related

wrapping the labels of legend in ggplot ZINB model

I need help in wrapping the labels of legend in ggplot. I tried various option including
str_wrap(model, width=20)
scale_colour_discrete(labels = function(x) str_wrap(x, width = 5))
guides(colour = guide_legend(nrow = 2))
but without any success
library(ggplot2)
ggplot(coefs, aes(x = estimate, y = term, colour = model)) +
geom_vline(xintercept = 1, lty = 1, color = "yellow", size = 1) +
geom_pointrange(aes(xmin = conf.low, xmax = conf.high),
position = position_dodge(width = 0.5)
) +
facet_wrap(~type, scale = "free") +
geom_text(aes(x = estimate, label = sprintf("%0.2f", estimate)), position = position_dodge(0.5), vjust = -0.5) +
labs(x = "gy", y = "age") +
scale_color_manual(
name = "Model",
labels = c("Fullfasdfasdfad-asdkljaflsdjfals;jfasdf", "Subadfasdfaasdfasdfasdfsdfasdfasf"),
values = c("dodgerblue4", "firebrick4")
)
Data
coefs <- structure(list(model = c(
"all_adj", "all_adj", "all_adj", "all_adj",
"adj_sub", "adj_sub"
), term = c(
"ageb", "agec", "ageb", "agec",
"ageb", "ageb"
), type = c(
"count", "count", "zero", "zero", "count",
"zero"
), estimate = c(
0.937781183281121, 1.09774595782208, 0.895560088459192,
0.891707940838411, 0.76445315191301, 1.01406754426526
), conf.low = c(
0.422176961883128,
0.319479297647212, 0.273199977915238, 0.132809852827134, 0.175087960312586,
0.186498610242251
), conf.high = c(
2.08309222699744, 3.77190696483063,
2.93568058885374, 5.98707878088866, 3.33768592898348, 5.51389087026671
)), row.names = c(NA, -6L), class = c("tbl_df", "tbl", "data.frame"))

ggplot piechart label freq instead of percent?

Hi supposed I have the following pie info.
df=structure(list(Var1 = c("a", "b"), Freq = c(306L, 1064L), per = c(0.223357664233577,
0.776642335766423)), row.names = c(NA, -2L), class = "data.frame")
and I plot this pie chart with direction -1
ggplot(data = df,
aes(x = "", y = per, fill = Var1)) +
geom_col() +
geom_text(aes(label = scales::percent(per, accuracy = 1)),
position = position_stack(vjust = 0.5),
color = "grey20", size = pietext ) +
coord_polar(theta = "y", direction =-1 ) +
theme_void ()
However what I would like is to label with with the frequency rather than the percentage.
Var1 Freq per
1 a 306 0.2233577
2 b 1064 0.7766423
Is this possible with this method? I tried replacing per with Freq but that just gave some really strange text.
thank you.
aes(label = Freq) is the way to go:
ggplot(data = df,
aes(x = "", y = per, fill = Var1)) +
geom_col() +
geom_text(aes(label = Freq),
position = position_stack(vjust = 0.5),
color = "grey20", size=12) +
coord_polar(theta = "y", direction =-1) +
theme_void ()
Just change geom_text(aes(label =Freq)
ggplot(data = df, aes(x = "", y = per, fill = Var1)) +
geom_col() +
geom_text(aes(label =Freq),
position = position_stack(vjust = 0.5),
color = "black", size = 10 ) +
labs( x="", y="", fill="")+
scale_fill_manual(values=c("#4E79A7", "#fc7d0b"))+
coord_polar(theta = "y", direction =-1 ) +
theme_no_axes()
Plot:
or something that is better than a pie chart
Sample code:
library(waffle)
library(ggthemes)
vals <- c(306,1064)
val_names <- sprintf("%s (%s)", c("a","b"), label=vals)
names(vals) <- val_names
waffle::waffle(vals) +
ggthemes::scale_fill_tableau(name=NULL)
Plot:
Sample code:
df=structure(list(Var1 = c("a", "b"), Freq = c(306L, 1064L), per = c(0.223357664233577, 0.776642335766423)), row.names = c(NA, -2L), class = "data.frame")

How to plot a chart with dual Y, both are bar plot with ggplot2?

I would like to plot a chart with dual Y, both are bar plot with ggplot2, and both bar with its own error bar and label, the following code fails. The bars overlaped, and the labels can not be displayed.
Thanks a lot.
df<- structure(list(dose = structure(1:3, .Label = c("0.5", "1", "2"
), class = "factor"), mean1 = c(13.23, 22.7, 26.06), sd1 = c(0.1,
0.2, 0.3), label = c("a", "b", "c"), mean2 = c(7.98, 16.77, 26.14
), sd2 = c(0.01, 0.2, 0.3), label2 = c("a", "b", "c")), row.names = c(NA,
-3L), class = "data.frame")
ggplot(df,aes(x = dose, fill = dose))+
geom_bar(aes(y = mean1), position = 'dodge', stat="identity", width=.4) +
geom_bar(aes(y = mean2/5), position = 'dodge', stat="identity", width=.4)+
scale_y_continuous(sec.axis = sec_axis(~. *5, name = "mean2"))+
geom_errorbar(aes(ymin = mean1, ymax = mean1 + sd1), width=.07,
position=position_dodge(0.4)) +
geom_errorbar(aes(ymin = mean2, ymax = mean2 + sd2), width=.07,
position=position_dodge(0.4))
geom_text(aes(y =mean1 + sd1, label = label1),vjust = -0.5, position=position_dodge(0.4))
geom_text(aes(y =mean2 + sd2, label = label2,),vjust = -0.5, position=position_dodge(0.4))
Is this what you are looking for? You just need to restructure your data so that it can be dodged by group.
bind_rows(
df |>
select(dose, label, mean = mean1, sd = sd1) |>
mutate(group = 1),
df |>
select(dose, label, mean = mean2, sd = sd2) |>
mutate(group = 2,
mean = mean/5)
) |>
ggplot(aes(x = dose, fill = dose, group = group))+
geom_bar(aes(y = mean), position = 'dodge', stat="identity", width=.4)+
geom_errorbar(aes(ymin = mean, ymax = mean + sd), width=.07,
position=position_dodge(0.4)) +
geom_text(aes(y =mean + sd, label = label),vjust = -0.5, position=position_dodge(0.4))+
scale_y_continuous(sec.axis = sec_axis(~. *5, name = "mean2"))

Using group argument in aes() in ggplot2

I am trying to use the "group" argument in aes() in ggplot2, and I am not sure why it is not working as I currently have it.
I would like an image that groups my "maskalthalf" variable in the way that this image uses "sex" (found here).
This is what my graph currently looks like.
This is the code I have so far.
ggplot(groups, aes(x = message, y = mean, group = factor(maskalthalf))) +
geom_bar(stat = "identity", width = 0.5, fill = "003900") +
geom_text(aes(label = round(mean, digits = 1), vjust = -2)) +
geom_errorbar(aes(ymin = mean - se, ymax = mean + se), width = .2, position = position_dodge(.9)) +
labs(title = "Evaluations of Personal and General Convincingness") +
ylab("Rating") +
xlab("Personal evaluation or general evaluation") +
ylim(0, 8)
This is a sketch of what I am aiming for:
Data:
structure(list(maskalthalf = c("High", "High", "Low", "Low"),
message = c("General", "Personal", "General", "Personal"),
mean = c(4.79090909090909, 6.38181818181818, 4.69879518072289,
4.8433734939759), se = c(0.144452868727642, 0.104112130946133,
0.149182255019704, 0.180996951567937)), row.names = c(NA,
-4L), groups = structure(list(maskalthalf = c("High", "Low"),
.rows = structure(list(1:2, 3:4), ptype = integer(0), class = c("vctrs_list_of",
"vctrs_vctr", "list"))), row.names = 1:2, class = c("tbl_df",
"tbl", "data.frame"), .drop = TRUE), class = c("grouped_df",
"tbl_df", "tbl", "data.frame"))
The image in your first example uses facets to group by variable. So you could try that:
ggplot(df1, aes(x = message, y = mean)) +
geom_col(width = 0.5, fill = "003900") +
geom_text(aes(label = round(mean, digits = 1), vjust = -2)) +
geom_errorbar(aes(ymin = mean - se, ymax = mean + se), width = .2, position = position_dodge(.9)) +
labs(title = "Evaluations of Personal and General Convincingness") +
ylab("Rating") +
xlab("Personal evaluation or general evaluation") +
ylim(0, 8) +
facet_wrap(~maskalthalf)

vjust inconsistent in stacked bar plot

I have a stacked bar plot, with highly unequal heights of bars. I would like to show the percentages on top of each bar.
What I have done so far is the following
df = structure(list(Type = c("Bronchoscopy", "Bronchoscopy", "Endoscopy",
"Endoscopy"), Bacteremia = structure(c(1L, 2L, 1L, 2L), .Label = c("False",
"True"), class = "factor"), count = c(2710L, 64L, 13065L, 103L
), perc = c(97.6928622927181, 2.3071377072819, 99.2178007290401,
0.782199270959903)), class = c("grouped_df", "tbl_df", "tbl",
"data.frame"), row.names = c(NA, -4L), groups = structure(list(
Type = c("Bronchoscopy", "Endoscopy"), .rows = list(1:2,
3:4)), row.names = c(NA, -2L), class = c("tbl_df", "tbl",
"data.frame"), .drop = TRUE))
ggplot(df, aes(x = Type, y = perc, fill = Bacteremia)) +
geom_bar(stat = "identity") +
ylab("percent") +
geom_text(aes(label = paste0(round(perc, 2), "%")), position =
position_stack(vjust = -0.1), color = "black", fontface = "bold")
I can't seem to get the vjust right. It seems like it's not behaving in the same way for the bottom versus the top bar.
What I would like to achieve is to place the percentages slightly higher than the top edge of each bar.
Any ideas?
Here's a possible approach:
ggplot(df, aes(x = Type, y = perc, fill = Bacteremia)) +
geom_bar(stat = "identity") +
ylab("percent") +
geom_text(aes(label = paste0("", round(perc, 2), "%\n"), y = perc),
color = "black", fontface = "bold", nudge_y = 2)
I should elaborate that ggplot2 is going to try to place the geom_text() relative to the data. If you are trying to align horizontally the text labels, you will need to either use annotate() or supply a labelling dataset with type, percent and Bacteremia and call that in geom_text() as below.
labdf <- cbind(df, ypos = c(103, 5, 103, 5))
ggplot(df, aes(x = Type, y = perc, fill = Bacteremia)) +
geom_bar(stat = "identity") +
ylab("percent") +
geom_text(data = labdf,
aes(label = paste0("", round(perc, 2), "%"), y = ypos, x = Type),
color = "black", fontface = "bold")
Here's one way to do it:
df <-
tibble(
Type = c("Bronchoscopy", "Bronchoscopy", "Endoscopy", "Endoscopy"),
Bacteremia = c("False", "True", "False", "True"),
count = c(2710L, 64L, 13065L, 103L)
) %>%
group_by(Type) %>%
mutate(Percent = round((count / sum(count) * 100), 1))
df %>%
ggplot(aes(x = Type, y = Percent, fill = Bacteremia)) +
geom_col() +
geom_label(
data = . %>% filter(Bacteremia == "True"),
aes(y = Percent + 5, label = str_c(Percent, "%")),
show.legend = FALSE
) +
geom_label(
data = . %>% filter(Bacteremia == "False"),
aes(y = 105, label = str_c(Percent, "%")),
show.legend = FALSE
)
The choices of 5 and 105 work on my computer, but may need to be tweaked a bit based on your specific settings and aspect ratio. The first geom_label call sets the y-axis based on the precise percentage, while the second one sets it at a constant level above the bars.
You might also want to play around with using geom_text vs. geom_label to experiment with different color and label settings. The nice thing about geom_label is that it will make it very clear which group is being labeled.

Resources