Recipe: Non-spatial scRNA-seq¶
You have: a dissociated single-cell dataset — Scanpy .h5ad or Seurat .rds — with
annotated cell types and no tissue coordinates. You want: a simulation seeded with a
realistic cell-type composition.
What this recipe gets you¶
Composition, not architecture. Dissociation destroyed the spatial information, so BIWT places cells at random within the domain. What survives is the mixture: if your tumor is 62% malignant, 20% T cell, 18% myeloid, your simulation starts that way.
Spatial structure that emerges during the simulation is a result; spatial structure you impose at t=0 is an assumption.
Before you start¶
Find your annotation column and see the composition you are about to reproduce:
import anndata
adata = anndata.read_h5ad("pbmc.h5ad")
adata.obs["cell_type"].value_counts()
That distribution is what BIWT will preserve. If it contains clusters you do not want in the model — doublets, low-quality cells, ambient-RNA clusters — note them now; you will delete them two steps in.
Walking through¶
Import and cluster column¶
Pick the file, then pick your annotation column. Prefer a named column over
seurat_clusters / leiden if you have one.
Spatial query¶
If this screen does not appear, BIWT found no coordinates.
If it does appear, your object has something BIWT read as coordinates. Before saying yes, check what it is: many objects carry a UMAP or t-SNE embedding in a place BIWT will find. Placing cells at their UMAP coordinates draws your embedding in the simulation domain. Say no.
Edit cell types¶
This is the substantive step for scRNA-seq data, which typically has more clusters than a model needs.
Delete the artifacts: doublets, low_quality, high-mito clusters, ambient clusters.
Merge aggressively toward what your model distinguishes. If every T-cell subset will get the same phenotype parameters, they are one cell type. Twelve clusters commonly collapse to four or five populations.
Rename¶
Give them names your config can use. CD8_T_cell, not 4.
Cell counts — the step that matters¶
Four modes; for this recipe two are worth considering.
Scale by proportion is the usual answer. A 40,000-cell dataset is far more agents than most PhysiCell runs want. Set a total of a few thousand and BIWT divides it in the observed ratios.
Set confluence (%) is the answer when density is what you are reasoning about. If you might change the domain later, confluence travels better.
Use data counts is right only when the dataset size is already the population you want. Set manually gives you each count directly.
Rare populations disappear at small totals
Proportional scaling of a population that is 0.3% of your data down to a 2,000-cell total gives you six cells. If a rare type matters to the model, use Set manually and over-represent it deliberately, rather than letting rounding decide.
Positions¶
Random placement inside the domain, with no domain-mismatch dialog — there is no data extent to compare.
Non-spatial data does not mean the initial condition has to be unstructured: this screen is where you can build the geometry your model expects. Place each type in its own pass with a different plotter — a disc of tumor, an annulus of immune cells around it, a rectangle of stroma along one edge.
Cell templates¶
Assign a cell template per type, if your host supplied a template library or you load a TOML file here. The step is skippable, and positions alone are a valid result.
What you get¶
Your chosen number of cells, in the data's type proportions, at random positions with z = 0.