那麼這裏是我迄今爲止 - 我去了一個切點複製fig. 2
。
明天更新。 (上半場僅僅是創建一些數據)
from mpl_toolkits.mplot3d import Axes3D
from matplotlib import cm
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import proj3d
import numpy as np
import matplotlib.gridspec as gridspec
import matplotlib
def smooth1d(x, window_len):
s=np.r_[2*x[0]-x[window_len:1:-1],x,2*x[-1]-x[-1:-window_len:-1]]
w = np.hanning(window_len)
y=np.convolve(w/w.sum(),s,mode='same')
return y[window_len-1:-window_len+1]
def smooth2d(A, sigma=3):
window_len = max(int(sigma), 3)*2+1
A1 = np.array([smooth1d(x, window_len) for x in np.asarray(A)])
A2 = np.transpose(A1)
A3 = np.array([smooth1d(x, window_len) for x in A2])
A4 = np.transpose(A3)
return A4
class BaseFilter(object):
def prepare_image(self, src_image, dpi, pad):
ny, nx, depth = src_image.shape
#tgt_image = np.zeros([pad*2+ny, pad*2+nx, depth], dtype="d")
padded_src = np.zeros([pad*2+ny, pad*2+nx, depth], dtype="d")
padded_src[pad:-pad, pad:-pad,:] = src_image[:,:,:]
return padded_src#, tgt_image
def get_pad(self, dpi):
return 0
def __call__(self, im, dpi):
pad = self.get_pad(dpi)
padded_src = self.prepare_image(im, dpi, pad)
tgt_image = self.process_image(padded_src, dpi)
return tgt_image, -pad, -pad
class GaussianFilter(BaseFilter):
"simple gauss filter"
def __init__(self, sigma, alpha=0.5, color=None):
self.sigma = sigma
self.alpha = alpha
if color is None:
self.color=(0, 0, 0)
else:
self.color=color
def get_pad(self, dpi):
return int(self.sigma*3/72.*dpi)
def process_image(self, padded_src, dpi):
#offsetx, offsety = int(self.offsets[0]), int(self.offsets[1])
tgt_image = np.zeros_like(padded_src)
aa = smooth2d(padded_src[:,:,-1]*self.alpha,
self.sigma/72.*dpi)
tgt_image[:,:,-1] = aa
tgt_image[:,:,:-1] = self.color
return tgt_image
from matplotlib.artist import Artist
class FilteredArtistList(Artist):
"""
A simple container to draw filtered artist.
"""
def __init__(self, artist_list, filter):
self._artist_list = artist_list
self._filter = filter
Artist.__init__(self)
def draw(self, renderer):
renderer.start_rasterizing()
renderer.start_filter()
for a in self._artist_list:
a.draw(renderer)
renderer.stop_filter(self._filter)
renderer.stop_rasterizing()
##Create the landscape
from noise import snoise2
def boxOnSurface(rect, X,Y,Z):
#Make rectangle of indicies to draw. Left the four loops expanded for clarity. Otherwise it's fairly ugly.
rXs, rYs, rZs = [],[],[]
for j in range(rect[0][1], rect[1][1]):
i = rect[0][0]
rXs.append(X[i][j])
rYs.append(Y[i][j])
rZs.append(Z[i][j])
for i in range(rect[0][0], rect[1][0]):
j = rect[1][1]
rXs.append(X[i][j])
rYs.append(Y[i][j])
rZs.append(Z[i][j])
for j in range(rect[1][1], rect[0][1], -1):
i = rect[1][0]
rXs.append(X[i][j])
rYs.append(Y[i][j])
rZs.append(Z[i][j])
for i in range(rect[1][0], rect[0][0]-1, -1):
j = rect[0][1]
rXs.append(X[i][j])
rYs.append(Y[i][j])
rZs.append(Z[i][j])
return rXs, rYs, rZs, [np.mean(rXs), np.mean(rYs), np.mean(rZs)]
octaves = 4
freq = octaves * 100
xs, ys = np.linspace(0.0, 100.0, 100), np.linspace(0.0, 100.0, 100)
X,Y = np.meshgrid(xs,ys)
Z1 = np.zeros(X.shape)
for i,x in enumerate(xs):
for j,y in enumerate(ys):
Z1[i][j] = int(snoise2(x/freq, y/freq, octaves) * 127.0 + 128.0)
# get some different colours for the surface.
faceValues = np.zeros(X.shape)
noise = []
for i,x in enumerate(xs):
for j,y in enumerate(ys):
faceValues[i][j] = snoise2(4*x/freq, 4*y/freq, octaves)
jet = cm.get_cmap("jet")
faceColours = []
for i,x in enumerate(xs):
faceColours.append([])
for j,y in enumerate(ys):
normalised = (faceValues[i][j] - faceValues.min())/(faceValues.max() - faceValues.min())
faceColours[i].append(jet(normalised))
faceValues[i][j] = normalised
fig = plt.figure()
miniPlotCount = 5
gs = gridspec.GridSpec(5, miniPlotCount)
ax = fig.add_subplot(gs[0:4,:], projection='3d')
miniAxes = []
for i in range(miniPlotCount):
miniAxes.append(fig.add_subplot(gs[4,i]))
ax.plot_surface(X,Y,Z1, cmap=cm.jet, linewidth=0.2, cstride=2, rstride=2, facecolors=faceColours, vmin=0, vmax=1)
#This decides where we draw the rectangle to be inspecting.
rect = ((25,45),(65,70))
boxXs, boxYs, boxZs, middleOfBox = boxOnSurface(rect, X,Y,Z1)
ax.plot(boxXs, boxYs, boxZs)
xb, yb, zb = middleOfBox
xPoint, yPoint, _ = proj3d.proj_transform(xb, yb, zb, ax.get_proj())
labels = []
grids = []
for i in range(miniPlotCount):
bbox = miniAxes[i].get_window_extent()
xytext = ((bbox.min[0] + bbox.max[0])/2, (bbox.min[1] + bbox.max[1])/2)
labels.append(ax.annotate("", xy=(xPoint,yPoint), arrowprops = {"arrowstyle":'->', "connectionstyle":'arc3,rad=0'}, textcoords="figure pixels", xytext=xytext))
# miniAxes[i].contourf(X[rect[0][0]:rect[1][0],rect[0][1]:rect[1][1]], Y[rect[0][0]:rect[1][0],rect[0][1]:rect[1][1]], Z1[rect[0][0]:rect[1][0],rect[0][1]:rect[1][1]])#, vmin=Z1.min(), vmax=Z1.max())
miniAxes[i].contourf(X[rect[0][0]:rect[1][0],rect[0][1]:rect[1][1]], Y[rect[0][0]:rect[1][0],rect[0][1]:rect[1][1]], faceValues[rect[0][0]:rect[1][0],rect[0][1]:rect[1][1]], vmin=faceValues.min(), vmax=faceValues.max())
# miniAxes[i].set_agg_filter(gaussFilter)
gaussFilter = GaussianFilter(i)
miniAxes[i].grid(linestyle="-", linewidth=2, agg_filter=gaussFilter)
def update_position(e):
xPoint, yPoint, _ = proj3d.proj_transform(xb, yb, zb, ax.get_proj())
for label in labels:
label.xy = xPoint, yPoint
label.update_positions(fig.canvas.renderer)
fig.canvas.draw()
fig.canvas.mpl_connect('motion_notify_event', update_position)
plt.show()
它創建這樣的:
那已經模糊了網格線。 (我不知道爲什麼它沒有模糊其中兩個)看起來,您可以通過在agg_filter=
kwarg中添加您在matplotlib中放置的任何對象的agg_filter
。如果您編輯了GaussianFilter
課程,您可以使它能夠接收所有不確定性數據,然後使用它將blur/opactiy/whatever應用於圖像的各個部分。
我不知道如果我正確地得到您的問題。是否可以通過使用pcolormesh進行熱圖來解決,然後使用與您的不確定性相對應的alpha值繪製黑色線條來形成網格? – Christoph
我沒有看到任何阻止你這樣做的事情。讓所有的線路匹配起來會有點麻煩,但是有工具可以完成所有這些,我已經使用了它們。 – will
是的,我相信我提出的解決方案可以發揮作用。如果我正在解決正確的問題,我不太確定。 – Christoph