Error: stat_bin() in ggplot2 - r

I'm trying to plot a bar that uses 3 data sets. This bar chart, p4, is a summary of the previous 3 bar charts, The first 3 graphs work, its p4 that is the issue. Once i tried making it i got the error:
Error: stat_bin() must not be used with a y aesthetic
I'm not sure what the error could be, i'm very new to r and ggplot2.
Code:
library(ggplot2)
p<-ggplot(data=english, aes(x = reorder(V1, -V3), y=V3))+
geom_bar(stat="identity",
fill="steelblue",
color="black",
width = 0.8,
position = position_dodge(width = 0.9)) +
ggtitle("English") +
theme(plot.title = element_text(hjust = 0.5)) +
labs(x="Letter", y="Frequency") +
coord_flip() +
scale_y_continuous(limits = c(0,max(english[,"V3"])+3)) +
geom_text(aes(label=V3), vjust=0.4, hjust=-0.1, size=3.5)
p2<-ggplot(data=french, aes(x = reorder(V1, -V3), y=V3))+
geom_bar(stat="identity",
fill="steelblue",
color="black",
width = 0.8,
position = position_dodge(width = 0.9)) +
ggtitle("French") +
theme(plot.title = element_text(hjust = 0.5)) +
labs(x="Letter", y="Frequency") +
coord_flip() +
scale_y_continuous(limits = c(0,max(french[,"V3"])+3)) +
geom_text(aes(label=V3), vjust=0.4, hjust=-0.1, size=3.5)
p3<-ggplot(data=german, aes(x = reorder(V1, -V3), y=V3))+
geom_bar(stat="identity",
fill="steelblue",
color="black",
width = 0.8,
position = position_dodge(width = 0.9)) +
ggtitle("German") +
theme(plot.title = element_text(hjust = 0.5)) +
labs(x="Letter", y="Frequency") +
coord_flip() +
scale_y_continuous(limits = c(0,max(german[,"V3"])+3)) +
geom_text(aes(label=V3), vjust=0.4, hjust=-0.1, size=3.5)
p4<-ggplot(aes(x=V1, y=V3))+
geom_bar(data=english,
stat="identity",
fill="steelblue",
color="black",
width = 0.8,
position = position_dodge(width = 0.9))+
geom_bar(data=french,
stat="identity",
fill="green",
color="black",
width = 0.8,
position = position_dodge(width = 0.9))+
geom_bar(data=german,
stat="identity",
fill="red",
color="black",
width = 0.8,
position = position_dodge(width = 0.9))+
ggtitle("Laguages") +
theme(plot.title = element_text(hjust = 0.5)) +
labs(x="Letter", y="Frequency")
require(gridExtra)
grid.arrange(p, p2, p3, p4, ncol=2)

Related

coord_trans and coord_flip in same plot

I am trying to use both coord_trans and coord_flip in the same plot, but that seems to not work. Any suggestion how to use coord_trans for a plot that needs to be flipped?
Using scale_y_log10 does not work since it messes up the stat_summary
p <- ggplot(df.2,aes(reorder(x,y),y,colour=z)) +
geom_jitter(width = 0.2,size=0.1) +
theme_classic(base_size = 8) +
stat_summary(
fun = mean,
geom = "errorbar",
aes(ymax = ..y.., ymin = ..y..),
position = position_dodge(width = 0.1),
width = 0.7,
colour="black") +
coord_flip() +
theme(legend.position = "none") +
labs(x="",y="") +
scale_color_manual(values = mycolors)
p + coord_trans(y = "log10")

R geom_col label cutoff either above or below

Does anyone have a solution to this graph? The labels above the bar graph are cutoff either at the top or at the bottom, depending on how I do the vertical adjustment. I don't think I can reduce the size of the font enough to fit and be readable.
On the one hand, I have this, where the label is cut off in the first bar for Paid Search
ggplot(all_rb6, aes(x = `Number of Touchpoints`, y = Percent, fill = Campaign)) +
geom_col(position = 'dodge') +
facet_wrap(~Campaign) +
labs(title="Title", subtitle = "subtitle") +
theme(plot.title = element_text(hjust = 0.5, face = "bold")) +
theme(plot.subtitle = element_text(hjust = 0.5)) +
labs(caption = "Marketing") +
geom_text(aes(label = paste(format(Percent), "%")), vjust = -0.5, position = position_dodge(.9), colour = "black") +
scale_fill_brewer(palette = "Pastel1")
On the other hand, I have this graph, where the labels are cut off for the third bar in all of them.
ggplot(all_rb6, aes(x = `Number of Touchpoints`, y = Percent, fill = Campaign)) +
geom_col(position = 'dodge') +
facet_wrap(~Campaign) +
labs(title="Title", subtitle = "subtitle") +
theme(plot.title = element_text(hjust = 0.5, face = "bold")) +
theme(plot.subtitle = element_text(hjust = 0.5)) +
labs(caption = "Marketing") +
geom_text(aes(label = paste(format(Percent), "%")), vjust = 1.5, position = position_dodge(.9), colour = "black") +
scale_fill_brewer(palette = "Pastel1")

