OpenGL 将打包的纹理坐标传递给着色器
OpenGL pass packed texture coordinates to the shader
我需要在我的游戏中做一些大量的优化,我在想既然我们可以将 vec4 颜色传递给打包成一个浮点数的着色器,有没有办法也传递 vec2 纹理坐标?例如,在下面的代码中,我可以将 2 个纹理坐标(它始终为 1 和 0)作为一个元素传递,就像它在颜色元素中发生的方式一样。
public void point(float x,float y,float z,float size,float color){
float hsize=size/2;
if(index>vertices.length-7)return;
vertices[index++]=x-hsize;
vertices[index++]=y-hsize;
vertices[index++]=color;
vertices[index++]=0;
vertices[index++]=0;
vertices[index++]=x+hsize;
vertices[index++]=y-hsize;
vertices[index++]=color;
vertices[index++]=1;
vertices[index++]=0;
vertices[index++]=x+hsize;
vertices[index++]=y+hsize;
vertices[index++]=color;
vertices[index++]=1;
vertices[index++]=1;
vertices[index++]=x-hsize;
vertices[index++]=y+hsize;
vertices[index++]=color;
vertices[index++]=0;
vertices[index++]=1;
num++;
}
{
mesh=new Mesh(false,COUNT*20, indices.length,
new VertexAttribute(Usage.Position, 2,"a_position"),
new VertexAttribute(Usage.ColorPacked, 4,"a_color"),
new VertexAttribute(Usage.TextureCoordinates, 2,"a_texCoord0")
);
}
片段着色器
varying vec4 v_color;
varying vec2 v_texCoords;
uniform sampler2D u_texture;
void main() {
vec4 color=v_color * texture2D(u_texture, v_texCoords);
gl_FragColor = color;
}
垂直着色器
attribute vec4 a_position;
attribute vec4 a_color;
attribute vec2 a_texCoord0;
uniform mat4 u_projTrans;
varying vec4 v_color;
varying vec2 v_texCoords;
void main() {
v_color = a_color;
v_texCoords = a_texCoord0;
gl_Position = u_projTrans * a_position;
}
我知道这不会对性能产生太大影响,但我只是愿意在这里和那里多花一些时间来进行一些小的优化,以使我的游戏 运行 更快。
我还没有尝试过,但我认为它会起作用。只需使用 Usage.ColorPacked
作为您的纹理坐标。我不认为你可以发送小于 4 字节的任何东西,所以你也可以使用已经定义的打包颜色。您只会为每个顶点保存一个字节。你可以把你的坐标放在前两个元素里,忽略后两个元素。
mesh = new Mesh(false,COUNT*20, indices.length,
new VertexAttribute(Usage.Position, 2,"a_position"),
new VertexAttribute(Usage.ColorPacked, 4,"a_color"),
new VertexAttribute(Usage.ColorPacked, 4,"a_texCoord0")
);
我不认为 VertexAttribute 的 usage
参数实际上被 Libgdx 中的任何东西使用。如果您查看源代码,它只会检查 usage
是否为 ColorPacked,并据此决定每个组件是使用单个字节还是使用 4 个字节。
在你的顶点着色器中:
attribute vec4 a_position;
attribute vec4 a_color;
attribute vec4 a_texCoord0; //note using vec4
uniform mat4 u_projTrans;
varying vec4 v_color;
varying vec2 v_texCoords;
void main() {
v_color = a_color;
v_texCoords = a_texCoord0.xy; //using the first two elements
gl_Position = u_projTrans * a_position;
}
要正确转换纹理坐标:
final Color texCoordColor = new Color(0, 0, 0, 0);
//....
texCoordColor.r = texCoord.x;
texCoordColor.g = texCoord.y;
float texCoord = texCoordColor.toFloatBits();
我需要在我的游戏中做一些大量的优化,我在想既然我们可以将 vec4 颜色传递给打包成一个浮点数的着色器,有没有办法也传递 vec2 纹理坐标?例如,在下面的代码中,我可以将 2 个纹理坐标(它始终为 1 和 0)作为一个元素传递,就像它在颜色元素中发生的方式一样。
public void point(float x,float y,float z,float size,float color){
float hsize=size/2;
if(index>vertices.length-7)return;
vertices[index++]=x-hsize;
vertices[index++]=y-hsize;
vertices[index++]=color;
vertices[index++]=0;
vertices[index++]=0;
vertices[index++]=x+hsize;
vertices[index++]=y-hsize;
vertices[index++]=color;
vertices[index++]=1;
vertices[index++]=0;
vertices[index++]=x+hsize;
vertices[index++]=y+hsize;
vertices[index++]=color;
vertices[index++]=1;
vertices[index++]=1;
vertices[index++]=x-hsize;
vertices[index++]=y+hsize;
vertices[index++]=color;
vertices[index++]=0;
vertices[index++]=1;
num++;
}
{
mesh=new Mesh(false,COUNT*20, indices.length,
new VertexAttribute(Usage.Position, 2,"a_position"),
new VertexAttribute(Usage.ColorPacked, 4,"a_color"),
new VertexAttribute(Usage.TextureCoordinates, 2,"a_texCoord0")
);
}
片段着色器
varying vec4 v_color;
varying vec2 v_texCoords;
uniform sampler2D u_texture;
void main() {
vec4 color=v_color * texture2D(u_texture, v_texCoords);
gl_FragColor = color;
}
垂直着色器
attribute vec4 a_position;
attribute vec4 a_color;
attribute vec2 a_texCoord0;
uniform mat4 u_projTrans;
varying vec4 v_color;
varying vec2 v_texCoords;
void main() {
v_color = a_color;
v_texCoords = a_texCoord0;
gl_Position = u_projTrans * a_position;
}
我知道这不会对性能产生太大影响,但我只是愿意在这里和那里多花一些时间来进行一些小的优化,以使我的游戏 运行 更快。
我还没有尝试过,但我认为它会起作用。只需使用 Usage.ColorPacked
作为您的纹理坐标。我不认为你可以发送小于 4 字节的任何东西,所以你也可以使用已经定义的打包颜色。您只会为每个顶点保存一个字节。你可以把你的坐标放在前两个元素里,忽略后两个元素。
mesh = new Mesh(false,COUNT*20, indices.length,
new VertexAttribute(Usage.Position, 2,"a_position"),
new VertexAttribute(Usage.ColorPacked, 4,"a_color"),
new VertexAttribute(Usage.ColorPacked, 4,"a_texCoord0")
);
我不认为 VertexAttribute 的 usage
参数实际上被 Libgdx 中的任何东西使用。如果您查看源代码,它只会检查 usage
是否为 ColorPacked,并据此决定每个组件是使用单个字节还是使用 4 个字节。
在你的顶点着色器中:
attribute vec4 a_position;
attribute vec4 a_color;
attribute vec4 a_texCoord0; //note using vec4
uniform mat4 u_projTrans;
varying vec4 v_color;
varying vec2 v_texCoords;
void main() {
v_color = a_color;
v_texCoords = a_texCoord0.xy; //using the first two elements
gl_Position = u_projTrans * a_position;
}
要正确转换纹理坐标:
final Color texCoordColor = new Color(0, 0, 0, 0);
//....
texCoordColor.r = texCoord.x;
texCoordColor.g = texCoord.y;
float texCoord = texCoordColor.toFloatBits();