半岛体育游戏规则玩法

热线电话:
半岛体育游戏规则玩法
热门搜索:

“星云图”式单细胞UMAP密度图

新闻动态 点击次数:196 发布日期:2026-04-29 11:41
写在开头

最近#单细胞实战100次合集里面,开始在解析胃腺癌的空间转录组与单细胞RNA测序研究系列推文,和之前胃癌单细胞图谱是一个团队的成果

图片

在研读文献的过程中发现,文中好喜欢用密度星云图展示不同分组的细胞占比情况,有一说一就怪好看的,就像尝试复现一下。

图片

主要参考借鉴的推文有:

老俊俊的生信笔记——单细胞二维密度图一文拿捏!生信技能树——画个同款新奇的“Galaxy”星系UMAP图(Nat Immunol:IF27.8)视频版资料:读取数据并随机下采样

数据链接是:https://www.ncbi.nlm.nih.gov/geo/query/acc.cgi?acc=GSE183904

第一层次降维聚类可视化——UMAP图新解:首次分群后按大类分组加圈

复现图表及注释:Density plot of UMAP representation comparing normal and gastric tumor samples after random downsampling to approximately 30,000 cells each to allow statistical equivalence. Each dot represents a single cell. Dashed lines highlight higher proportions of epithelial cells in normal samples and myeloid cells in tumor samples.

图片

所以需要提取注释后的数据,并基于Normal和tumor分组进行随机下采样

#清空环境,加载需要的R包rm(list = ls())library(Seurat)library(tidyverse)source('scRNA_scripts/lib.R')#读取数据及注释结果load(file = "phe.Rdata")sce.all <- readRDS("2-harmony/sce.all_int.rds")sce.all@meta.data <- phe#整理activeident,并下采样sce.all.int <- SetIdent(sce.all, value = "group")sce.all.int <- subset(sce.all.int,downsample=30000)sce.all.int <- SetIdent(sce.all.int, value = "cell_class")

图片

得到需要的数据后,就可以尝试复现密度星云图。

亚群分类密度图

老俊俊的生信笔记——单细胞二维密度图一文拿捏!中,使用ggSCvis亚群分类密度图,看起来得到的结果和文献结果很像

图片

代入实际分析的数据进行可视化:

library(ggSCvis)p1 <- ggscplot(object = sce.all.int) +  stat_density2d(geom = "raster", aes(fill = ..density..),                 contour = F, show.legend = T) +  geom_scPoint(color = "white", size = 0.00001) +  facet_wrap(~group, ncol = 2) +  theme_bw() +  theme(panel.grid = element_blank(),        axis.ticks = element_blank(),        strip.background = element_blank(),        strip.text = element_blank(),        axis.text = element_blank()) +  scale_fill_viridis_c(option = "magma", direction = 1) +  coord_cartesian(expand = F);p1

使用ggSCvis(通常用于单细胞数据的可视化)来创建一个二维散点图,其中包含了密度图和点的分布

初始化一个绘图对象 p1,使用 ggscplot 函数,其中 object 参数指定了要可视化的单细胞数据对象 sce.all.int。添加一个二维密度图层 stat_density2d,使用 raster 几何对象来显示密度。添加一个点图层 geom_scPoint,其中点的颜色为白色,大小为 0.2。使用 facet_wrap 函数根据 group 变量分面显示,每行显示 2 个分面。

图片

结果和文章中出入还是较大,比如密度图颜色被覆盖较多,不按group分组进行展示,所以再试试别的方法

ggpointdensity绘制细胞密度图

生信技能树——画个同款新奇的“Galaxy”星系UMAP图(Nat Immunol:IF27.8)中得到带注释信息圈的密度图

图片

提取需要的UMAP坐标数据以及注释分组信息,绘制需要的密度图:

#ggpointdensityinstall.packages("ggpointdensity")  # 如未安装library(ggpointdensity)# 提取UMAP + 分组信息# 提取UMAP坐标umap_df <- Embeddings(sce.all.int, reduction = "umap") %>%  as.data.frame()# 确保列名统一为 UMAP_1 和 UMAP_2colnames(umap_df) <- c("UMAP_1", "UMAP_2")# 添加meta信息(如group、cell_class)umap_df$group <- sce.all.int$groupumap_df$cell_class <- sce.all.int$cell_class

图片

分开可视化之后拼图:

# 分成两个数据框df_normal <- umap_df %>% filter(group == "Normal")df_tumor  <- umap_df %>% filter(group == "Tumor")# 星云密度图函数plot_density_map <- function(data, title) {  ggplot(data, aes(x = UMAP_1, y = UMAP_2)) +    geom_pointdensity(size = 0.5) +    scale_color_viridis_c(option = "plasma") +    theme_void(base_size = 12) +    ggtitle(title) +    theme(      legend.position = "none",      plot.title = element_text(hjust = 0.5, face = "bold", size = 16)    )}p1 <- plot_density_map(df_normal, "Normal")p2 <- plot_density_map(df_tumor, "Tumor")p1 + p2

图片

可视化结果中,按照group分组分开展示,并且按照细胞亚群密度可视化,但是和星云图还是有点区别。

所以想着如果添加一个点图层 geom_scPoint会不会看起来好些,也就是结合两篇推文的内容进行可视化

密度图加上点图层
p <- ggplot(umap_df, aes(x = UMAP_1, y = UMAP_2)) +  stat_density_2d(    geom = "raster", aes(fill = after_stat(density)),    contour = FALSE, n = 200  ) +  geom_point(color = "white", size = 0.0001, alpha = 0.5) +  facet_wrap(~group, ncol = 2) +  scale_fill_viridis(option = "magma", direction = 1) +  coord_cartesian(expand = FALSE) +  theme_void() +  theme(    strip.text = element_text(face = "bold", size = 14),    legend.position = "none"  );p

图片

有点类似了,但是白色有点掩盖掉了密度图本身的颜色,所以可以调整为更加淡一些的颜色,然后加上细胞大类注释以及圈图即可

#加载需要的R包library(ggplot2)library(ggrepel)library(ggforce)library(viridis)# 计算每组每类细胞的中心位置label_centroids <- umap_df %>%  group_by(group, cell_class) %>%  summarize(    UMAP_1 = median(UMAP_1),    UMAP_2 = median(UMAP_2),    .groups = 'drop'  )#最终可视化结果p <- ggplot(umap_df, aes(x = UMAP_1, y = UMAP_2)) +  stat_density_2d(    geom = "raster",    aes(fill = after_stat(density)),    contour = FALSE, n = 200  ) +  geom_point(color = "#FFFFFFAA", size = 0.005, alpha = 0.2) +  geom_text_repel(    data = label_centroids,    aes(label = cell_class),    color = "white", size = 4, fontface = "bold",    box.padding = 0.5, max.overlaps = Inf  ) +  facet_wrap(~group, ncol = 2) +  scale_fill_viridis(option = "magma", direction = 1) +  coord_cartesian(expand = FALSE) +  theme_void() +  theme(    strip.text = element_text(face = "bold", size = 14),    legend.position = "none"  ) +   stat_ellipse(aes(group = cell_class), color = "white", linetype = "dashed", alpha = 0.5);p

图片

代码简单解析:

计算每个细胞类在每组中的中心位置用于标注——label_centroids“星云图”外观由 stat_density_2d() 渲染出的密度热图模拟geom_point(color = "#FFFFFFAA", size = 0.005, alpha = 0.2)白色透明点,制造一种“边缘星点”效果,视觉上增强结构边界的细腻感。geom_text_repel 避让机制有效防止标签遮挡密度区域facet_wrap(~group, ncol = 2)分成两列图(Normal / Tumor)viridis::magma 是适合暗背景图的高对比色带,星云感较强,theme_void() 去除坐标轴、背景网格等视觉杂项。stat_ellipse(aes(group = cell_class), color = "white", linetype = "dashed", alpha = 0.5)为每个 cell_class 添加轮廓线(高斯椭圆拟合)对比原图不足之处

轮廓线没有很好的契合到UMAP的图形上,细胞亚群标注由于位置问题,导致有些亚群标题不够突出

文章应该对细胞亚群进行了筛选,但复现的时候,只基于分组进行了下采样,大家按照自己的实际需求去展示即可

图片

如果你也想做单细胞转录组数据分析,最好是有自己的计算机资源哦,比如我们的满足你生信分析计算需求的低价解决方案,而且还需要有基本的生物信息学基础,也可以看看我们的生物信息学马拉松授课,你的生物信息学入门课。

2025年也会继续学习分享单细胞内容,并且组建了交流群——承包你2025全部的单细胞转录组降维聚类分群,欢迎一起讨论交流学习!

本站仅提供存储服务,所有内容均由用户发布,如发现有害或侵权内容,请点击举报。

新闻动态