阅读 167

pygame 读取一大堆图片进来,再获取一张图片上的那么一小块区域

本篇博客目的

一次性加载所有素材图片,在通过调用指定图片的名称,获取图片上的某个目标区域(子图)。

可以先临摹并理解代码,最终实现效果如下所示。

image.png

实现上图效果的代码如下所示,在编写的时候可以在重要部分增加注释,辅助理解。

import pygame import os import sys pygame.init() screen = pygame.display.set_mode((400, 400)) # accept 参数限制了传入的图片格式 def load_graphics(path, accept=(".jpg", ".png", ".jpeg")):     graphics = {}     for pic in os.listdir(path):         name, ext = os.path.splitext(pic)         if ext.lower() in accept:             img = pygame.image.load(os.path.join(path, pic))             # 判断图片是否透明背景             if img.get_alpha():                 img = img.convert_alpha()             else:                 # 加快游戏加载图片操作                 img = img.convert()             graphics[name] = img     return graphics def get_image(target, x, y, width, height, colorkey):     image = pygame.Surface((width, height))     image.blit(target, (0, 0), (x, y, width, height))     image.set_colorkey(colorkey)     return image if __name__ == "__main__":     while True: # imgs 文件夹里面的图片自行准备即可,文件名随意 # 可以准备各种后缀名的图片         graphics = load_graphics("./imgs")         print(graphics)         for event in pygame.event.get():             if event.type == pygame.QUIT:                 sys.exit()         screen.fill((12, 200, 180))         # 类似 335,160,70,60,都是根据不同图片测量的,你可以通过截图工具或者画板进行测量。         small_img = get_image(             graphics["one_pic1"], 335, 160, 70, 60, (0, 0, 0))         screen.blit(small_img, (100, 100))         pygame.display.update() 复制代码

代码部分的详细说明与避坑指南

load_graphics 函数作用是调用文件夹所有图片,然后再返回一个字典,字典的键为图片名,值是 pygame.image.load 函数加载的一个 Surface 对象。

代码中需要掌握的重点函数有 img.get_alpha(),该函数用于判断图片是否为透明图片,即带 alpha 值。

使用方式为 pygame.Surface.get_alpha() ,可获取整个图像的透明度,当图片有透明区域的时候,会返回具体的值,一般都是 255,测试本场景可以在文件夹中放置一些不具备透明度的图片,根据文件名进行返回,不透明图片返回不是 0,是 None。

图片1.png 255 图片2.png 255 图片3.png 255 图片4.png 255 图片5.jpg None 复制代码

pygame.Surface.convert() 函数用于修改图像(Surface 对象)为像素格式; pygame.Surface.convert_alpha() 函数也用于修改图像(Surface 对象)为像素格式,在颜色元组中比多了 alpha 值。

对于这二者的区别,就是透明与透明的区别,这两个函数会将图片转换成一种特殊的像素格式图片(pygame内部实现的),会使得游戏渲染图片速度加快,核心原理先不用深究,只需要在编写 pygame 的时候,使用这个函数即可。

在代码编写过程中,一定要记得中文名称会产生的问题,不过该案例无中文 BUG,图片读取中,图片名如果设置为中文,可以正常读取,但建议使用英文单词进行命名。

pygame 读取一大堆图片进来,再获取一张图片上的那么一小块区域

上文代码,在运行过程中,还会出现如下错误:

pygame.error: No video mode has been set 复制代码

该异常出现的原因是调用图片之前,没有对游戏窗口进行初始化操作,也就是缺少了下述代码。

screen = pygame.display.set_mode((400, 400)) 复制代码

提取图片某个区域

该部分的内容是一个新知识点,也需要重点的学习一下,代码部分如下:

def get_image(target, x, y, width, height, colorkey):     image = pygame.Surface((width, height))     image.blit(target, (0, 0), (x, y, width, height))     image.set_colorkey(colorkey)     return image 复制代码

通过 get_image 函数,可以获取指定图片区域,构造 Surface 对象的函数在之前的博客中已经学习了。

image = pygame.Surface((width, height)) 创建了一个 Surface 对象。

image.blit(target, (0, 0), (x, y, width, height)) 在上一行代码创建的 Surface 对象上进行绘制,目标图片是 target,请回顾 blit 函数的三个参数含义,分别是图像,绘制的坐标点,绘制的截面。

翻译过来就是在一个 Surface 对象的 (0,0) 点开始绘制 target 上的一个区域。

或者理解成之前博客中提及的描述,拿着一个透明玻璃在一张图片上进行滑动,寻找目标区域。

set_colorkeyget_colorkey

这两个函数时用来操作透明相关数据的,set_colorkey 目标是当绘制 Surface 对象时,将与 colorkeys 相同的颜色值设为透明,colorkeys 一般传入 RGB 颜色,如果传入 None,则取消 colorkeys 设置。

需要注意,如果代码中的图片已经使用 convert_alpha() 函数转换为透明像素格式,那在进行透明度设置会实现混合效果。

不过该函数使用之后,效果并不是很理想,建议透明图片还是提前准备好。



作者:梦想橡皮擦
链接:https://juejin.cn/post/7027657272574607368


文章分类
代码人生
版权声明:本站是系统测试站点,无实际运营。本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 XXXXXXo@163.com 举报,一经查实,本站将立刻删除。
相关推荐