2013-05-24 13 views
6

Mam GUI, który wyświetla wykres. Chcę dopasować ten wykres do istniejącego obrazu. I wyświetlany obraz pod działki przy użyciu:Skalowanie obrazu w matplotlib bez zmiany osi

myaxe.plot(...) 
myaxeimage = myaxe.imshow(myimage, axpect='auto', extent=myaxe.axis(), zorder=-1) 

jestem już w stanie grać z nieprzejrzystości obrazu, używając

myaxeimage.set_alpha() 

Teraz chciałbym, aby móc powiększać i i poruszać się po obrazie, korzystając z GUI, bez dotykania istniejącego wykresu i osi, w celu dopasowania go do mojego wykresu. Innymi słowy, chcę przeskalować do podanych współczynników sx i sy i umieścić pochodzenie obrazu w danym punkcie (x,y), wycinając fragmenty obrazu wychodzące poza osie. Jak mogę to zrobić?

+1

może użyć drugiej osi i sprawdzić, czy można uczynić ją przezroczystą (nie jest to jednak możliwe). – tacaswell

Odpowiedz

0

Wreszcie następuje tcaswell sugestię i wykorzystywane 2 różne osie. W ten sposób po prostu muszę grać z set_xlim() i set_ylim() z moich osi obrazu, aby zmienić pochodzenie i/lub współczynnik powiększenia mojego obrazu. Zamawiam, aby uzyskać obraz poniżej mojej działki, bez ukrywania go ramą wątku, usunąłem ramkę wątku i zamiast tego użyłem ramki osi obrazowych. Ukryłem również tyknięcia z osi obrazu.

from matplotlib import pyplot 

f = pyplot.figure() 
a = f.add_subplot(111, frameon=False) # Remove frame 
a.plot(...) 

myimg = pyplot.imread(...) 
imgaxes = f.add_axes(a.get_position(), # new axes with same position 
    label='image', # label to ensure imgaxes is different from a 
    zorder=-1, # put image below the plot 
    xticks=[], yticks=[]) # remove the ticks 
img = imgaxes.imshow(myimg, aspect='auto') # ensure image takes all the place 

# now, to modify things 
img.set_alpha(...) 
imgaxes.set_xlim((x1, x2)) # x1 and x2 must be calculated from 
          # image size, origin, and zoom factor 
6

Istnieje plik watermark example dystrybuowany z matplotlib, który jest podobny. Zaczynając od tego kodu, możemy zmodyfikować w następujący sposób:

Użyj najpierw ax.imshow, aby narysować obraz. Robię to, ponieważ parametr extent wpływa na ostateczny zakres ax. Ponieważ chcemy, aby ostateczny zakres był zarządzany przez plt.plot(...), umieśćmy go na końcu.

myaximage = ax.imshow(im, aspect='auto', extent=(1,15,0.3,0.7), alpha=0.5, origin='upper', zorder=-1) 

Zamiast extent=myaxe.axis() użyć extent kontrolować położenie i rozmiar obrazu. extent=(1,15,0.3,0.7) umieszcza obraz w prostokącie jako (1, 0.3) jako lewy dolny róg i (15, 0.7) jako prawy górny róg.

Z origin='upper' indeks [0,0] indeks tablicy im jest umieszczony w lewym górnym rogu zakresu. Z origin='lower' zostałby umieszczony w lewym dolnym rogu.


import numpy as np 
import matplotlib.pyplot as plt 
import matplotlib.cbook as cbook 
import matplotlib.image as image 
np.random.seed(1) 
datafile = cbook.get_sample_data('logo2.png', asfileobj=False) 
im = image.imread(datafile) 
fig, ax= plt.subplots() 

myaximage = ax.imshow(im, aspect='auto', extent=(1,15,0.3,0.7), alpha=0.5, zorder=-1) 
ax.plot(np.random.rand(20), '-o', ms=20, lw=2, alpha=1.0, mfc='orange') 
ax.grid() 
plt.show() 

enter image description here


Jeśli chcesz rozszerzyć obraz i przypiąć go do tego stopnia, działki, może trzeba użyć ax.set_xlim i ax.set_ylim także:

myaximage = ax.imshow(im, aspect='auto', extent=(-1,25,0.3,0.7), alpha=0.5, zorder=-1, 
         origin='upper') 

ax.plot(np.random.rand(20), '-o', ms=20, lw=2, alpha=1.0, mfc='orange') 
ax.set_xlim(0,20) 
ax.set_ylim(0,1) 

enter image description here


Albo na większą kontrolę, można obcięcie obrazu do dowolnej ścieżki za pomocą myaximage.set_clip_path:

import numpy as np 
import matplotlib.pyplot as plt 
import matplotlib.cbook as cbook 
import matplotlib.image as image 
import matplotlib.patches as patches 
np.random.seed(1) 
datafile = cbook.get_sample_data('logo2.png', asfileobj=False) 
im = image.imread(datafile) 
fig, ax= plt.subplots() 

myaximage = ax.imshow(im, aspect='auto', extent=(-5,25,0.3,0.7), 
         alpha=0.5, origin='upper', 
         zorder=-2) 
# patch = patches.Circle((300,300), radius=100) 
patch = patches.Polygon([[5, 0.4], [15, 0.4], [15, 0.6], [5, 0.6]], closed=True, 
         transform=ax.transData) 
myaximage.set_clip_path(patch) 
ax.plot(np.random.rand(20), '-o', ms=20, lw=2, alpha=1.0, mfc='orange', 
     zorder=-1) 

ax.set_xlim(0, 20) 
ax.set_ylim(0, 1) 

plt.show() 

enter image description here