英文:
Pygame convert list of shapes to mask
问题
目标是在同一时刻,当一个形状或几个形状经过屏幕时,显示背景中的图像。我的方法是创建一个形状列表(矩形或圆形),然后将所有形状转换为蒙版,然后在每次循环中将屏幕填充为全黑,只显示蒙版。
有没有办法用形状列表创建一个蒙版?我查看了pygame.mask(https://www.pygame.org/docs/ref/mask.html?highlight=mask#module-pygame.mask),但看不到将形状列表转换为蒙版的方法。有什么建议吗?
英文:
The goal is to reveal an image in the background at the same time that a shape or a couple of shapes go through the screen. My approach is to create a list of shapes (rects or circles), then converting al that to a mask and then fill the screen all black but the masks every loop.
Is there a way to make a mask with a list of shapes? I checked pygame.mask (https://www.pygame.org/docs/ref/mask.html?highlight=mask#module-pygame.mask) but cant see a way to convert list of shapes to mask. Any advice?
答案1
得分: 1
你可以做的是为每个形状创建一个"Mask",并创建一个用于填充(覆盖)整个屏幕的"Mask"。
然后,针对以这种方式创建的每个形状遮罩,使用"Mask.draw" 更新屏幕遮罩,类似于这样:
for rect, mask in surfaces:
screen_mask.draw(mask, rect.topleft)
其中,"surfaces" 是一个包含"Rect" / "Mask" 元组的列表。
然后,您可以使用屏幕遮罩来覆盖屏幕,例如使用"Mask.to_surface",如下所示:
new_background = screen_mask.to_surface(background.copy(), setsurface=background)
screen.blit(new_background, (0, 0))
其中,"background" 是您的原始背景图像,"screen_mask" 是应该覆盖屏幕的遮罩,"new_background" 是您要绘制而不是"background" 的表面。
这里是我拼凑的一个示例,你可以了解一下:
import pygame, math
def main():
d = 0
pygame.init()
screen = pygame.display.set_mode((640, 960))
img = pygame.image.load('pexels-stijn-dijkstra-16745023.jpg').convert()
triangle = pygame.Surface((32, 32))
triangle.set_colorkey((0,0,0))
pygame.draw.lines(triangle, 'red', True, ((0, 0), (32, 0), (16, 32)), 8)
triangle_rect = triangle.get_frect(center=(400, 100))
triangle_mask = pygame.mask.from_surface(triangle)
circle = pygame.Surface((32, 32))
circle.set_colorkey((0,0,0))
pygame.draw.circle(circle, 'yellow', (16, 16), 16)
pygame.draw.circle(circle, 'black', (16, 16), 12)
circle_rect = circle.get_frect(center=(200, 400))
circle_mask = pygame.mask.from_surface(circle)
surfaces = (
(triangle, triangle_rect, triangle_rect, triangle_mask),
(circle, circle_rect, circle_rect, circle_mask)
)
cloack = pygame.mask.Mask((640, 960))
clock = pygame.time.Clock()
while True:
for e in pygame.event.get():
if e.type == pygame.QUIT or e.type == pygame.KEYDOWN and e.key == pygame.K_ESCAPE:
return
for surface, rect, base, mask in surfaces:
cloack.draw(mask, rect.topleft)
rect.x = base.x + math.sin(0.01 * pygame.time.get_ticks()) * 10
rect.y += 0.5
back = cloack.to_surface(img.copy(), setsurface=img)
screen.blit(back, (0, 0))
for surface, rect, base, mask in surfaces:
screen.blit(surface, rect)
pygame.display.flip()
d = clock.tick(60)
main()
希望这能帮助你了解如何使用"Mask"来覆盖屏幕。
英文:
What you can do is to create a Mask
for each shape and one Mask
to fill (cover) the entire screen.
Then, for each shape mask created this way, update the screen mask with Mask.draw
, something like this:
for rect, mask in surfaces:
screen_mask.draw(mask, rect.topleft)
where surfaces
is a list of Rect
/Mask
tuples.
Then you can use the screen mask to cover the screen, e.g. with Mask.to_surface
like this:
new_background = screen_mask.to_surface(background.copy(), setsurface=background)
screen.blit(new_background, (0, 0))
where background
is your original background image, screen_mask
the mask that should cover the screen and new_background
is the surface you draw instead of background
.
Here's an example I hacked together; you'll get the idea:
import pygame, math
def main():
d = 0
pygame.init()
screen = pygame.display.set_mode((640, 960))
img = pygame.image.load('pexels-stijn-dijkstra-16745023.jpg').convert()
triangle = pygame.Surface((32, 32))
triangle.set_colorkey((0,0,0))
pygame.draw.lines(triangle, 'red', True, ((0, 0), (32, 0), (16, 32)), 8)
triangle_rect = triangle.get_frect(center=(400, 100))
triangle_mask = pygame.mask.from_surface(triangle)
circle = pygame.Surface((32, 32))
circle.set_colorkey((0,0,0))
pygame.draw.circle(circle, 'yellow', (16, 16), 16)
pygame.draw.circle(circle, 'black', (16, 16), 12)
circle_rect = circle.get_frect(center=(200, 400))
circle_mask = pygame.mask.from_surface(circle)
surfaces = (
(triangle, triangle_rect, triangle_rect, triangle_mask),
(circle, circle_rect, circle_rect, circle_mask)
)
cloack = pygame.mask.Mask((640, 960))
clock = pygame.time.Clock()
while True:
for e in pygame.event.get():
if e.type == pygame.QUIT or e.type == pygame.KEYDOWN and e.key == pygame.K_ESCAPE:
return
for surface, rect, base, mask in surfaces:
cloack.draw(mask, rect.topleft)
rect.x = base.x + math.sin(0.01 * pygame.time.get_ticks()) * 10
rect.y += 0.5
back = cloack.to_surface(img.copy(), setsurface=img)
screen.blit(back, (0, 0))
for surface, rect, base, mask in surfaces:
screen.blit(surface, rect)
pygame.display.flip()
d = clock.tick(60)
main()
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论