Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
159 views
in Technique[技术] by (71.8m points)

r - Creating Stacked Bar Chart With one Variable for each Bar, using melt, and ggplot

This question is raising different points as the one I posted yesterday, with a better description, so I hope for your understanding. I have the following Data:

Data <- data.frame(LMX = c(1.92, 2.33, 3.52, 5.34, 6.07, 4.23, 3.45, 5.64), Thriving = c(4.33, 6.54, 6.13, 4.85, 4.26, 6.32, 5.63, 4.55), Wellbeing = c(1.92, 2.33, 3.52, 2.34, 4.07, 3.23, 3.45, 4.64))
rownames(Data) <- 1:8

Now, my aim is to generate a flipped over bar chart that is showing one bar for each variable with all bars summing up to 100% and being divided according to the values - yellow for all values from 0 to 1.99, orange for all values from 2 to 3.99, red for all values from 4 to 5.99 and green for all values from 6 to 7. More precisely, I am looking for something like this.:
More precisely, I am looking for something like this.

Now, I tried the following code:

Data_A <- melt(cbind(Data, ind = rownames(Data)), id.vars = c('ind'))

ggplot(Data_A, aes(x = variable, y = value, fill = factor(value))) + 
geom_bar(position = "fill", stat = "identity") + 
scale_y_continuous(labels = percent_format())  + 
coord_flip()

Unfortunately, I have no idea how to group the values in those categories I mentioned above. What is more, using this code the values are not even arranged in the right order, from low to high.

Could you please give me some recommendations how to get a picture as shown above?

Also, there is one further problem: each of those 8 individuals belongs to one of two groups and I would like to distinguish the values in the light of those two groups. However, including this additional variable to my code would just melt it together with the other variables. So I don't see any way to account for the groups here as well, using for instance facet_grid() to add the group-identifier. Do you have a suggestion here as well? Should I maybe use an entirely different approach/code?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

Is this what you're looking for regarding the first part? (I advise you change colors to prevent epileptic seizures.)

Data %>%
  mutate_all(cut, c(0, 2, 4, 6, 7), right = F, ) %>% 
  gather(key = "variable", value= "value") %>% 
  ggplot(aes(x = variable, fill = value)) + 
  geom_bar(position = position_fill(reverse = TRUE)) +
  coord_flip() +
  scale_fill_manual(values=c("yellow", "orange", "red", "green"))

enter image description here

For the second part, a reproducible example would be useful but you can probably add a "group" variable (between gather and ggplot) and use facet_grid or facet_wrap.

--- Edited below after information about groups ---

Column selection is missing in DataG[Data_IlA$G1_ID == 2] and variable names are not the same as the one in DataG so DataG_1 cannot be created.

Does one of the suggestions below make the figure you want?

DataG %>%
  gather(key = "variable", value = "value", -Group_ID) %>%
  mutate(value = cut(value, c(0, 1.99, 3.99, 5.99, 7))) %>%
  ggplot(aes(x = variable, fill = value)) +
  geom_bar(position = position_fill(reverse = TRUE)) +
  scale_y_continuous(labels = scales::percent) +
  coord_flip() +
  scale_fill_manual(values=c("#19557E","#6E3B60", "#EA916A", "#EFC76C")) +
  theme(panel.background = element_blank()) +
  xlab("") + ylab("") +
  facet_grid(Group_ID ~ .)

enter image description here

DataG %>%
  gather(key = "variable", value = "value", -Group_ID) %>%
  mutate(value = cut(value, c(0, 1.99, 3.99, 5.99, 7))) %>%
  ggplot(aes(x = Group_ID, fill = value)) +
  geom_bar(position = position_fill(reverse = TRUE)) +
  scale_x_discrete(limits = c("Group 1","Group 2")) +
  scale_y_continuous(labels = scales::percent) +
  coord_flip() +
  scale_fill_manual(values=c("#19557E","#6E3B60", "#EA916A", "#EFC76C")) +
  theme(panel.background = element_blank()) +
  xlab("") + ylab("") +
  facet_grid(variable ~ .)

enter image description here

--- Edited below after comment on groups ---

If you need to change categories for any variable, the easiest way may be to do so before calling ggplot:

DataG %>%
  mutate(Group_ID = case_when(
    Group_ID == 1 ~ "1st group's name",
    Group_ID == 2 ~ "2nd group's name"
  )) %>% 
  gather(key = "variable", value = "value", -Group_ID) %>%
  mutate(value = cut(value, c(0, 1.99, 3.99, 5.99, 7))) %>%
  ggplot(aes(x = variable, fill = value)) +
  geom_bar(position = position_fill(reverse = TRUE)) +
  scale_y_continuous(labels = scales::percent) +
  coord_flip() +
  scale_fill_manual(values=c("#19557E","#6E3B60", "#EA916A", "#EFC76C")) +
  theme(panel.background = element_blank()) +
  xlab("") + ylab("") +
  facet_grid(Group_ID ~ .)

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...