我想知道nVidia OpenGL驱动程序中固定管道(没有连接着色器)内的属性位置:
glVertex = 0
glColor = 3
glNormal = ?
glTexCoord = ?
glMultiTexCoord 0..7 = ?
glSecondaryColor = ?
glFog = ?
Run Code Online (Sandbox Code Playgroud)
根据经验,我找到了顶点和主要颜色位置,但仍然很高兴知道它们.
如果你想知道原因,那么出于兼容性的原因,甚至是GLSL调试(只是为了看看我是否在着色器不能正常工作时将正确的数据传递到正确的位置)等等......
我正在使用现代的OpenGL 4.3核心.
我刚刚意识到1024p x 1024p的tileset对我来说太小了.所以,我用1024p x 1024p x 4p 3D纹理替换它.(我知道,这不是最好的解决方案,我最好使用2D纹理数组.我只是想知道为什么我当前的解决方案不起作用.)
x和y纹理坐标工作正常,和以前一样.z也工作,但有点不正确.我希望第一层有z == 0.0第二层 - z == 0.3333333第三层 - 第四层 - 第四层z == 0.66666666- z == 1.0.
第1层和第4层按预期工作.但是,0.33333333和0.66666666给我的不正确的结果:
0.33333333 -与第二层混合>第一层
0.66666666 -与第4层混合>第3层
(我用线性过滤,这就是为什么他们搅和在一起.)
我试图为第二层和第三层选择正确的z值:
当z == 0.38
第三层显示正常时,第二次显示正常z == 0.62
(当然这些数字是近似的.)
任何想法为什么会发生这种情况以及如何解决这个问题
这是我创建纹理的方式:
glActiveTexture(GL_TEXTURE1);
glGenTextures(1, &maintex);
glBindTexture(GL_TEXTURE_3D, maintex);
glTexImage3D(GL_TEXTURE_3D, 0, GL_RGBA8, TEXSIZE, TEXSIZE, 4, 0, GL_RGBA, GL_UNSIGNED_BYTE, textemp);
glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); …Run Code Online (Sandbox Code Playgroud) 当制服使用布局绑定时,我对什么是绑定纹理的正确方法感到有些困惑。
layout(binding = 0, std140) uniform uCommon
{
mat4 projectionMatrix;
mat4 viewMatrix;
};
layout(binding = 1, std140) uniform uModel
{
mat4 modelViewProjectionMatrix;
};
layout(binding = 3) uniform sampler2D uTexture;
Run Code Online (Sandbox Code Playgroud)
要绑定我的第一个纹理,我应该使用“GL_TEXTURE0 + 3”吗?
glActiveTexture(GL_TEXTURE0 + 3);
glBindTexture(GL_TEXTURE_2D, textureId);
Run Code Online (Sandbox Code Playgroud)
这是正确的方法吗?
编辑:或者采样器使用与其他制服分开的绑定?我可以用吗:
layout(binding = 0) uniform sampler2D uTexture;
Run Code Online (Sandbox Code Playgroud)
还在使用的时候
layout(binding = 0, std140) uniform uCommon
Run Code Online (Sandbox Code Playgroud) 当我查看OpenGL 4.5规范时,我注意到你可以通过调用获得统一的位置:
glGetProgramResourceLocation(program, GL_UNIFORM, name);
Run Code Online (Sandbox Code Playgroud)
这非常类似于:
glGetUniformLocation(program, name);
Run Code Online (Sandbox Code Playgroud)
我想知道使用前者而不是后者是否有任何优势.
我在#1绘制调用期间在片段着色器中生成了一个缓冲区(作为SSBO访问)。然后,我想使用该缓冲区(作为VBO访问)作为绘图调用#2的输入。
问题是,使用函数void glDrawArrays(GLenum mode, GLint first, GLsizei count),我应该知道countCPU上的值。但是在CPU上,我不知道该值。该值仅作为原子计数器存储在GPU内存中。
有什么方法可以使用count存储在GPU内存中的值作为参数进行绘图调用?
我知道我可以从GPU检索值,然后在CPU中使用它,但是由于同步,这会使程序变慢。
我正在尝试将GL_RGB9_E5格式与3D纹理配合使用。为此,我创建了一个简单的测试来了解格式的用法。不知何故我没有得到我所期望的。以下是测试程序
GLuint texture;
const unsigned int depth = 1;
const unsigned int width = 7;
const unsigned int height = 3;
glGenTextures(1, &texture);
glBindTexture(GL_TEXTURE_3D, texture);
const float color[3] = { 0.0f, 0.5f, 0.0f };
const rgb9e5 uColor = float3_to_rgb9e5(color);
GLuint * t1 = (GLuint*)malloc(width*height*depth* sizeof(GLuint));
GLuint * t2 = (GLuint*)malloc(width*height*depth* sizeof(GLuint));
int index = 0;
for (int i = 0; i < depth; i++)
for (int j = 0; j < width; j++)
for (int k = 0; …Run Code Online (Sandbox Code Playgroud) 在我的灯光视图之外采样点时,我遇到了问题,因此我的阴影贴图.这是我在使用GL_TEXTURE_WRAP设置为GL_CLAMP或GL_CLAMP_TO_EDGE的纹理参数创建阴影贴图时得到的:

我已经确定在这里发生的是,地图一侧阴影贴图之外的每个点都有阴影,而地图外侧的每个点都没有阴影被认为是没有阴影的.我认为这是GL_CLAMP和GL_CLAMP_TO_EDGE的预期行为,但我没有在网上找到的各种阴影映射示例中看到这个问题.通过使用GL_CLAMP_TO_BORDER并设置边框颜色来删除其中一些问题,但这也不是我在我看过的任何示例中看到的修复.在遮蔽聚光灯时这是一个预期的问题,如果是这样,通常的修复方法是什么?
我正在尝试使用计算着色器写入 SSBO 并在 CPU 上读回数据。
计算着色器只是一个写入 24 个浮点的 1x1x1 玩具示例:
#version 450 core
layout(local_size_x = 1, local_size_y = 1, local_size_z = 1) in;
layout (std430, binding = 0) buffer particles {
float Particle[];
};
void main() {
for (int i = 0; i < 24; ++i) {
Particle[i] = i + 1;
}
}
Run Code Online (Sandbox Code Playgroud)
这就是我运行着色器并读取数据的方式:
val bufferFlags = GL_MAP_READ_BIT | GL_MAP_PERSISTENT_BIT | GL_MAP_COHERENT_BIT
val bufferSize = 24 * 4
val bufferId = glCreateBuffers()
glNamedBufferStorage(bufferId, bufferSize, bufferFlags)
val mappedBuffer = glMapNamedBufferRange(bufferId, …Run Code Online (Sandbox Code Playgroud) 我遇到了无效的操作,以错误的方式绑定多个着色器:
// Getting ids for each uniform
GLuint uniform1 = glGetUniformLocation(shader1_program.id, "mvp");
GLuint uniform2 = glGetUniformLocation(shader2_program.id, "mvp");
loop {
// Print mesh 1 shader 1
glUseProgram(shader1_program.id);
glUniformMatrix4fv(uniform1 , 1, GL_FALSE, mvp1);
check_gl_error(); // =============================> this one provides the error
glBindVertexArray(vao1);
glDrawArrays(GL_TRIANGLES, 0, vertex_number1);
// Print mesh 2 with shader2
glUseProgram(shader2_program.id);
glUniformMatrix4fv(uniform2 , 1, GL_FALSE, mvp2);
check_gl_error();
glBindVertexArray(vao2);
glDrawArrays(GL_TRIANGLES, 0, vertex_number2);
}
Run Code Online (Sandbox Code Playgroud)
这是check_gl_error()获取错误代码glGetError并打印含义的函数:
typedef struct glmaperror_s {
GLenum err; …Run Code Online (Sandbox Code Playgroud) 我想discard在我的片段着色器中阻止该片段写入模板缓冲区;我对游戏中的视觉效果有一个想法,如果我可以依赖该行为,那么它可能是可以实现的discard。
我的片段着色器没有做任何非常奇特的事情;它只是对纹理进行采样,如果 alpha 接近 0,则discard否则写入。
void main()
{
vec4 texColor = texture(tex, texCoord);
if(texColor.a < 0.5f)
{
discard;
}
FragColor = texColor;
}
Run Code Online (Sandbox Code Playgroud)
然而,听起来我不能依赖于discard阻止模板缓冲区被写入:
如果模板测试处于活动状态,则丢弃的片段仍会影响模板缓冲区。即使模板或深度测试失败,模板测试也可以修改模板缓冲区。并且由于模板测试发生在深度测试之前,因此深度测试失败不能阻止模板测试更新模板缓冲区。
我确实需要在渲染时激活模板测试。我不能依靠discard阻止写入模板缓冲区吗?