用Python和Pygame写游戏从入门到精通(17)
admin
2023-07-31 00:36:26
0

最近有些忙,没有更新这个系列,不行啊不行,抓紧更新一篇,这几次可是3D啊3D,多么诱人的词啊……

游戏通常希望营造一个真实的世界,越接近真实越好啊,这样的代入感会很强。在早期,由于硬件的限制,游戏只能提供一些2D的图像,因为这对于电脑绘图是最容易的。还好随着技术发展,现在的显卡已经可以画出很逼真的3D画面了,所以“硬件杀手”游戏层出不穷,贫困游戏迷的噩梦啊。

在开开心心的继续之前,是不是有记忆力好的人想起这个系列第一篇里面我说过,pygame不适合做3D,怎么这里又厚颜无耻的开始说3D了?这不是搬石头砸自己的脚么:)这里我要仔细说明一下,所谓3D,说到底就是利用透视原理,在2D的画面上创造出有纵深错觉(说白了也就是近大远小)的画面而已,毕竟,屏幕是平的,怎么可能真的画出距离呢?换句话说,计算机3D的本质还是2D,只不过额外多了很多东西。

在纯pygame中,我们画3D画面就是通过计算在2D图像上画一些大小不一的东西:)

距离的魔法

我们看现实中的东西,和我们看画面上的东西,最大差别在于能感受现实物体的距离。而距离的产生,则是因为我们双眼看到的东西是不同的,两眼交替闭合,你会发现眼前的东西左右移动。一只眼睛则很难正确的判断距离,虽然比上眼睛还是能感觉到远近,但更精细一点,比如很难把线穿过针眼。

我们在3D画面上绘图的时候,就要遵循这个规律,看看下面的代码。

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667 import pygamefrom pygame.locals import *from random import randint class Star(object):     def __init__(self, x, y, speed):         self.x = x        self.y = y        self.speed = speed def run():     pygame.init()    screen = pygame.display.set_mode((640, 480)) #, FULLSCREEN)     stars = []     # 在第一帧,画上一些星星    for n in xrange(200):         x = float(randint(0, 639))        y = float(randint(0, 479))        speed = float(randint(10, 300))        stars.append( Star(x, y, speed) )     clock = pygame.time.Clock()     white = (255, 255, 255)     while True:         for event in pygame.event.get():            if event.type == QUIT:                return            if event.type == KEYDOWN:                return         # 增加一颗新的星星        y = float(randint(0, 479))        speed = float(randint(10, 300))        star = Star(640., y, speed)        stars.append(star)         time_passed = clock.tick()        time_passed_seconds = time_passed / 1000.         screen.fill((0, 0, 0))         # 绘制所有的星        for star in stars:             new_x = star.x time_passed_seconds * star.speed            pygame.draw.aaline(screen, white, (new_x, star.y), (star.x+1., star.y))            star.x = new_x         def on_screen(star):            return star.x > 0         # 星星跑出了画面,就删了它        stars = filter(on_screen, stars)         pygame.display.update() if __name__ == \”__main__\”:    run()

这里你还可以把FULLSCREEN加上,更有感觉。

这个程序给我的画面,发挥一下你的想象,不是一片宇宙么,无数的星云穿梭,近的速度更快,远的则很慢。而实际上看代码,我们只是画了一些长短不同的线而已!虽然很简单,还是用了不少不少python的技术,特别是函数式编程的(小)技巧。不过强大的你一定没问题:)但是pygame的代码,没有任何没讲过的,为什么这样就能有3D的效果了?感谢你的大脑,因为它知道远的看起来更慢,所以这样的错觉就产生了。

理解3D空间

3D空间的事情,基本就是立体几何的问题,高中学一半应该就差不多理解了,这里不多讲了。你能明白下图的小球在(7, 5, 10)的位置,换句话说,如果你站在原点,面朝Z轴方向。那么小球就在你左边7,上面5,前面10的位置。这就够了~

使用3D向量

我们已经学习了二维向量来表达运动,在三维空间内,当然要使用三维的向量。其实和二维的概念都一样,加减缩放啥的,这里就不用三个元素的元组列表先演练一番了,直接祭出我们的gameobjects神器吧!

12345678910 from gameobjects.vector3 import *A = Vector3(6, 8, 12)B = Vector3(10, 16, 12)print \”A is\”, Aprint \”B is\”, Bprint \”Magnitude of A is\”, A.get_magnitude()print \”A+B is\”, A+Bprint \”A-B is\”, ABprint \”A normalized is\”, A.get_normalized()print \”A*2 is\”, A * 2

运行一下看看结果吧,有些无趣?确实,光数字没法展现3D的美啊,下一次,让我们把物体在立体空间内运动起来。


相关内容

热门资讯

500 行 Python 代码... 语法分析器描述了一个句子的语法结构,用来帮助其他的应用进行推理。自然语言引入了很多意外的歧义,以我们...
定时清理删除C:\Progra... C:\Program Files (x86)下面很多scoped_dir开头的文件夹 写个批处理 定...
65536是2的几次方 计算2... 65536是2的16次方:65536=2⁶ 65536是256的2次方:65536=256 6553...
Mobi、epub格式电子书如... 在wps里全局设置里有一个文件关联,打开,勾选电子书文件选项就可以了。
scoped_dir32_70... 一台虚拟机C盘总是莫名奇妙的空间用完,导致很多软件没法再运行。经过仔细检查发现是C:\Program...
pycparser 是一个用... `pycparser` 是一个用 Python 编写的 C 语言解析器。它可以用来解析 C 代码并构...
小程序支付时提示:appid和... [Q]小程序支付时提示:appid和mch_id不匹配 [A]小程序和微信支付没有进行关联,访问“小...
微信小程序使用slider实现... 众所周知哈,微信小程序里面的音频播放是没有进度条的,但最近有个项目呢,客户要求音频要有进度条控制,所...
Prometheus+Graf... 一,Prometheus概述 1,什么是Prometheus?Prometheus是最初在Sound...
python绘图库Matplo... 本文简单介绍了Python绘图库Matplotlib的安装,简介如下: matplotlib是pyt...