我正在为我的计算机图形学项目编写一个程序来模拟我们的太阳系。我使用Python作为编程语言和Pygame(用于控制显示,鼠标和键盘事件),PyOpenGL(用于3D建模和纹理)和PIL(Python图像库,用于加载OpenGL纹理的图像)。该应用的主要目的是能够通过键盘(一种免费的相机游戏)在太阳系中飞行。我使用了“开始”的firstopengl.py方法 使用Python和Pygame进行游戏开发从新手到专业“由Will McGugan编写的书来控制相机。我的问题是,当我运行程序(仅渲染场景中心的纹理太阳)时,它运行良好,直到你移动距离对象太近或太远(旋转到目前为止没有显示任何问题)。错误输出为:
C:\Python27\python.exe E:/Nestor/RESPALDO/NESTOR/DATA/7mo_Semestre/GxC/Proyecto/star-trip/main.py
Traceback (most recent call last):
File "E:/Nestor/RESPALDO/NESTOR/DATA/7mo_Semestre/GxC/Proyecto/star-trip/main.py", line 235, in <module>
main()
File "E:/Nestor/RESPALDO/NESTOR/DATA/7mo_Semestre/GxC/Proyecto/star-trip/main.py", line 225, in main
planets[0].render()
File "E:\Nestor\RESPALDO\NESTOR\DATA\7mo_Semestre\GxC\Proyecto\star-trip\spaceobjects.py", line 46, in render
baseline.loadTexture(self.texture)
File "E:\Nestor\RESPALDO\NESTOR\DATA\7mo_Semestre\GxC\Proyecto\star-trip\baseline.py", line 158, in loadTexture
glTexImage2D(GL_TEXTURE_2D, 0, 3, ix, iy, 0, GL_RGBA, GL_UNSIGNED_BYTE, data)
File "C:\Python27\lib\site-packages\pyopengl-3.1.0-py2.7.egg\OpenGL\latebind.py", line 41, in __call__
return self._finalCall( *args, **named )
File "C:\Python27\lib\site-packages\pyopengl-3.1.0-py2.7.egg\OpenGL\wrapper.py", line 875, in wrapperCall
raise err
OpenGL.error.GLError
乍一看似乎我在应用太阳的纹理时做错了所以这是我以前用来做的代码:
def loadTexture(texture_path):
#Load texture file
data = open(texture_path)
ix = data.size[0]
iy = data.size[1]
data = data.tostring("raw", "RGBX", 0, -1)
# Create textures
textures = glGenTextures(3)
# Select our current texture
glBindTexture(GL_TEXTURE_2D, int(textures[0])) # 2d texture (x and y size)
glPixelStorei(GL_UNPACK_ALIGNMENT,1)
glTexImage2D(GL_TEXTURE_2D, 0, 3, ix, iy, 0, GL_RGBA, GL_UNSIGNED_BYTE, data)
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP)
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP)
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT)
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT)
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST)
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST)
glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_DECAL)
# Create Linear Filtered Texture
glBindTexture(GL_TEXTURE_2D, int(textures[1]))
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR)
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR)
glTexImage2D(GL_TEXTURE_2D, 0, 3, ix, iy, 0, GL_RGBA, GL_UNSIGNED_BYTE, data)
# Create a MipMapped Texture
glBindTexture(GL_TEXTURE_2D, int(textures[2]))
glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_LINEAR)
glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR_MIPMAP_NEAREST)
gluBuild2DMipmaps(GL_TEXTURE_2D, 3, ix, iy, GL_RGBA, GL_UNSIGNED_BYTE, data)
return textures
我也得到“内存不足”的错误,我不太明白,所以任何优化建议都会受到赞赏。
答案 0 :(得分:0)
您是否反复调用loadTexture?听起来有点像它,虽然它很难从你的代码中分辨出来,但是你启动后(当你接近太阳时)异常发生的事实表明它是& #39;在渲染循环中被调用。
如果你在每个渲染循环中调用它,那么你将分配相同纹理图(以及构建gipmaps)的gazillions,这将非常快速地咀嚼图形内存。确保只调用一次loadtextures,保存返回的纹理ID,然后用这些id调用glBind2D,而不是一遍又一遍地调用loadtexture。