diff --git a/src/spatialdata_plot/pl/render.py b/src/spatialdata_plot/pl/render.py index 852e7a86..eb0fc300 100644 --- a/src/spatialdata_plot/pl/render.py +++ b/src/spatialdata_plot/pl/render.py @@ -1421,7 +1421,15 @@ def _render_images( if isinstance(ch_norm, Normalize): ch_norm = copy(ch_norm) - layers[ch] = ch_norm(layers[ch]) + ch_arr = np.asarray(layers[ch]) + ch_min, ch_max = float(ch_arr.min()), float(ch_arr.max()) + if ch_min == ch_max and not ( + isinstance(ch_norm, Normalize) and (ch_norm.vmin is not None or ch_norm.vmax is not None) + ): + logger.warning(f"Channel {ch!r} has a constant value ({ch_min:.6g}).") + layers[ch] = np.full(ch_arr.shape, 0.5, dtype=np.float64) + else: + layers[ch] = ch_norm(layers[ch]) # Colors for the channel legend (set by each branch if applicable) legend_colors: list[str] | None = None diff --git a/tests/_images/Images_constant_channel_renders_as_midgrey.png b/tests/_images/Images_constant_channel_renders_as_midgrey.png new file mode 100644 index 00000000..c7ffd0b1 Binary files /dev/null and b/tests/_images/Images_constant_channel_renders_as_midgrey.png differ diff --git a/tests/pl/test_render_images.py b/tests/pl/test_render_images.py index 03e21a8e..7bfef71e 100644 --- a/tests/pl/test_render_images.py +++ b/tests/pl/test_render_images.py @@ -154,6 +154,13 @@ def test_plot_correctly_normalizes_multichannel_images(self, sdata_raccoon: Spat axs[1].set_title("two-channel uint16") fig.tight_layout() + def test_plot_constant_channel_renders_as_midgrey(self): + h, w = 64, 64 + data = np.full((1, h, w), 128, dtype=np.uint8) + img = Image2DModel.parse(data, dims=("c", "y", "x")) + sdata = SpatialData(images={"img": img}) + sdata.pl.render_images("img").pl.show(title="constant channel: mid-value (not black)") + # --------------------------------------------------------------------------- # Grayscale + transfunc visual tests