我目前正试图使用OpenGL superbible和http://www.learnopengl.com/进入GLSL。我想要的环境是OpenTK。
我尝试转换" Hello Triangle"从learnopengl.com到OpenTK的入门级教程,它意味着使用非常简单的着色器绘制三角形,而不使用任何透视/世界/模型转换。
我的结果只是颜色缓冲,但是一个空窗口,我根本不明白我在哪里犯了错误,所以任何寻找帮助,更重要的是理解它们都会非常感激。
我的OpenTK代码:
using System;
using System.Drawing;
using System.Drawing.Imaging;
using System.IO;
using OpenTK;
using OpenTK.Graphics.OpenGL;
using OpenTK.Input;
namespace learnopengl.HelloTriangle
{
public class MainWindow : GameWindow
{
int _shaderId;
int _vao;
int _glbuf;
int _fragObj;
int _vertexObj;
Vector3[] _triangleVert;
public MainWindow()
: base(800,600)
{
KeyDown += MainWindow_KeyDown;
_triangleVert = new Vector3[] {
new Vector3(-0.5f, -0.5f, 0.0f),
new Vector3(0.5f, -0.5f, 0.0f),
new Vector3(-0.5f, 0.5f, 0.0f)
};
}
void MainWindow_KeyDown(object sender, KeyboardKeyEventArgs e)
{
if (e.Key == Key.Escape)
this.Exit();
if (e.Key == Key.F11)
if (this.WindowState == WindowState.Fullscreen)
this.WindowState = WindowState.Normal;
else
this.WindowState = WindowState.Fullscreen;
}
protected override void OnLoad(EventArgs e)
{
base.OnLoad(e);
System.Diagnostics.Trace.WriteLine(string.Format("OpenGL version: {0}", GL.GetString(StringName.Version)));
GL.ClearColor(Color.Purple);
_vertexObj = GL.CreateShader(ShaderType.VertexShader);
_fragObj = GL.CreateShader(ShaderType.FragmentShader);
int statusCode;
string info;
GL.ShaderSource(_vertexObj, File.ReadAllText(@"shader\triangle.vert"));
GL.CompileShader(_vertexObj);
info = GL.GetShaderInfoLog(_vertexObj);
Console.Write(string.Format("triangle.vert compile: {0}",info));
GL.GetShader(_vertexObj, ShaderParameter.CompileStatus, out statusCode);
if (statusCode != 1) throw new ApplicationException(info);
GL.ShaderSource(_fragObj, File.ReadAllText(@"shader\triangle.frag"));
GL.CompileShader(_fragObj);
info = GL.GetShaderInfoLog(_fragObj);
Console.Write(string.Format("triangle.frag compile: {0}", info));
GL.GetShader(_fragObj, ShaderParameter.CompileStatus, out statusCode);
if (statusCode != 1) throw new ApplicationException(info);
_shaderId = GL.CreateProgram();
GL.AttachShader(_shaderId, _fragObj);
GL.AttachShader(_shaderId, _vertexObj);
GL.LinkProgram(_shaderId);
Console.Write(string.Format("link program: {0}", GL.GetProgramInfoLog(_shaderId)));
GL.UseProgram(_shaderId);
Console.Write(string.Format("use program: {0}", GL.GetProgramInfoLog(_shaderId)));
_vao = GL.GenVertexArray();
_glbuf = GL.GenBuffer();
GL.BindVertexArray(_vao);
GL.BindBuffer(BufferTarget.ArrayBuffer, _glbuf);
GL.BufferData<Vector3>(BufferTarget.ArrayBuffer, new IntPtr(Vector3.SizeInBytes * _triangleVert.Length), _triangleVert, BufferUsageHint.StaticDraw);
GL.VertexAttribPointer(0, 3, VertexAttribPointerType.Float, false, Vector3.SizeInBytes * _triangleVert.Length, 0);
GL.EnableVertexAttribArray(0);
GL.BindVertexArray(0);
}
protected override void OnResize(EventArgs e)
{
GL.Viewport(0, 0, Width, Height);
}
protected override void OnRenderFrame(FrameEventArgs e)
{
GL.Clear(ClearBufferMask.ColorBufferBit);
GL.BindVertexArray(_vao);
GL.DrawArrays(PrimitiveType.Triangles, 0, 3);
GL.BindVertexArray(0);
this.SwapBuffers();
}
protected override void OnUnload(EventArgs e)
{
GL.DeleteProgram(_shaderId);
GL.DeleteShader(_vertexObj);
GL.DeleteShader(_fragObj);
GL.DeleteVertexArray(_vao);
GL.DeleteBuffer(_glbuf);
base.OnClosed(e);
}
}
}
triangle.vert:
#version 330 core
layout(location = 0) in vec3 position;
void main()
{
gl_Position = vec4(position.x, position.y, position.z, 1.0f);
}
triangle.frag:
#version 330 core
//out vec4 color;
void main()
{
gl_FragColor = vec4(1.0f, 0.0f, 0.0f, 1.0f);
//color = vec4(1.0f, 0.0f, 0.0f, 1.0f);
}
编辑: 使用评论中的建议更新了代码,这些建议不会改变结果。
EDIT2: 我从链接/使用着色器添加了Info日志,并将所有信息日志重新路由到控制台。我得到一些可以忽略的警告。
如果我从所有着色器中删除float后缀,我还测试了是否发生了任何更改,但一切都保持不变。
答案 0 :(得分:3)
终于找到了问题的答案:
GL.VertexAttribPointer(0, 3, VertexAttribPointerType.Float, false, Vector3.SizeInBytes * _triangleVert.Length, 0);
第五个参数仅用于指定单个属性的大小,而不是整个数组:
GL.VertexAttribPointer(0, 3, VertexAttribPointerType.Float, false, Vector3.SizeInBytes, 0);
现在它可以正常工作,感谢所有有用的评论!