How to plot geom_line over bar chart grouped by x variable not fill variable?

I have a data frame df
Group Time_Period mean uci lci
1 A Before 4.712195 5.054539 4.369852
2 A After 5.881463 6.241784 5.521142
3 B Before 5.349754 5.872940 4.826567
4 B After 6.653595 7.246231 6.060959
I want to plot this to illustrate that there is no difference in the mean increase between groups. I tried the following :
ggplot(df, aes(x=Time_Period, y=mean, fill=Group)) +
geom_bar(stat="identity", position=position_dodge(width = 1), color="black") +
geom_point(position = position_dodge(width = 1))+
geom_line(aes(group=Group, color=Group), color=c("cyan4","firebrick","cyan4","firebrick"), size =1, position = position_dodge(width = 1)) +
geom_errorbar(aes(ymin=lci, ymax=uci), position=position_dodge(width = 1)) +
theme_bw() +
scale_y_continuous(limits=c(-0.2,8), breaks= seq(0,300,1), minor_breaks=seq(0,300,0.5)) +
theme(panel.grid.minor = element_line(colour="lightgrey", size=0.5)) +
theme(panel.grid.major = element_line(colour="grey", size=0.5)) +
labs(y="Sales", x="Time Period", fill="Category") +
theme(axis.text.x = element_text(face="bold", size=12)) +
theme(axis.text.y = element_text(face="bold", size=12)) +
theme(axis.title.x = element_text(face="bold", size=16)) +
theme(axis.title.y = element_text(face="bold", size=16)) +
theme(legend.text= element_text(face="bold", size=12)) +
theme(legend.title= element_text(face="bold", size=16))
which plots:
However my manager is concerned it is difficult to differentiate the two lines due to the overlap, so he told me to rearrange the columns so that x is Group and fill is Time Period.
I tried the following:
ggplot(df, aes(x=Group, y=mean, fill=Time_Period)) +
geom_bar(stat="identity", position=position_dodge(width = 1), color="black") +
geom_point(position = position_dodge(width = 1))+
geom_line(aes(group=Group), color="black", size =1, position = position_dodge(width = 1)) +
geom_errorbar(aes(ymin=lci, ymax=uci), position=position_dodge(width = 1)) +
theme_bw() +
scale_y_continuous(limits=c(-0.2,8), breaks= seq(0,300,1), minor_breaks=seq(0,300,0.5)) +
theme(panel.grid.minor = element_line(colour="lightgrey", size=0.5)) +
theme(panel.grid.major = element_line(colour="grey", size=0.5)) +
labs(y="Sales", x="Group", fill="Time Period") +
theme(axis.text.x = element_text(face="bold", size=12)) +
theme(axis.text.y = element_text(face="bold", size=12)) +
theme(axis.title.x = element_text(face="bold", size=16)) +
theme(axis.title.y = element_text(face="bold", size=16)) +
theme(legend.text= element_text(face="bold", size=12)) +
theme(legend.title= element_text(face="bold", size=16))
But I can't work out how to get the lines to plot correctly between the two bars instead of just vertically in the centre, even if I adjust the "width" argument for position_dodge:
Please could anyone advise me on how to fix the plot?
You're looking for position_dodge2(). There's a little about it on the ggplot2 dodge reference, and a little more in the actual code on Github. The relevant section below, with some emphasis added:
Dodging preserves the vertical position of an geom while adjusting the
horizontal position. position_dodge2 is a special case of position_dodge
for arranging box plots, which can have variable widths. position_dodge2
also works with bars and rectangles. But unlike position_dodge,
position_dodge2 works without a grouping variable in a layer.
So here's the code, with some of the theming removed.
library(tidyverse)
txt = "
Group Time_Period mean uci lci
1 A Before 4.712195 5.054539 4.369852
2 A After 5.881463 6.241784 5.521142
3 B Before 5.349754 5.872940 4.826567
4 B After 6.653595 7.246231 6.060959"
df <- read.table(text = txt, header = TRUE) %>%
mutate(Group = fct_relevel(Group, "A", "B")) %>%
mutate(Time_Period = fct_relevel(Time_Period, "Before", "After"))
ggplot(df, aes(x=Group, y=mean, fill=Time_Period)) +
geom_bar(stat="identity", position=position_dodge(width = 1), color="black") +
geom_point(position = position_dodge(width = 1))+
geom_line(aes(group=Group), color="black", size =1,
position = position_dodge2(width = 1)) +
geom_errorbar(aes(ymin=lci, ymax=uci), position=position_dodge(width = 1)) +
theme_bw() +
scale_y_continuous(limits=c(-0.2,8), breaks= seq(0,300,1), minor_breaks=seq(0,300,0.5)) +
labs(y="Sales", x="Group", fill="Time Period")
Created on 2019-11-21 by the reprex package (v0.3.0)

ggplot2 How to align graphs with equal y scale as percentage

