[英]How can I add multiple textures to my openGL program?
我正在編寫一個openGL程序並且有多個模型被繪制到環境中,但我不知道如何將不同的紋理應用於每個模型,所以現在它們都具有相同的紋理。 我已經讀過我需要在程序中添加多個紋理單元或使用紋理圖集。 紋理圖集似乎更復雜,所以我試圖添加紋理單位。
我認為這個過程的工作方式是:
從這里開始,我想我可以使用glActiveTexture告訴openGL我想要使用哪個紋理單元。 這似乎只適用於一個紋理(即跳過步驟3),但失敗了兩個或更多。
我確定我錯過了什么,所以有人能指出我正確的方向嗎?
//Generate textures
int texturec=2;
int w[texturec],h[texturec];
unsigned char *data[texturec];
data[0]=getImage(&w[0],&h[0],"resources/a.png");
data[1]=getImage(&w[1],&h[1],"resources/b.png");
//Apply textures
GLuint textures[texturec];
glGenTextures(texturec, textures);
//Bind a.png to the first texture unit
glBindTexture(GL_TEXTURE_2D, textures[0]);
glTexImage2D(GL_TEXTURE_2D, 0,GL_RGB, w[0], h[0], 0, GL_RGB, GL_UNSIGNED_BYTE, data[0]);
//Bind b.png to the second texture unit
glBindTexture(GL_TEXTURE_2D, textures[1]);
glTexImage2D(GL_TEXTURE_2D, 0,GL_RGB, w[1], h[1], 0, GL_RGB, GL_UNSIGNED_BYTE, data[1]);
glActiveTexture(GL_TEXTURE0);
//Not super clear on what this does, but it needs to be here.
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
以下是我的着色器:
分段:
#version 330 core
in vec2 UV;
out vec3 color;
uniform sampler2D textureSampler;
void main(){
color=texture(textureSampler,UV).rgb;
}
頂點:
#version 330 core
layout(location=0) in vec3 vertexPos;
layout(location=1) in vec2 vertexUV;
out vec2 UV;
uniform mat4 MVP;
void main(){
gl_Position=MVP*vec4(vertexPos,1);
UV=vertexUV;
}
編輯:
在應用Rabid76的建議之后,這是我的新代碼:
//Generate textures
int texturec=2;
int w[texturec],h[texturec];
unsigned char *data[texturec];
data[0]=getImage(&w[0],&h[0],"resources/a.png");
data[1]=getImage(&w[1],&h[1],"resources/b.png");
//Apply textures
GLuint textures[texturec];
glGenTextures(texturec, textures);
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, textures[0]);
glTexImage2D(GL_TEXTURE_2D, 0,GL_RGB, w[0], h[0], 0, GL_RGB, GL_UNSIGNED_BYTE, data[0]);
glActiveTexture(GL_TEXTURE1);
glBindTexture(GL_TEXTURE_2D, textures[1]);
glTexImage2D(GL_TEXTURE_2D, 0,GL_RGB, w[1], h[1], 0, GL_RGB, GL_UNSIGNED_BYTE, data[1]);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
//Shaders
programID=loadShaders("shaders/vertex.shader","shaders/fragment.shader");
glUseProgram(programID);
//Use texture unit 1
glActiveTexture(GL_TEXTURE1);
GLint texLoc=glGetUniformLocation(programID, "textureSampler");
glUniform1i(texLoc, 1);
- 使用
glGenTextures
生成兩個紋理單元。
沒有glGenTextures
不會生成紋理單元。
glGenTextures
保留名稱值,可用於紋理對象。
glBindTexture
將命名紋理綁定到紋理目標。 調用此函數時,紋理對象將綁定到當前紋理單元。
當前紋理單元可以通過glActiveTexture
設置:
例如
GLuint textures[texturec];
glGenTextures(texturec, textures);
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, textures[0]);
// [...]
glActiveTexture(GL_TEXTURE1);
glBindTexture(GL_TEXTURE_2D, textures[1]);
// [...]
紋理對象名稱值和紋理單元是完全不同的東西。
紋理單元是紋理對象和着色器程序之間的綁定點。
一方面,紋理對象必須綁定到紋理單元,另一方面,紋理單元必須設置為紋理采樣器均勻。 所以紋理單元是兩者之間的“鏈接”。
從GLSL版本4.2開始,紋理單元可以通過着色器中的布局限定符(GLSL)進行設置。 綁定點對應於紋理單元。 例如, binding = 1
表示紋理單元1:
layout(binding = 1) uniform sampler2D textureSampler;
或者,可以通過glUniform1i
將紋理單元索引分配給紋理采樣器:
GLint texLoc = glGetUniformLocation(programID, "textureSampler");
glUniform1i(texLoc, 1);
如果着色器程序使用1個紋理采樣器均勻
uniform sampler2D textureSampler;
那么在繪制調用之前綁定適當的紋理對象就足夠了:
glActiveTexture(GL_TEXTURE0); // this is default
glBindTexture(GL_TEXTURE_2D, textures[0]);
但是如果着色器程序使用多個紋理采樣器制服(相同目標),則不同的紋理對象必須綁定到不同的紋理單元:
例如
layout(binding = 3) uniform sampler2D textureSampler1;
layout(binding = 4) uniform sampler2D textureSampler2;
glActiveTexture(GL_TEXTURE3);
glBindTexture(GL_TEXTURE_2D, textures[0]);
glActiveTexture(GL_TEXTURE4);
glBindTexture(GL_TEXTURE_2D, textures[1]);
分別
layout(location = 7) uniform sampler2D textureSampler1;
layout(location = 8) uniform sampler2D textureSampler2;
glActiveTexture(GL_TEXTURE3);
glBindTexture(GL_TEXTURE_2D, textures[0]);
glActiveTexture(GL_TEXTURE4);
glBindTexture(GL_TEXTURE_2D, textures[1]);
glUseProgram(programID);
glUniform1i(7, 3); // location = 7 <- texture unit 3
glUniform1i(8, 4); // location = 8 <- texture unit 4
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.