我是OpenGL的新手,我一直在解决纹理错位/拉伸的问题。纹理大小为256x256,类型为png。
左边是一个四边形,有2个三角形,纹理正确, 在右边是一个自定义平面,有16个四边形全部三角形。
从图片中可以看出,即使我应该正确分配了所有的UV,纹理也不能正确贴合在脸部。
这是所有顶点,UV以及面如何形成的图片。 (在新标签中打开以获得更大的图片):
以下是我如何开始使用我的OpenGL视图的代码片段:
public void Start(){
Glut.glutInit();
Glut.glutInitDisplayMode(Glut.GLUT_DOUBLE | Glut.GLUT_DEPTH);
Glut.glutInitWindowSize(_width, _height);
Glut.glutCreateWindow("OpenGL View");
//Gl.ReloadFunctions();
texture = new Texture("water.png");
//Define functions
Glut.glutIdleFunc(OnRenderFrame);
Glut.glutDisplayFunc(OnDisplay);
Glut.glutMouseFunc(OnMouse);
Glut.glutMotionFunc(OnMove);
Glut.glutCloseFunc(OnClose);
program = new ShaderProgram(VertexShader, FragmentShader);
program["projection_matrix"].SetValue(Matrix4.CreatePerspectiveFieldOfView(0.45f,
(float)_width / _height, 0.1f, 1000f));
program.Use();
Glut.glutSetOption(Glut.GLUT_ACTION_ON_WINDOW_CLOSE, Glut.GLUT_ACTION_CONTINUE_EXECUTION);
Glut.glutMainLoop();
}
private static void OnRenderFrame()
{
Gl.Viewport(0, 0, _width, _height);
Gl.Clear(ClearBufferMask.ColorBufferBit | ClearBufferMask.DepthBufferBit);
Gl.UseProgram(program);
Gl.Enable(EnableCap.Texture2D);
Gl.BindTexture(texture);
Matrix4 transform = Matrix4.CreateRotationY(yangle) * Matrix4.CreateRotationX(xangle)
* Matrix4.CreateTranslation(translationVector);
program["model_matrix"].SetValue(transform);
program["view_matrix"].SetValue(Matrix4.LookAt(
new Vector3(0, 0, viewZoom), Vector3.Zero,Vector3.Up));
//Bind Vertices and Vertex indices
Gl.BindBufferToShaderAttribute(_model, program, "vertexPosition");
Gl.BindBufferToShaderAttribute(_modelUV, program, "vertexUV");
Gl.BindBuffer(_model);
Gl.BindBuffer(_modelFaces);
Gl.DrawElements(BeginMode.Triangles, _modelFaces.Count, DrawElementsType.UnsignedInt,
IntPtr.Zero);
Glut.glutSwapBuffers();
}
public static string VertexShader = @"
in vec3 vertexPosition;
in vec2 vertexUV;
out vec2 uv;
uniform mat4 projection_matrix;
uniform mat4 view_matrix;
uniform mat4 model_matrix;
void main(void)
{
gl_Position = projection_matrix * view_matrix * model_matrix * vec4(vertexPosition,1);
uv = vertexUV;
}
";
public static string FragmentShader = @"
uniform sampler2D texture;
in vec2 uv;
out vec4 fragment;
void main(void)
{
fragment = texture2D(texture, uv);
}
";
我似乎无法确定问题,UV看起来都很好,即使它们不正确,它们也不应该拉伸并重复纹理,因为它们在0和1的范围内。 / p>
答案 0 :(得分:0)
问题在于我将UV分配给视频卡的内存。
这就是我加载模型的方式:
public void SetModel(Vector3[] modelVertices, int[] modelFaces, Vector2[] modelUV)
{
_model = new VBO<Vector3>(modelVertices);
_modelFaces = new VBO<int>(modelFaces, BufferTarget.ElementArrayBuffer);
_modelUV = new VBO<Vector2>(modelUV, BufferTarget.TextureBuffer);
}
这就是它应该如何:
public void SetModel(Vector3[] modelVertices, int[] modelFaces, Vector2[] modelUV)
{
_model = new VBO<Vector3>(modelVertices);
_modelFaces = new VBO<int>(modelFaces, BufferTarget.ElementArrayBuffer);
_modelUV = new VBO<Vector2>(modelUV);
}
当我在TextureBuffer中使用BufferTarget将向量分配给VBO时,它会翻转出来。解决方法是删除参数,以便BufferTarget默认为ArrayBuffer。
我还通过删除无顶点的顶点来编辑我的渲染功能:
private static void OnRenderFrame()
{
Gl.Clear(ClearBufferMask.ColorBufferBit | ClearBufferMask.DepthBufferBit);
Gl.UseProgram(program);
Matrix4 transform = Matrix4.CreateRotationY(yangle) * Matrix4.CreateRotationX(xangle)
* Matrix4.CreateTranslation(translationVector);
Gl.BindTexture(texture);
program["model_matrix"].SetValue(transform);
program["view_matrix"].SetValue(Matrix4.LookAt(
new Vector3(0, 0, viewZoom), Vector3.Zero,Vector3.Up));
Gl.BindBufferToShaderAttribute(_model, program, "vertexPosition");
Gl.BindBufferToShaderAttribute(_modelUV, program, "vertexUV");
Gl.BindBuffer(_modelFaces);
Gl.DrawElements(BeginMode.Triangles, _modelFaces.Count, DrawElementsType.UnsignedInt,
IntPtr.Zero);
Glut.glutSwapBuffers();
}