Cell Composition Analysis: Bar Plot of Cell Type Proportions Across Samples and Groups
Author: SeekGene
Time: 4 min
Words: 612 words
Updated: 2026-02-27
Reads: 0 times
Load Data
R
# Load cloud platform project data, including Seurat rds and corresponding meta.data
data <- readRDS("/home/demo-seekgene-com/workspace/data/AY1752565399550/input.rds")
meta <- read.table("/home/demo-seekgene-com/workspace/data/AY1752565399550/meta.tsv",
header = TRUE,
sep = "\t",
row.names = 1)
data <- AddMetaData(data, meta.data=meta)Calculate Total Cell Counts and Proportions for Each Cell Type Across Samples
R
# 1. Prepare data, data is a Seurat object, CellAnnotation is a column name for annotation results in meta.data
cell_counts <- data@meta.data %>%
count(CellAnnotation) %>%
mutate(n_thousands = n / 1000)
# 2. Calculate the percentage of each cell type in different samples. CellAnnotation, Sample, and Group are column names in meta.data. Adjust according to your needs.
cell_percentages <- data@meta.data %>%
count(CellAnnotation, Sample, Group) %>%
group_by(CellAnnotation) %>% # Group by cell type
mutate(percentage = n / sum(n) * 100) %>%
ungroup()
# 3. Create sample color mapping
sample_info <- data@meta.data %>%
distinct(CellAnnotation, Group) %>%
arrange(Group, Sample)
# Assign different colors for AD and Ctrl samples
ad_samples <- sample_info %>% filter(Group == "AD") %>% pull(Sample)
ctrl_samples <- sample_info %>% filter(Group == "Ctrl") %>% pull(Sample)
# Define sample colors, sample name before the equals sign, color after
sample_colors=c("3329"="#004983","4305"="#0040d1","4313"="#3472ff","4443"="#5b8dff",
"4481"="#6f9bff","4482"="#96b6ff","4627"="#aac4ff","1224"="#ff2668",
"1230"="#ff3a76","1238"="#ff4e84","3586"="#ff6292","HCT17HEX"="#ff89ad",
"HCTZZT"="#ffb0c8","NT1261"="#ffc4d6","NT1271"="#ffebf1")
sample_order <- names(sample_colors) # Get sample order from color mapping
cell_percentages$Sample <- factor(cell_percentages$Sample, levels = sample_order)Plot Bar Chart of Total Cell Counts for Each Cell Type using ggplot2
R
# 5. Create the upper part
upper_plot <- ggplot(cell_counts, aes(x = CellAnnotation, y = n_thousands, fill = CellAnnotation)) +
geom_bar(stat = "identity", width = 0.7) +
scale_fill_manual(values = my36colors[1:length(unique(cell_counts$CellAnnotation))]) +
labs(title = "Cell Count by Subclustering Type",
x = "Cell Type", y = "Cell Count (x1000)") +
theme_minimal() +
theme(axis.text.x = element_text(angle = 45, hjust = 1),
legend.position = "none",
panel.grid.major = element_blank(),
panel.grid.minor = element_blank(),
panel.border = element_rect(fill = NA, color = "black"))Plot Bar Chart of Cell Type Percentages Across Samples using ggplot2
R
# 5. Create the lower part: Percentage stacked bar chart
lower_plot <- ggplot(cell_percentages, aes(x = CellAnnotation, y = percentage, fill = Sample)) +
geom_bar(stat = "identity", position = "stack", width = 0.7, color = "black", linewidth = 0.3) +
scale_fill_manual(values = sample_colors,
name = "Donor",
labels = function(x) paste0(x, " (", sample_info$CellAnnotation[match(x, sample_info$Sample)], ")")) +
labs(x = "Cell Type", y = "% From Donor") +
theme_classic() +
theme(
axis.text.x = element_text(angle = 45, hjust = 1, size = 10),
axis.text.y = element_text(size = 10),
axis.title.x = element_text(size = 12, face = "bold"),
axis.title.y = element_text(size = 12, face = "bold"),
legend.position = "right",
legend.title = element_text(face = "bold"),
legend.key.size = unit(0.4, "cm"),
panel.grid.major.y = element_line(color = "grey80", linewidth = 0.2),
panel.border = element_rect(color = "black", fill = NA, linewidth = 0.5)
) +
scale_y_continuous(labels = function(x) paste0(x, "%"),
expand = expansion(mult = c(0, 0.05)))Combine and Save Plots
R
# 6. Combine charts (remove titles for a more scientific style)
combined_plot <- upper_plot / lower_plot +
plot_layout(heights = c(1, 1.2))
# 7. Display charts
print(combined_plot)
# 8. Save as high-quality image
ggsave("cell_distribution_plot.png", combined_plot,
width = 10, height = 8, dpi = 300, bg = "white")
# 9. Verify data
cat("Verify total percentage of each cell type:\n")
validation <- cell_percentages %>%
group_by(CellAnnotation) %>%
summarise(total_percent = sum(percentage), .groups = "drop")
print(validation)
cat("\nSample Information:\n")
print(sample_info)