Skip to content

Commit 504b388

Browse files
committed
Preview for PR #22 6b06016
1 parent fdb76f8 commit 504b388

24 files changed

Lines changed: 267 additions & 99 deletions

pr-22/_sources/notebooks/tutorials/common_errors.ipynb

Lines changed: 145 additions & 44 deletions
Original file line numberDiff line numberDiff line change
@@ -29,10 +29,10 @@
2929
"id": "38a9546a",
3030
"metadata": {
3131
"execution": {
32-
"iopub.execute_input": "2026-08-18T23:00:40.958364Z",
33-
"iopub.status.busy": "2026-08-18T23:00:40.958120Z",
34-
"iopub.status.idle": "2026-08-18T23:00:46.730012Z",
35-
"shell.execute_reply": "2026-08-18T23:00:46.729444Z"
32+
"iopub.execute_input": "2026-08-19T03:32:58.684716Z",
33+
"iopub.status.busy": "2026-08-19T03:32:58.684535Z",
34+
"iopub.status.idle": "2026-08-19T03:33:04.321850Z",
35+
"shell.execute_reply": "2026-08-19T03:33:04.321265Z"
3636
}
3737
},
3838
"outputs": [
@@ -75,6 +75,56 @@
7575
"sdata"
7676
]
7777
},
78+
{
79+
"cell_type": "markdown",
80+
"id": "03f14f09",
81+
"metadata": {},
82+
"source": [
83+
"## 0. `AttributeError: ... object has no attribute 'pl'`\n",
84+
"\n",
85+
"The `.pl` accessor is only attached when you `import spatialdata_plot`. Forget that import and every\n",
86+
"`sdata.pl.…` call raises `AttributeError` — the first wall most newcomers hit. The `Setup` cell above\n",
87+
"already does the import; the cell below runs a *fresh* interpreter without it to show the message."
88+
]
89+
},
90+
{
91+
"cell_type": "code",
92+
"execution_count": 2,
93+
"id": "d550e432",
94+
"metadata": {
95+
"execution": {
96+
"iopub.execute_input": "2026-08-19T03:33:04.323735Z",
97+
"iopub.status.busy": "2026-08-19T03:33:04.323350Z",
98+
"iopub.status.idle": "2026-08-19T03:33:08.844352Z",
99+
"shell.execute_reply": "2026-08-19T03:33:08.843536Z"
100+
}
101+
},
102+
"outputs": [
103+
{
104+
"name": "stdout",
105+
"output_type": "stream",
106+
"text": [
107+
"AttributeError: 'SpatialData' object has no attribute 'pl'\n"
108+
]
109+
}
110+
],
111+
"source": [
112+
"import os\n",
113+
"import subprocess\n",
114+
"import sys\n",
115+
"\n",
116+
"# A fresh interpreter that never imports spatialdata_plot, so `.pl` is unregistered.\n",
117+
"# PYTHON_COLORS=0 keeps the captured traceback free of ANSI colour codes.\n",
118+
"snippet = \"import spatialdata as sd; sd.datasets.blobs().pl.render_shapes('blobs_circles')\"\n",
119+
"result = subprocess.run(\n",
120+
" [sys.executable, \"-c\", snippet],\n",
121+
" capture_output=True,\n",
122+
" text=True,\n",
123+
" env={**os.environ, \"PYTHON_COLORS\": \"0\", \"NO_COLOR\": \"1\"},\n",
124+
")\n",
125+
"print(result.stderr.strip().splitlines()[-1])"
126+
]
127+
},
78128
{
79129
"cell_type": "markdown",
80130
"id": "5ec56751",
@@ -88,14 +138,14 @@
88138
},
89139
{
90140
"cell_type": "code",
91-
"execution_count": 2,
141+
"execution_count": 3,
92142
"id": "12b055e9",
93143
"metadata": {
94144
"execution": {
95-
"iopub.execute_input": "2026-08-18T23:00:46.732100Z",
96-
"iopub.status.busy": "2026-08-18T23:00:46.731683Z",
97-
"iopub.status.idle": "2026-08-18T23:00:46.734623Z",
98-
"shell.execute_reply": "2026-08-18T23:00:46.734105Z"
145+
"iopub.execute_input": "2026-08-19T03:33:08.846271Z",
146+
"iopub.status.busy": "2026-08-19T03:33:08.846138Z",
147+
"iopub.status.idle": "2026-08-19T03:33:08.849074Z",
148+
"shell.execute_reply": "2026-08-19T03:33:08.848642Z"
99149
}
100150
},
101151
"outputs": [
@@ -128,14 +178,14 @@
128178
},
129179
{
130180
"cell_type": "code",
131-
"execution_count": 3,
181+
"execution_count": 4,
132182
"id": "86745998",
133183
"metadata": {
134184
"execution": {
135-
"iopub.execute_input": "2026-08-18T23:00:46.735964Z",
136-
"iopub.status.busy": "2026-08-18T23:00:46.735841Z",
137-
"iopub.status.idle": "2026-08-18T23:00:46.738032Z",
138-
"shell.execute_reply": "2026-08-18T23:00:46.737590Z"
185+
"iopub.execute_input": "2026-08-19T03:33:08.850507Z",
186+
"iopub.status.busy": "2026-08-19T03:33:08.850389Z",
187+
"iopub.status.idle": "2026-08-19T03:33:08.852860Z",
188+
"shell.execute_reply": "2026-08-19T03:33:08.852432Z"
139189
}
140190
},
141191
"outputs": [
@@ -154,12 +204,55 @@
154204
" print(\"KeyError:\", e)"
155205
]
156206
},
207+
{
208+
"cell_type": "markdown",
209+
"id": "9c53205c",
210+
"metadata": {},
211+
"source": [
212+
"## 3. Ambiguous colour/column name\n",
213+
"\n",
214+
"If a `color` string is **both** a valid matplotlib colour name and a column in the element or its\n",
215+
"annotating table, `spatialdata-plot` cannot tell which you meant and raises. Disambiguate with a hex\n",
216+
"string or an RGB(A) tuple, or rename the column. Here we deliberately add a column called `red` to\n",
217+
"force the clash."
218+
]
219+
},
220+
{
221+
"cell_type": "code",
222+
"execution_count": 5,
223+
"id": "dac9e6a7",
224+
"metadata": {
225+
"execution": {
226+
"iopub.execute_input": "2026-08-19T03:33:08.854274Z",
227+
"iopub.status.busy": "2026-08-19T03:33:08.854151Z",
228+
"iopub.status.idle": "2026-08-19T03:33:08.857544Z",
229+
"shell.execute_reply": "2026-08-19T03:33:08.857049Z"
230+
}
231+
},
232+
"outputs": [
233+
{
234+
"name": "stdout",
235+
"output_type": "stream",
236+
"text": [
237+
"ValueError: `color='red'` is ambiguous: it is a valid matplotlib color name AND a column name in element 'blobs_circles'. Disambiguate by either passing an unambiguous color form (hex string like '#ffa500' or an RGB(A) tuple), or by renaming the column.\n"
238+
]
239+
}
240+
],
241+
"source": [
242+
"circles = sdata[\"blobs_circles\"]\n",
243+
"circles[\"red\"] = circles[\"radius\"] # a column whose name is also a colour\n",
244+
"try:\n",
245+
" sdata.pl.render_shapes(\"blobs_circles\", color=\"red\").pl.show()\n",
246+
"except ValueError as e:\n",
247+
" print(\"ValueError:\", e)"
248+
]
249+
},
157250
{
158251
"cell_type": "markdown",
159252
"id": "555854a5",
160253
"metadata": {},
161254
"source": [
162-
"## 3. Invalid image channel\n",
255+
"## 4. Invalid image channel\n",
163256
"\n",
164257
"Selecting a channel that does not exist raises a `ValueError` that lists the valid channels — helpful\n",
165258
"when you are unsure how a multichannel image is indexed (see the *Multichannel & fluorescence images*\n",
@@ -168,14 +261,14 @@
168261
},
169262
{
170263
"cell_type": "code",
171-
"execution_count": 4,
264+
"execution_count": 6,
172265
"id": "b1164416",
173266
"metadata": {
174267
"execution": {
175-
"iopub.execute_input": "2026-08-18T23:00:46.739419Z",
176-
"iopub.status.busy": "2026-08-18T23:00:46.739308Z",
177-
"iopub.status.idle": "2026-08-18T23:00:46.741767Z",
178-
"shell.execute_reply": "2026-08-18T23:00:46.741290Z"
268+
"iopub.execute_input": "2026-08-19T03:33:08.858839Z",
269+
"iopub.status.busy": "2026-08-19T03:33:08.858735Z",
270+
"iopub.status.idle": "2026-08-19T03:33:08.861474Z",
271+
"shell.execute_reply": "2026-08-19T03:33:08.861008Z"
179272
}
180273
},
181274
"outputs": [
@@ -199,22 +292,22 @@
199292
"id": "bac6ece4",
200293
"metadata": {},
201294
"source": [
202-
"## 4. A per-channel `norm` list of the wrong length\n",
295+
"## 5. A per-channel `norm` list of the wrong length\n",
203296
"\n",
204297
"When you pass a list of norms for an image, its length must match the number of channels you are\n",
205298
"rendering (see the *Normalization and contrast* tutorial)."
206299
]
207300
},
208301
{
209302
"cell_type": "code",
210-
"execution_count": 5,
303+
"execution_count": 7,
211304
"id": "50f8a28b",
212305
"metadata": {
213306
"execution": {
214-
"iopub.execute_input": "2026-08-18T23:00:46.743101Z",
215-
"iopub.status.busy": "2026-08-18T23:00:46.742992Z",
216-
"iopub.status.idle": "2026-08-18T23:00:46.745491Z",
217-
"shell.execute_reply": "2026-08-18T23:00:46.745025Z"
307+
"iopub.execute_input": "2026-08-19T03:33:08.862734Z",
308+
"iopub.status.busy": "2026-08-19T03:33:08.862642Z",
309+
"iopub.status.idle": "2026-08-19T03:33:08.865037Z",
310+
"shell.execute_reply": "2026-08-19T03:33:08.864515Z"
218311
}
219312
},
220313
"outputs": [
@@ -238,22 +331,22 @@
238331
"id": "4d06836d",
239332
"metadata": {},
240333
"source": [
241-
"## 5. `grayscale` needs exactly three channels\n",
334+
"## 6. `grayscale` needs exactly three channels\n",
242335
"\n",
243336
"`grayscale=True` collapses a three-channel selection into one intensity, so it requires exactly three\n",
244337
"channels."
245338
]
246339
},
247340
{
248341
"cell_type": "code",
249-
"execution_count": 6,
342+
"execution_count": 8,
250343
"id": "b77803c7",
251344
"metadata": {
252345
"execution": {
253-
"iopub.execute_input": "2026-08-18T23:00:46.746983Z",
254-
"iopub.status.busy": "2026-08-18T23:00:46.746876Z",
255-
"iopub.status.idle": "2026-08-18T23:00:46.896268Z",
256-
"shell.execute_reply": "2026-08-18T23:00:46.895864Z"
346+
"iopub.execute_input": "2026-08-19T03:33:08.866284Z",
347+
"iopub.status.busy": "2026-08-19T03:33:08.866186Z",
348+
"iopub.status.idle": "2026-08-19T03:33:09.025021Z",
349+
"shell.execute_reply": "2026-08-19T03:33:09.024560Z"
257350
}
258351
},
259352
"outputs": [
@@ -287,21 +380,21 @@
287380
"id": "52c83cb4",
288381
"metadata": {},
289382
"source": [
290-
"## 6. Invalid `PercentileNormalize` bounds\n",
383+
"## 7. Invalid `PercentileNormalize` bounds\n",
291384
"\n",
292385
"Percentile bounds are validated at construction time: they must satisfy `0 <= pmin < pmax <= 100`."
293386
]
294387
},
295388
{
296389
"cell_type": "code",
297-
"execution_count": 7,
390+
"execution_count": 9,
298391
"id": "c5293c63",
299392
"metadata": {
300393
"execution": {
301-
"iopub.execute_input": "2026-08-18T23:00:46.897867Z",
302-
"iopub.status.busy": "2026-08-18T23:00:46.897752Z",
303-
"iopub.status.idle": "2026-08-18T23:00:46.900467Z",
304-
"shell.execute_reply": "2026-08-18T23:00:46.899901Z"
394+
"iopub.execute_input": "2026-08-19T03:33:09.026804Z",
395+
"iopub.status.busy": "2026-08-19T03:33:09.026686Z",
396+
"iopub.status.idle": "2026-08-19T03:33:09.029442Z",
397+
"shell.execute_reply": "2026-08-19T03:33:09.028925Z"
305398
}
306399
},
307400
"outputs": [
@@ -317,7 +410,13 @@
317410
}
318411
],
319412
"source": [
320-
"for bad in [(50, 50), (90, 10), (-1, 50), (0, 101)]:\n",
413+
"bad_bounds = [\n",
414+
" (50, 50), # pmin == pmax (must be strictly increasing)\n",
415+
" (90, 10), # pmin > pmax\n",
416+
" (-1, 50), # pmin < 0\n",
417+
" (0, 101), # pmax > 100\n",
418+
"]\n",
419+
"for bad in bad_bounds:\n",
321420
" try:\n",
322421
" PercentileNormalize(*bad)\n",
323422
" except ValueError as e:\n",
@@ -334,8 +433,10 @@
334433
"`spatialdata-plot` fails fast with messages that name the offending element, column, channel, or\n",
335434
"bound:\n",
336435
"\n",
436+
"- **`AttributeError: ... has no attribute 'pl'`** — you forgot `import spatialdata_plot`.\n",
337437
"- **Element not found** — check the key in `sdata`.\n",
338438
"- **No column to colour by** — put the value on the element or its annotating table.\n",
439+
"- **Ambiguous colour/column name** — pass a hex/RGB(A) colour, or rename the column.\n",
339440
"- **Invalid channel** — the message lists the valid channels.\n",
340441
"- **Wrong-length `norm` list** — one norm per rendered channel.\n",
341442
"- **`grayscale` needs three channels** — select exactly three.\n",
@@ -354,14 +455,14 @@
354455
},
355456
{
356457
"cell_type": "code",
357-
"execution_count": 8,
458+
"execution_count": 10,
358459
"id": "384e30e6",
359460
"metadata": {
360461
"execution": {
361-
"iopub.execute_input": "2026-08-18T23:00:46.901803Z",
362-
"iopub.status.busy": "2026-08-18T23:00:46.901692Z",
363-
"iopub.status.idle": "2026-08-18T23:00:46.933690Z",
364-
"shell.execute_reply": "2026-08-18T23:00:46.933162Z"
462+
"iopub.execute_input": "2026-08-19T03:33:09.030827Z",
463+
"iopub.status.busy": "2026-08-19T03:33:09.030712Z",
464+
"iopub.status.idle": "2026-08-19T03:33:09.058691Z",
465+
"shell.execute_reply": "2026-08-19T03:33:09.058073Z"
365466
}
366467
},
367468
"outputs": [

pr-22/_static/documentation_options.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
const DOCUMENTATION_OPTIONS = {
2-
VERSION: '0.1.dev1+g375c17330.d20260818',
2+
VERSION: '0.1.dev1+g375c17330.d20260819',
33
LANGUAGE: 'en',
44
COLLAPSE_INDEX: false,
55
BUILDER: 'html',

pr-22/api.html

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@
5656
<link rel="preload" as="script" href="_static/scripts/bootstrap.js?digest=90905a2f556bf617f1a9" />
5757
<link rel="preload" as="script" href="_static/scripts/pydata-sphinx-theme.js?digest=90905a2f556bf617f1a9" />
5858

59-
<script src="_static/documentation_options.js?v=6ef967b8"></script>
59+
<script src="_static/documentation_options.js?v=d505e5a5"></script>
6060
<script src="_static/doctools.js?v=fd6eb6e6"></script>
6161
<script src="_static/sphinx_highlight.js?v=6ffebe34"></script>
6262
<script src="_static/clipboard.min.js?v=a7894cd8"></script>
@@ -71,7 +71,7 @@
7171
<link rel="prev" title="Interactive region annotation" href="notebooks/examples/interactive_annotate.html" />
7272
<meta name="viewport" content="width=device-width, initial-scale=1"/>
7373
<meta name="docsearch:language" content="en"/>
74-
<meta name="docsearch:version" content="0.1.dev1+g375c17330.d20260818" />
74+
<meta name="docsearch:version" content="0.1.dev1+g375c17330.d20260819" />
7575

7676

7777
<script src="_static/searchtools.js"></script>

pr-22/changelog.html

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@
5656
<link rel="preload" as="script" href="_static/scripts/bootstrap.js?digest=90905a2f556bf617f1a9" />
5757
<link rel="preload" as="script" href="_static/scripts/pydata-sphinx-theme.js?digest=90905a2f556bf617f1a9" />
5858

59-
<script src="_static/documentation_options.js?v=6ef967b8"></script>
59+
<script src="_static/documentation_options.js?v=d505e5a5"></script>
6060
<script src="_static/doctools.js?v=fd6eb6e6"></script>
6161
<script src="_static/sphinx_highlight.js?v=6ffebe34"></script>
6262
<script src="_static/clipboard.min.js?v=a7894cd8"></script>
@@ -71,7 +71,7 @@
7171
<link rel="prev" title="Plotting (.pl)" href="plotting.html" />
7272
<meta name="viewport" content="width=device-width, initial-scale=1"/>
7373
<meta name="docsearch:language" content="en"/>
74-
<meta name="docsearch:version" content="0.1.dev1+g375c17330.d20260818" />
74+
<meta name="docsearch:version" content="0.1.dev1+g375c17330.d20260819" />
7575

7676

7777
<script src="_static/searchtools.js"></script>

pr-22/contributing.html

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@
5656
<link rel="preload" as="script" href="_static/scripts/bootstrap.js?digest=90905a2f556bf617f1a9" />
5757
<link rel="preload" as="script" href="_static/scripts/pydata-sphinx-theme.js?digest=90905a2f556bf617f1a9" />
5858

59-
<script src="_static/documentation_options.js?v=6ef967b8"></script>
59+
<script src="_static/documentation_options.js?v=d505e5a5"></script>
6060
<script src="_static/doctools.js?v=fd6eb6e6"></script>
6161
<script src="_static/sphinx_highlight.js?v=6ffebe34"></script>
6262
<script src="_static/clipboard.min.js?v=a7894cd8"></script>
@@ -71,7 +71,7 @@
7171
<link rel="prev" title="Changelog" href="changelog.html" />
7272
<meta name="viewport" content="width=device-width, initial-scale=1"/>
7373
<meta name="docsearch:language" content="en"/>
74-
<meta name="docsearch:version" content="0.1.dev1+g375c17330.d20260818" />
74+
<meta name="docsearch:version" content="0.1.dev1+g375c17330.d20260819" />
7575

7676

7777
<script src="_static/searchtools.js"></script>

pr-22/gallery.html

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@
5656
<link rel="preload" as="script" href="_static/scripts/bootstrap.js?digest=90905a2f556bf617f1a9" />
5757
<link rel="preload" as="script" href="_static/scripts/pydata-sphinx-theme.js?digest=90905a2f556bf617f1a9" />
5858

59-
<script src="_static/documentation_options.js?v=6ef967b8"></script>
59+
<script src="_static/documentation_options.js?v=d505e5a5"></script>
6060
<script src="_static/doctools.js?v=fd6eb6e6"></script>
6161
<script src="_static/sphinx_highlight.js?v=6ffebe34"></script>
6262
<script src="_static/clipboard.min.js?v=a7894cd8"></script>
@@ -71,7 +71,7 @@
7171
<link rel="prev" title="spatialdata-plot: rich static plotting from SpatialData objects" href="index.html" />
7272
<meta name="viewport" content="width=device-width, initial-scale=1"/>
7373
<meta name="docsearch:language" content="en"/>
74-
<meta name="docsearch:version" content="0.1.dev1+g375c17330.d20260818" />
74+
<meta name="docsearch:version" content="0.1.dev1+g375c17330.d20260819" />
7575

7676

7777
<script src="_static/searchtools.js"></script>

0 commit comments

Comments
 (0)