python - PyOpenGL 将变量传递给顶点着色器
问题描述
经过一些建议后,我决定以艰难的方式学习一点 OpenGL。我试图将一个(float
- 命名的myAttrib
)变量传递给顶点着色器,它似乎工作(第 33 行),但显然没有。稍后我想将代码分成更多部分。
代码:
from OpenGL.GL import *
from OpenGL.GL.shaders import *
import pygame
from pygame.locals import *
import numpy, time
def getFileContent(file):
content = open(file, 'r').read()
return content
def initDraw():
pygame.init()
pygame.display.set_mode((640, 480), HWSURFACE | OPENGL | DOUBLEBUF)
vertices = [0.0, 0.5,
0.5, -0.5,
-0.5, -0.5,]
vertices = numpy.array(vertices, dtype = numpy.float32)
myAttrib = 0.3
vertexShader = compileShader(getFileContent("helloTriangle.vert"), GL_VERTEX_SHADER)
fragmentShader = compileShader(getFileContent("helloTriangle.frag"), GL_FRAGMENT_SHADER)
shaderProgram = glCreateProgram()
glAttachShader(shaderProgram, vertexShader)
glAttachShader(shaderProgram, fragmentShader)
glBindAttribLocation(shaderProgram, 1, "myAttrib")
glLinkProgram(shaderProgram)
print(glGetAttribLocation(shaderProgram, "myAttrib"))
glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, 0, vertices)
glEnableVertexAttribArray(0)
glClearColor(0, 0, 0, 1)
glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT)
glUseProgram(shaderProgram)
glDrawArrays(GL_TRIANGLES, 0, 3)
pygame.display.flip()
time.sleep(2)
initDraw()
顶点着色器:
#version 130
attribute vec2 vPosition;
attribute float myAttrib;
void main()
{
gl_Position = vec4(vPosition.x, vPosition.y + myAttrib, 0.0, 1.0);
}
片段着色器:
#version 130
void main()
{
gl_FragColor = vec4(0.0, 1.0, 0.0, 1.0);
}
解决方案
如果使用属性,则必须定义一组通用顶点属性,每个顶点坐标具有一个属性值(在您的情况下为 3)。请参阅顶点规范。
如果您要使用统一,那么您可以为存储在默认统一块的统一变量中的程序设置一个值(您可以想象这有点像全局变量)。见统一(GLSL):
案例 1 - 属性myAttrib
:
顶点着色器
#version 130
attribute vec2 vPosition;
attribute float myAttrib;
void main()
{
gl_Position = vec4(vPosition.x, vPosition.y + myAttrib, 0.0, 1.0);
}
您必须在为顶点坐标执行此操作时定义一个通用顶点属性数组:
attrib = [-0.2, 0.2, 0.0]
myAttrib = numpy.array(attrib, dtype = numpy.float32)
# .....
glLinkProgram(shaderProgram)
myAttrib_location = glGetAttribLocation(shaderProgram, "myAttrib")
# .....
glVertexAttribPointer(myAttrib_location, 1, GL_FLOAT, GL_FALSE, 0, myAttrib)
glEnableVertexAttribArray(myAttrib_location)
或者
glBindAttribLocation(shaderProgram, 1, "myAttrib")
glLinkProgram(shaderProgram)
# .....
glVertexAttribPointer(1, 1, GL_FLOAT, GL_FALSE, 0, myAttrib)
glEnableVertexAttribArray(1)
案例 2 - 制服myUniform
顶点着色器
#version 130
attribute vec2 vPosition;
uniform float myUniform;
void main()
{
gl_Position = vec4(vPosition.x, vPosition.y + myUniform, 0.0, 1.0);
}
通过 获取制服 ( "myUniform"
)的位置glGetUniformLocation
并将值设置为制服glUniform
:
myUniform = 0.3
# .....
glLinkProgram(shaderProgram)
myUniform_location = glGetUniformLocation(shaderProgram, "myUniform")
# .....
glUseProgram(shaderProgram)
glUniform1f(myUniform_location, myUniform)
glDrawArrays(GL_TRIANGLES, 0, 3)
推荐阅读
- react-native - 反应原生底部选项卡导航到所需屏幕
- jquery - 我希望它根据一天横向滚动
- flutter - Flutter中可滚动的Carousel + GridView + GridView + GridView
- templates - 为 Rstudio (default.R) 创建一个模板脚本,其中创建日期自动插入到脚本中
- flutter - 如何在 Flutter 中的 TextField 标签中添加红色星号
- elasticsearch - 围绕平均值的 Elasticsearch 范围聚合
- version-control - 将存储库克隆到我的本地系统一些错误
- postgresql - 使用存储库模式的 TypeORM 更新查询,如何使用 where 子句选择更新表并仅更新一个字段
- python - 升级后没有名为“googleapiclient”的模块
- python - 从 onEvent 内部停止 Azure EventBus 接收器