I'm trying to obtain 2 aligned bar plots with percentage scales of 2 different factors. The y scales calculated as percent are different. I would like to have the same y scales for both plots, for example from 0 to 40% in both. I've tried ylim() which doesn't work on the percentage scale. Example below
library(ggplot2)
library(scales)
data("diamonds")
First bar-plot for cut
p<- ggplot(diamonds, aes(x = cut)) +
geom_bar(aes(y = (..count..)/sum(..count..), fill=cut)) +
scale_y_continuous(labels = percent) +
geom_text(aes(y = ((..count..)/sum(..count..)), label =
scales::percent((..count..)/sum(..count..))),
stat = "count", vjust = -0.25) +
ggtitle("Cut") + theme(plot.title = element_text(hjust = 0.5, size=14,
face="bold")) +
xlab("Cut") +
ylab("Percent") +
theme(legend.position="bottom")
Second bar-plot for clarity
p1<- ggplot(diamonds, aes(x = clarity)) +
geom_bar(aes(y = (..count..)/sum(..count..), fill=clarity)) +
scale_y_continuous(labels = percent) +
geom_text(aes(y = ((..count..)/sum(..count..)), label =
scales::percent((..count..)/sum(..count..))),
stat = "count", vjust = -0.25) +
ggtitle("Clarity") + theme(plot.title = element_text(hjust = 0.5, size=14,
face="bold")) +
xlab("Clarity") +
ylab("Percent") +
theme(legend.position="bottom")
Arranging bar-plot with different scales
grid.arrange(p,p1, ncol = 2)
different scales but I would like for example both at 40% top
If scales weren't percentages I would do this:
p<- ggplot(diamonds, aes(x = cut)) +
geom_bar(aes(y = (..count..)/sum(..count..), fill=cut)) +
scale_y_continuous(labels = percent) +
geom_text(aes(y = ((..count..)/sum(..count..)), label = scales::percent((..count..)/sum(..count..))),
stat = "count", vjust = -0.25) +
ggtitle("Cut") + theme(plot.title = element_text(hjust = 0.5, size=14, face="bold")) +
xlab("Cut") +
ylab("Percent") +
ylim(0, 40)
theme(legend.position="bottom")
But here, of course, it doesn't work and returns this:
Ok I found a way, here the code for Cut for a % scale limited to 60%
p<- ggplot(diamonds, aes(x = cut)) +
geom_bar(aes(y = (..count..)/sum(..count..), fill=cut)) +
geom_text(aes(y = ((..count..)/sum(..count..)), label = scales::percent((..count..)/sum(..count..))),
stat = "count", vjust = -0.25) +
ggtitle("Diamonds Cut") + theme(plot.title = element_text(hjust = 0.5, size=14, face="bold")) +
scale_y_continuous(labels = scales::percent, limits=c(0,0.6)) + labs(y="Percent")
xlab("Cut") +
theme(legend.position="bottom")
p

Add confidence interval with labels to a bar plot

Given the following data:
df.plot <- data.frame(x=c("outcome name","outcome name"),
Condition=c("A","B"),
Score=c(41.5,51.8))
I can produce the following graph:
With this code:
ggplot(df.plot, aes(x=x, y=Score, fill=Condition)) +
geom_bar(position = 'dodge', stat='identity', width=.5) +
xlab(NULL) + coord_cartesian(ylim=c(0,100)) +
geom_text(aes(label=round(Score,2)), position=position_dodge(width=0.5), vjust=-0.25)
I would like to add a confidence interval to the "B" bar that goes from 27.5 to 76.1. I would like those values to be labeled in the graph.
I tried modifying df.plot to include this information and using geom_errorbar but i endup with 2 intervals intead of just one for Condition "B"
df.plot <- data.frame(x=c("outcome name","outcome name"),
Condition=c("A","B"),
Score=c(41.5,51.8),
lb = c(NULL,27.5),
ub = c(NULL,76.1))
ggplot(df.plot, aes(x=x, y=Score, fill=Condition)) +
geom_bar(position = 'dodge', stat='identity', width=.5) +
xlab(NULL) + coord_cartesian(ylim=c(0,100)) +
geom_errorbar(aes(ymin = lb, ymax = ub),
width = 0.2,
linetype = "dotted",
position = position_dodge(width = 0.5),
color="red", size=1) +
geom_text(aes(label=round(Score,2)), position=position_dodge(width=0.5), vjust=-0.25)
Finally, i'm not sure how to add the labels to the top and bottom of the interval.
NA is used for missing values not NULL
This should work as you expect:
df.plot <- data.frame(x=c("outcome name","outcome name"),
Condition=c("A","B"),
Score=c(41.5,51.8),
lb = c(NA,27.5),
ub = c(NA,76.1))
ggplot(df.plot, aes(x=x, y=Score, fill=Condition)) +
geom_bar(position = 'dodge', stat='identity', width=.5) +
xlab(NULL) + coord_cartesian(ylim=c(0,100)) +
geom_errorbar(aes(ymin = lb, ymax = ub),
width = 0.2,
linetype = "dotted",
position = position_dodge(width = 0.5),
color="red", size=1) +
geom_text(aes(label=round(Score,2)), position=position_dodge(width=0.5), vjust=-0.25) +
geom_text(aes(y = lb, label = lb), position=position_dodge(width=0.5), vjust=2)

Resources