3D画像(腎臓組織)の操作#

このチュートリアルでは、3つの空間次元と3つのカラー次元(チャネル)を持つ生物医学画像をインタラクティブに探索します。3D画像処理の一般的な紹介については、3D画像(細胞)の探索を参照してください。ここで使用するデータは、共焦点蛍光顕微鏡で撮影された腎臓組織に対応しています(kidney-tissue-fluorescence.tifの下の[1]を参照してください)。

import matplotlib.pyplot as plt
import numpy as np

import plotly
import plotly.express as px
from skimage import data

画像のロード#

この生物医学画像は、scikit-imageのデータレジストリを通じて利用できます。

返されるデータセットは、3Dマルチチャネル画像です。

print(f'number of dimensions: {data.ndim}')
print(f'shape: {data.shape}')
print(f'dtype: {data.dtype}')
number of dimensions: 4
shape: (16, 512, 512, 3)
dtype: uint16

次元は、(z, y, x, c)、つまり、[平面, 行, 列, チャネル]の順で提供されます。

ここでは、データのスライス(2D平面)のみを検討します。具体的には、スタックの中央にあるスライスを検討しましょう。imshow関数は、グレースケールとRGB(A)の2D画像の両方を表示できます。

plot 3d interaction
Clipping input data to the valid range for imshow with RGB data ([0..1] for floats or [0..255] for integers). Got range [64..4095].

<matplotlib.image.AxesImage object at 0x7fb7a0a61e50>

警告メッセージによると、値の範囲が予想外です。画像のレンダリングは、明らかに色に関して満足のいくものではありません。

vmin, vmax = data.min(), data.max()
print(f'range: ({vmin}, {vmax})')
range: (10, 4095)

plotly.express.imshow()関数のPlotly実装を使用します。これは、浮動小数点数の(0.0, 1.0)と整数値の(0, 255)を超える値範囲をサポートしているためです。

ほら、蛍光顕微鏡です!

各チャネルの値範囲の正規化#

一般的に、チャネルごとに値範囲を正規化したい場合があります。チャネル軸に沿ってデータを(スライス)分割しましょう。これにより、各画像の最大値が使用される3つのシングルチャネル画像が得られます。

fig = px.imshow(
    data[n_plane // 2], facet_col=2, binary_string=True, labels={'facet_col': 'channel'}
)
plotly.io.show(fig)

各カラーチャネルの値の範囲は何ですか?チャネル軸以外のすべての軸で最小値と最大値を取得して確認します。

vmin_0, vmin_1, vmin_2 = np.min(data, axis=(0, 1, 2))
vmax_0, vmax_1, vmax_2 = np.max(data, axis=(0, 1, 2))
print(f'range for channel 0: ({vmin_0}, {vmax_0})')
print(f'range for channel 1: ({vmin_1}, {vmax_1})')
print(f'range for channel 2: ({vmin_2}, {vmax_2})')
range for channel 0: (10, 4095)
range for channel 1: (68, 4095)
range for channel 2: (35, 4095)

非常に具体的に、チャネルごとに値範囲を渡しましょう

Plotlyを使用すると、パン、ズームイン/アウト、および目的の図をPNG形式の静止画像としてエクスポートすることにより、この視覚化を操作できます。

アニメーションフレームとしてのスライスの探索#

再生ボタンをクリックして、16枚すべてのスライスのスタックをz軸に沿って移動します。

fig = px.imshow(
    data,
    zmin=[vmin_0, vmin_1, vmin_2],
    zmax=[vmax_0, vmax_1, vmax_2],
    animation_frame=0,
    binary_string=True,
    labels={'animation_frame': 'plane'},
)
plotly.io.show(fig)

チャネルファセットとスライスアニメーションの結合#

fig = px.imshow(
    data,
    animation_frame=0,
    facet_col=3,
    binary_string=True,
    labels={'facet_col': 'channel', 'animation_frame': 'plane'},
)
plotly.io.show(fig)

生物学者の目には、2つの明るいブロブ(channel=2で最適に見える)が腎臓糸球体であるとわかります[2]

スクリプトの総実行時間: (0 分 14.496 秒)

Sphinx-Galleryによって生成されたギャラリー