Matplotlib掩蔽根据像素的当前颜色值重置像素的顺序?

2024-07-05 09:56:07 发布

您现在位置:Python中文网/ 问答频道 /正文

1)我需要Matplotlib中似乎没有的掩蔽功能。 (如果不是这样,请告诉我)。你知道吗

2)Matplotlib具有剪裁功能,但“剪裁”区域使用相同的zorder, 因此,呈现几个重叠的多边形形状,这些形状应该根据它们的顺序来查看 在使用剪辑来渲染其中一个的区域中失败,因为我们以前在剪辑区域下面渲染的任何内容都将被擦除(可以说都是白色的)。你知道吗

3)如果可以在渲染时随时“重置”给定像素颜色(我们的背景色)的zorder,那么我们就可以通过剪裁解决问题。我们甚至不需要剪辑,因为我们可以只使用一个给定的zorder值来定义我们所需的遮罩区域的部分,和一个较低的zorder值的部分被剪辑,并在渲染问题的部分后,我们改变所有的“白色”像素的zorder到一个非常低的zorder值,我们有掩蔽能力工作!你知道吗

下面是一个非常简单的示例代码来说明需要:

'''Example of two overlapping squares having arbitrary openings in them.
In this example the opening is just two smaller overlapping square, but it can be anything.
We want to paint the green and red squares so that we see what is behind the opening(s)'''
import matplotlib.pyplot as plt
fig, ax = plt.subplots(figsize=(6, 6))

# This is to test if a well ordered polygon with slits (to define holes) can be rendered
quad_small = [(-0.2, -0.2), (-0.2, 0.2), (0.2, 0.2), (0.2, -0.2), (-0.2, -0.2)]
quad1x1 = [(-1, 1.), (-1, -1.), (1, -1.), (1., 1.), (-1, 1.)]

#Fill quad1x1 with green
x11 = [coord[0] for coord in quad1x1]
y11 = [coord[1] for coord in quad1x1]
plt.fill(x11, y11, facecolor='green', zorder=5)

'''Now make one or more holes, possibly overlapping holes, 
NOTE: if we use clipping to define the holes, Matplotlib sets the same zorder over all the clippped areas 
which was used. Also clipping does not work well with overlapping small squares. Would only work with nonoverlapping
squares.'''
xsq = [coord[0] for coord in quad_small]
ysq = [coord[1] for coord in quad_small]
plt.fill(xsq, ysq, facecolor='white', zorder=5)
xsq = [coord[0]+0.2 for coord in quad_small]
ysq = [coord[1]+0.2 for coord in quad_small]
plt.fill(xsq, ysq, facecolor='white', zorder=5)

'''At this point green and white openings have the same zorder=5.
We would need a call to change the zorder of all the 'white' pixels to a lower value, say 3'''

'''Now we want to render another polygon (red) with holes, but ONLY on areas not covered by the previous rendering,
we use a lower zorder so that we do not paint on the green part'''
x11 = [coord[0]+0.3 for coord in quad1x1]
y11 = [coord[1]+0.3 for coord in quad1x1]
plt.fill(x11, y11, facecolor='red', zorder=4)
xsq = [coord[0]+0.3 for coord in quad_small]
ysq = [coord[1]+0.3 for coord in quad_small]
plt.fill(xsq, ysq, facecolor='white', zorder=4)
xsq = [coord[0]+0.5 for coord in quad_small]
ysq = [coord[1]+0.5 for coord in quad_small]
plt.fill(xsq, ysq, facecolor='white', zorder=4)

'''The hole (white area) of the green square is not painted in red because the zorder of the white area is higher'''

plt.show()

Snapshot of the rendering produced by the code above


Tags: thetoinforpltgreenfillsmall
2条回答

似乎甚至不需要剪裁;因为所有曲面都是闭合的。你知道吗

import numpy as np
import matplotlib.pyplot as plt
fig, ax = plt.subplots(figsize=(6, 6))


xi, yi = np.array([(-0.2, -0.2), (-0.2, 0.2), (0.2, 0.2), (0.2, -0.2), (-0.2, -0.2)]).T
xo, yo = np.array([(-1, 1.), (-1, -1.), (1, -1.), (1., 1.), (-1, 1.)]).T

plt.fill(list(xo)+list(xi), list(yo)+list(yi), facecolor='green', zorder=5)
plt.fill(list(xo+.3)+list(xi+.3), list(yo+.3)+list(yi+.3), facecolor='red', zorder=4)

plt.show()

enter image description here

上面提出的解决方案不起作用,因为它是针对单个不重叠的小四边形。当我们使用两个重叠的四边形时(对您的示例稍作修改):

import numpy as np
import matplotlib.pyplot as plt
fig, ax = plt.subplots(figsize=(6, 6))

xi, yi = np.array([(-0.2, -0.2), (-0.2, 0.2), (0.2, 0.2), (0.2, -0.2), (-0.2, -0.2)]).T
xo, yo = np.array([(-1, 1.), (-1, -1.), (1, -1.), (1., 1.), (-1, 1.)]).T

plt.fill(list(xo)+list(xi)+list(xi+0.1), list(yo)+list(yi)+list(yi+0.1), facecolor='green', zorder=5)
plt.fill(list(xo+.3)+list(xi+.3), list(yo+.3)+list(yi+.3), facecolor='red', zorder=4)

plt.show()

结果如in this snapshot所示

此外,即使在使用单个不重叠的小正方形的示例中,如果该正方形不完全“在”较大的多边形内,也会出现如下所示的渲染问题:

mport numpy as np
import matplotlib.pyplot as plt
fig, ax = plt.subplots(figsize=(6, 6))

xi, yi = np.array([(-0.2, -0.2), (-0.2, 0.2), (0.2, 0.2), (0.2, -0.2), (-0.2, -0.2)]).T
#xo, yo = np.array([(-1, 1.), (-1, -1.), (1, -1.), (1., 1.), (-1, 1.)]).T
xo, yo = np.array([(-.1, .1), (-1, -1.), (1, -1.), (1., 1.), (-.1, .1)]).T

#plt.fill(list(xo)+list(xi)+list(xi+0.1), list(yo)+list(yi)+list(yi+0.1), facecolor='green', zorder=5)
plt.fill(list(xo)+list(xi), list(yo)+list(yi), facecolor='green', zorder=5)
plt.fill(list(xo+.3)+list(xi+.3), list(yo+.3)+list(yi+.3), facecolor='red', zorder=4)

plt.show()

这是结果:Bad rendering when little square is partially outside

也许使用Shapely union可以解决第一个问题,即重叠的小四边形,但是我们如何解决小四边形部分位于外部的问题呢? 请告诉我什么对这个案子最好。你知道吗

相关问题 更多 >