はじめに
matplotlibで画像をマーカーとして用いる方法について説明する。
コード
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#picture scatter plot | |
%matplotlib inline | |
import numpy as np | |
import matplotlib.pyplot as plt | |
from matplotlib.offsetbox import OffsetImage, AnnotationBbox | |
def imscatter(x, y, image, ax=None, zoom=1): | |
if ax is None: | |
ax = plt.gca() | |
try: | |
image = plt.imread(image) | |
except TypeError: | |
# Likely already an array... | |
pass | |
im = OffsetImage(image, zoom=zoom) | |
x, y = np.atleast_1d(x, y) | |
artists = [] | |
for x0, y0 in zip(x, y): | |
ab = AnnotationBbox(im, (x0, y0), xycoords='data', frameon=False) | |
artists.append(ax.add_artist(ab)) | |
ax.update_datalim(np.column_stack([x, y])) | |
ax.autoscale() | |
return artists | |
x,y =np.random.rand(2, 20) | |
image_path = 'cactus5.png' | |
fig, ax = plt.subplots() | |
imscatter(x, y, image_path, ax=ax, zoom=.25) | |
ax.plot(x, y, 'ko',alpha=0) | |
plt.savefig('cactus_plot.png',dpi=200, transparent=False) | |
plt.show() |
解説
グラフの設定
ax = plt.gca()
gcaはGet Current Axesの略で,axが定義されてないときにcurrent axesをaxとして定義している。[1]
画像の読み込み
image = plt.imread(image)
matplotlibでの画像の読み込む。pngファイルを読み込んだものは(M, N, 4)の形になる。4の部分はRGBと透明度のαとなる。[2]
画像をプロットするための設定
im = OffsetImage(image, zoom=zoom)
OffsetImageは画像をいれる箱のことで、画像を指定して読み込む。zoomでもとの大きさに対するサイズをかえることができて、小さくするとOffsetImageは小さくなる。画像は下記サイトから入手した。
Cactus icon 5 | アイコン素材ダウンロードサイト「icooon-mono」 | 商用利用可能なアイコン素材が無料(フリー)ダウンロードできるサイト
6000個以上のアイコン素材を無料でダウンロードできるサイト ICOOON MONO
x, y = np.atleast_1d(x, y)
np.atleast_1dでx, yを1次元以上にする。at leastなので、2次元データとかはそのままとなる。
artists = []
for x0, y0 in zip(x, y):
ab = AnnotationBbox(im, (x0, y0), xycoords='data', frameon=False)
artists.append(ax.add_artist(ab))
AnnotationBboxで(x,y)の位置にimの画像を順次いれていく。imは画像ファイルそのものではなく、画像が入った箱(OffsetImage)とする必要がある。xycoordsは(x, y)の位置をどこにするかの設定で、’data’とすることでデータ値にもとづいて位置が決定する。frameonは画像の枠の設定でFalseで枠無しとなる。
プロットデータの生成
x,y =np.random.rand(2, 20)
ランダムデータを生成する。[3]
画像のプロット
imscatter(x, y, image_path, ax=ax, zoom=.25)
ax.plot(x, y, 'ko',alpha=0)
imscatter でプロットし, zoomで画像の大きさを調整できる。alpha=0で通常のプロットは見えなくしてある。
他の画像でプロット
マレーバクプロット
マレーバクのイラスト
いらすとやは季節のイベント・動物・子供などのかわいいイラストが沢山見つかるフリー素材サイトです。
ベーグルプロット
ベーグルのイラスト
いらすとやは季節のイベント・動物・子供などのかわいいイラストが沢山見つかるフリー素材サイトです。
参考
matplotlib.pyplot.imread — Matplotlib 3.9.3 documentation
https://stackoverrun.com/ja/q/6174885
コメント
ちょうど画像をプロットする方法を探しており、大変勉強になりました。
ありがとうございます。
1点質問なのですが、同じ座標の画像が重ならないようにジッタープロットを作成するにはコードをどのように改変すれば良いでしょうか。
seabornを使えば良さそうですが、具体的な処理が分からず質問させていただきました。
seabornのstripplotを使った画像-ジッタープロットの記事を公開しました。
ご参考ください。
https://sabopy.com/py/matplotlib-120/