2
votes

I am trying to show a boxplot and a violin plot in one.

I can fill in the colors of the boxplot and violin plot based on the treatment. But, I don't want them in exactly the same color, I'd prefer the violin plot or the boxplot filling to be lighter.

Also, I am able to get the outer lines of the boxplot in different colors if I add col=TM to the aes of the geom_boxplot. But, then I can not choose these colors or don't know how to (they are now automatically pink and blue).

BACKGROUND:

I am working with a data set that looks something like this:

TM        yax    X       Zscore
Org   zscore  zhfa    -1.72
Org   zscore  zfwa    -0.12

I am plotting the z-scores based on the X (zhfa e.d.) per treatment (TM).

#Colours
ocean = c('#BBDED6' , '#61C0BF' , '#FAE3D9' , '#FFB6B9' )

## Plot ##
z <- ggplot(data = data, aes(x = X, y = Zscore,fill=TM)) +
      geom_split_violin(col="white", fill="white")  +
      geom_boxplot(alpha = 1, width=0.3, aes(fill=TM), position = position_dodge(width = 0.3))          

z + theme(axis.text = element_text(size = 12),legend.position="top")  +
    stat_compare_means(method="t.test", label.y=2.8, label.x=0.3, size=3) +
    scale_fill_manual(values=ocean, labels=c("Mineral fertilizer", "Organic fertilizer"))  

Now, half of the violin plot is filled white, but not both (which would already be better). If I would plot geom_split_violin() it would get exactly the same colors as the boxplot.

Furthermore, should the violinplot of zhfa be on the left side but it get's switched and is displayed at the right side, while it matched the data of the organic (left) boxplot.

The graph now:

I don't know if it can be solved by adding something related to the scale_fill_manual or if this is an impossible request

Sample Data:

data <- data.frame(TM = c(rep("org", 5), rep("min", 5),rep("org", 5), rep("min", 5),rep("org", 5), rep("min", 5)),
                 Zscore = runif(30,-2,2),
                 X = c(rep("zwfa", 10), rep("zhfa", 10), rep("zbfa", 10)))
1
Could you add data to your question using dput(head(df,20)) or some kind of dummy data to work with?NelsonGon
What library is geom_split_violin from?conv3d
That's a tricky one! I found it in one of the answers on stack overflow: stackoverflow.com/questions/35717353/…. If it becomes tricky like that, I'd also be happy to change the colors of the boxplots or already the outline of the boxplots!Marretje Adriaanse
Did the answer solve your problem?conv3d

1 Answers

1
votes

You can add an additional column to your data that is the same structure as TM but different values, then scale the fill:

Sample Data:

data <- data.frame(TM = c(rep("org", 5), rep("min", 5),rep("org", 5), rep("min", 5),rep("org", 5), rep("min", 5)),
                 Zscore = runif(30,-2,2),
                 X = c(rep("zwfa", 10), rep("zhfa", 10), rep("zbfa", 10)))

Begin solution:

data <- data %>% mutate(TMm = c(rep("orgM", 5), rep("minM", 5),rep("orgM", 5), rep("minM", 5),rep("orgM", 5), rep("minM", 5)))
#Colours
ocean = c('#BBDED6' , '#FAE3D9', '#61C0BF'  , '#FFFFFF')

## Plot ##
z <- ggplot(data = data, aes(x = X, y = Zscore,fill=TM)) +
  geom_split_violin(mapping = aes(fill=TMm))  +
  geom_boxplot(alpha = 1, width=0.3, aes(fill=TM), position = position_dodge(width = 0.3))          

z + theme(axis.text = element_text(size = 12),legend.position="top")  +
  stat_compare_means(method="t.test", label.y=2.8, label.x=0.3, size=3) +
  scale_fill_manual(breaks = c("org", "min"), values=ocean, labels=c("Mineral fertilizer", "Organic fertilizer"))

In your data you may have to change breaks = c("org", "min") to whatever you call the factor levels in the TM variable

Or if you want the whole violin plot white:

ocean = c('#BBDED6' , '#FFFFFF', '#61C0BF' , '#FFFFFF')

New Plot: