5 Simple Spatial Analysis
"""
Created on Mon May 16 19:00:32 2022
@author: Ajit Johnson Nirmal
SCIMAP tutorial May 2022
"""
# load packages
import scimap as sm
import scanpy as sc
import pandas as pd
import anndata as ad
Tutorial material
You can download the material for this tutorial from the following link:
The jupyter notebook is available here:
common_path = "/Users/aj/Dropbox (Partners HealthCare)/conferences/scimap_tutorial/may_2022_tutorial/"
#common_path = "C:/Users/ajn16/Dropbox (Partners HealthCare)/conferences/scimap_tutorial/may_2022_tutorial/"
# load data
#adata = sm.pp.mcmicro_to_scimap (image_path= str(common_path) + 'exemplar_001/quantification/unmicst-exemplar-001_cell.csv')
#manual_gate = pd.read_csv(str(common_path) + 'manual_gates.csv')
#adata = sm.pp.rescale (adata, gate=manual_gate)
#phenotype = pd.read_csv(str(common_path) + 'phenotype_workflow.csv')
#adata = sm.tl.phenotype_cells (adata, phenotype=phenotype, label="phenotype")
# add user defined ROI's before proceeding
# load saved anndata object
adata = ad . read ( str ( common_path ) + 'may2022_tutorial.h5ad' )
Calculate distances between cell types
sm.tl.spatial_distance
: The function allows users to calculate the average shortest between phenotypes or clusters of interest (3D data supported).
adata = sm . tl . spatial_distance ( adata ,
x_coordinate = 'X_centroid' , y_coordinate = 'Y_centroid' ,
z_coordinate = None ,
phenotype = 'phenotype' ,
subset = None ,
imageid = 'imageid' ,
label = 'spatial_distance' )
Proc essing Image : unmicst - exemplar - 001 _cell
adata . uns [ 'spatial_distance' ]
Other Immune cells
Unknown
Myeloid
Tumor
ASMA+ cells
Neutrophils
Treg
NK cells
unmicst-exemplar-001_cell_1
0.000000
508.809972
561.874000
547.544519
506.115689
581.323686
570.267087
1248.001853
unmicst-exemplar-001_cell_2
0.000000
25.516388
63.601485
67.024246
27.928445
157.289841
100.258654
816.837582
unmicst-exemplar-001_cell_3
0.000000
15.315383
59.503385
56.590105
34.479892
147.005355
96.374952
817.307871
unmicst-exemplar-001_cell_4
0.000000
28.482334
13.752853
51.500837
46.148651
111.763900
143.243322
746.050742
unmicst-exemplar-001_cell_5
26.357699
0.000000
45.589024
30.234937
58.354288
120.715789
96.739267
824.241184
...
...
...
...
...
...
...
...
...
unmicst-exemplar-001_cell_11166
0.000000
106.320078
70.605640
96.293073
50.637223
91.990689
43.229554
410.740868
unmicst-exemplar-001_cell_11167
0.000000
31.114913
72.531210
118.065360
54.921505
136.323479
30.072174
399.697389
unmicst-exemplar-001_cell_11168
0.000000
50.369768
70.748013
126.968337
36.065610
123.048957
40.094561
409.435592
unmicst-exemplar-001_cell_11169
0.000000
103.275795
64.057762
91.786425
64.741519
93.600860
35.697321
397.194037
unmicst-exemplar-001_cell_11170
10.165511
0.000000
88.288672
113.521913
86.006117
150.562555
23.735243
389.273701
11170 rows × 8 columns
# summary heatmap
import matplotlib.pyplot as plt
plt . rcParams [ 'figure.figsize' ] = [ 3 , 1 ]
sm . pl . spatial_distance ( adata )
# Heatmap without summarizing the individual images
sm . pl . spatial_distance ( adata , heatmap_summarize = False )
sm . pl . spatial_distance ( adata , heatmap_summarize = False , imageid = 'ROI_individual' )
# Numeric plot of shortest distance of phenotypes
# from tumor cells
sm . pl . spatial_distance ( adata , method = 'numeric' , distance_from = 'Tumor' )
sm . pl . spatial_distance ( adata , method = 'numeric' , distance_from = 'Tumor' , log = True )
# plot for each ROI seperately
sm . pl . spatial_distance ( adata , method = 'numeric' , distance_from = 'Tumor' , imageid = 'ROI' )
sm . pl . spatial_distance ( adata , method = 'numeric' , distance_from = 'Tumor' , imageid = 'ROI' , log = True )
# Distribution plot of shortest distance of phenotypes from Tumor cells
sm . pl . spatial_distance ( adata , method = 'distribution' , distance_from = 'Tumor' , distance_to = 'ASMA+ cells' ,
imageid = 'ROI_individual' , log = True )
Spatial co-occurance analysis
sm.tl.spatial_interaction
: The function allows users to computes how likely celltypes are found next to each another compared to random background (3D data supported).
# Using the radius method to identify local neighbours compute P-values
adata = sm . tl . spatial_interaction ( adata ,
method = 'radius' ,
radius = 30 ,
label = 'spatial_interaction_radius' )
Proc essing Image : [ 'unmicst-exemplar-001_cell' ]
Categories ( 1 , object ): [ 'unmicst-exemplar-001_cell' ]
Identifying neighbours within 30 pixels of every cell
Mapping phenotype to neighbors
Performing 1000 permutations
Consolidating the permutation results
# Using the KNN method to identify local neighbours
adata = sm . tl . spatial_interaction ( adata ,
method = 'knn' ,
knn = 10 ,
label = 'spatial_interaction_knn' )
Proc essing Image : [ 'unmicst-exemplar-001_cell' ]
Categories ( 1 , object ): [ 'unmicst-exemplar-001_cell' ]
Identifying the 10 nearest neighbours for every cell
Mapping phenotype to neighbors
Performing 1000 permutations
Consolidating the permutation results
# view results
# spatial_interaction heatmap for a single image
sm . pl . spatial_interaction ( adata ,
summarize_plot = True ,
binary_view = True ,
spatial_interaction = 'spatial_interaction_radius' ,
row_cluster = False , linewidths = 0.75 , linecolor = 'black' )
# spatial_interaction heatmap for a single image
sm . pl . spatial_interaction ( adata ,
summarize_plot = True ,
binary_view = True ,
spatial_interaction = 'spatial_interaction_knn' ,
row_cluster = False , linewidths = 0.75 , linecolor = 'black' )
# Pass the ROI's as different images
adata = sm . tl . spatial_interaction ( adata ,
method = 'radius' ,
imageid = 'ROI_individual' ,
radius = 30 ,
label = 'spatial_interaction_radius_roi' )
Proc essing Image : [ 'Other' ]
Categories ( 1 , object ): [ 'Other' ]
Identifying neighbours within 30 pixels of every cell
Mapping phenotype to neighbors
Performing 1000 permutations
Consolidating the permutation results
Proc essing Image : [ 'artifacts' ]
Categories ( 1 , object ): [ 'artifacts' ]
Identifying neighbours within 30 pixels of every cell
Mapping phenotype to neighbors
Performing 1000 permutations
Consolidating the permutation results
Proc essing Image : [ 'CD57-low-1' ]
Categories ( 1 , object ): [ 'CD57-low-1' ]
Identifying neighbours within 30 pixels of every cell
Mapping phenotype to neighbors
Performing 1000 permutations
Consolidating the permutation results
Proc essing Image : [ 'CD57-low-3' ]
Categories ( 1 , object ): [ 'CD57-low-3' ]
Identifying neighbours within 30 pixels of every cell
Mapping phenotype to neighbors
Performing 1000 permutations
Consolidating the permutation results
Proc essing Image : [ 'CD57-low-2' ]
Categories ( 1 , object ): [ 'CD57-low-2' ]
Identifying neighbours within 30 pixels of every cell
Mapping phenotype to neighbors
Performing 1000 permutations
Consolidating the permutation results
Proc essing Image : [ 'CD57-high-3' ]
Categories ( 1 , object ): [ 'CD57-high-3' ]
Identifying neighbours within 30 pixels of every cell
Mapping phenotype to neighbors
Performing 1000 permutations
Consolidating the permutation results
Proc essing Image : [ 'CD57-high-1' ]
Categories ( 1 , object ): [ 'CD57-high-1' ]
Identifying neighbours within 30 pixels of every cell
Mapping phenotype to neighbors
Performing 1000 permutations
Consolidating the permutation results
Proc essing Image : [ 'CD57-high-2' ]
Categories ( 1 , object ): [ 'CD57-high-2' ]
Identifying neighbours within 30 pixels of every cell
Mapping phenotype to neighbors
Performing 1000 permutations
Consolidating the permutation results
# spatial_interaction heatmap
sm . pl . spatial_interaction ( adata ,
summarize_plot = True ,
spatial_interaction = 'spatial_interaction_radius_roi' ,
row_cluster = True , linewidths = 0.75 , linecolor = 'black' )
# spatial_interaction heatmap
sm . pl . spatial_interaction ( adata ,
summarize_plot = False ,
spatial_interaction = 'spatial_interaction_radius_roi' ,
yticklabels = True ,
row_cluster = True , linewidths = 0.75 , linecolor = 'black' )
Quantifying the proximity score
sm.tl.spatial_pscore
: A scoring system to evaluate user defined proximity between cell types.
The function generates two scores and saved at adata.uns:
- Proximity Density: Total number of interactions identified divided by the total number of cells of the cell-types that were used for interaction analysis.
- Proximity Volume: Total number of interactions identified divided by the total number of all cells in the data.
The interaction sites are also recorded and saved in adata.obs
# Calculate the score for proximity between `Tumor CD30+` cells and `M2 Macrophages`
adata = sm . tl . spatial_pscore ( adata , proximity = [ 'Tumor' , 'NK cells' ],
score_by = 'ROI_individual' ,
phenotype = 'phenotype' ,
method = 'radius' ,
radius = 20 ,
subset = None ,
label = 'spatial_pscore' )
Identifying neighbours within 20 pixels of every cell
Finding neighbourhoods with Tumor
Finding neighbourhoods with NK cells
Please check :
adata .obs ['spatial_pscore' ] &
adata .uns ['spatial_pscore' ] for results
# Plot only `Proximity Volume` scores
plt . figure ( figsize = ( 10 , 5 ))
sm . pl . spatial_pscore ( adata , color = 'Black' , plot_score = 'Proximity Volume' )
/ opt / anaconda3 / envs / scimap / lib / python3 .9 / site - packages / seaborn / _decorators . py : 36 : FutureWarning :
Pass the following variables as keyword args : x , y . From version 0.12 , the only valid positional argument will be `data` , and passing other arguments without an explicit keyword will result in an error or misinterpretation .
# Plot only `Proximity Density` scores
plt . figure ( figsize = ( 10 , 5 ))
sm . pl . spatial_pscore ( adata , color = 'Black' , plot_score = 'Proximity Density' )
/ opt / anaconda3 / envs / scimap / lib / python3 .9 / site - packages / seaborn / _decorators . py : 36 : FutureWarning :
Pass the following variables as keyword args : x , y . From version 0.12 , the only valid positional argument will be `data` , and passing other arguments without an explicit keyword will result in an error or misinterpretation .
# voronoi plot
plt . rcParams [ 'figure.figsize' ] = [ 15 , 10 ]
sm . pl . voronoi ( adata , color_by = 'spatial_pscore' ,
voronoi_edge_color = 'black' ,
voronoi_line_width = 0.3 ,
voronoi_alpha = 0.8 ,
size_max = 5000 ,
overlay_points = None ,
plot_legend = True ,
legend_size = 6 )
# save adata
adata . write ( str ( common_path ) + 'may2022_tutorial.h5ad' )
/ opt / anaconda3 / envs / scimap / lib / python3 .9 / site - packages / anndata / _core / anndata . py : 1228 : FutureWarning :
The `inplace` parameter in pandas . Categorical . reorder_categories is deprecated and will be removed in a future version . Reordering categories will always return a new Categorical object .
... storing 'spatial_pscore' as categorical
This concludes this tutorial