C# OpenGL试图绘制多个2d纹理,但只显示第一个纹理
我有一个问题,我试图用纹理(每个行星一个纹理)绘制太阳系,当我绘制纹理时,只有第一个出现。其余的都没有 我的init函数遍历我的文件,将纹理保存到对象中,然后遍历对象。在迭代过程中,它生成纹理并使用OpenGL调用将其绑定到名称C# OpenGL试图绘制多个2d纹理,但只显示第一个纹理,c#,wpf,opengl,textures,C#,Wpf,Opengl,Textures,我有一个问题,我试图用纹理(每个行星一个纹理)绘制太阳系,当我绘制纹理时,只有第一个出现。其余的都没有 我的init函数遍历我的文件,将纹理保存到对象中,然后遍历对象。在迭代过程中,它生成纹理并使用OpenGL调用将其绑定到名称 SharpGL.OpenGL gl = args.OpenGL; gl.Enable(SharpGL.OpenGL.GL_BLEND); gl.Enable(SharpGL.OpenGL.GL_TEXTURE_2D);
SharpGL.OpenGL gl = args.OpenGL;
gl.Enable(SharpGL.OpenGL.GL_BLEND);
gl.Enable(SharpGL.OpenGL.GL_TEXTURE_2D);
gl.BlendFunc(SharpGL.Enumerations.BlendingSourceFactor.SourceAlpha, SharpGL.Enumerations.BlendingDestinationFactor.OneMinusSourceAlpha);
gl.ClearColor(0, 0, 0, 1);
foreach (ImageWrapper iw in m_images)
{
uint[] texNames = new uint[1];
gl.GenTextures(1, texNames);
gl.BindTexture(SharpGL.OpenGL.GL_TEXTURE_2D, texNames[0]);
gl.TexParameter(SharpGL.OpenGL.GL_TEXTURE_2D, SharpGL.OpenGL.GL_TEXTURE_WRAP_S, SharpGL.OpenGL.GL_REPEAT);
gl.TexParameter(SharpGL.OpenGL.GL_TEXTURE_2D, SharpGL.OpenGL.GL_TEXTURE_WRAP_T, SharpGL.OpenGL.GL_REPEAT);
gl.TexParameter(SharpGL.OpenGL.GL_TEXTURE_2D, SharpGL.OpenGL.GL_TEXTURE_MAG_FILTER, SharpGL.OpenGL.GL_LINEAR);
gl.TexParameter(SharpGL.OpenGL.GL_TEXTURE_2D, SharpGL.OpenGL.GL_TEXTURE_MIN_FILTER, SharpGL.OpenGL.GL_LINEAR);
gl.TexImage2D(SharpGL.OpenGL.GL_TEXTURE_2D,
0,
3,
iw.BitmapSource.PixelWidth,
iw.BitmapSource.PixelHeight,
0,
SharpGL.OpenGL.GL_BGRA,
SharpGL.OpenGL.GL_UNSIGNED_BYTE,
iw.Pixels);
iw.TextureHandle = texNames;
}
这是我的函数,它绘制了所有内容。我遍历所有包含纹理数据的对象,并尝试一次绘制一个。我还想执行一些旋转和变换,让我的太阳系旋转。该部分适用于显示的纹理
SharpGL.OpenGL gl = args.OpenGL;
gl.Clear(SharpGL.OpenGL.GL_COLOR_BUFFER_BIT | SharpGL.OpenGL.GL_DEPTH_BUFFER_BIT );
gl.LoadIdentity();
float[] data = new float[4];
foreach (ImageWrapper iw in m_images)
{
//gl.MatrixMode(SharpGL.Enumerations.MatrixMode.Modelview);
gl.Ortho2D(0, this.Width, 0, this.Height);
gl.Enable(OpenGL.GL_TEXTURE_2D);
gl.BindTexture(OpenGL.GL_TEXTURE_2D, iw.TextureHandle[0]);
gl.TexParameter(SharpGL.OpenGL.GL_TEXTURE_2D, SharpGL.OpenGL.GL_TEXTURE_WRAP_S, SharpGL.OpenGL.GL_REPEAT);
gl.TexParameter(SharpGL.OpenGL.GL_TEXTURE_2D, SharpGL.OpenGL.GL_TEXTURE_WRAP_T, SharpGL.OpenGL.GL_REPEAT);
gl.TexParameter(SharpGL.OpenGL.GL_TEXTURE_2D, SharpGL.OpenGL.GL_TEXTURE_MAG_FILTER, SharpGL.OpenGL.GL_LINEAR);
gl.TexParameter(SharpGL.OpenGL.GL_TEXTURE_2D, SharpGL.OpenGL.GL_TEXTURE_MIN_FILTER, SharpGL.OpenGL.GL_LINEAR);
gl.PushMatrix();
//gl.Translate(this.Width / 2, this.Height / 2, 0);
//gl.Rotate(iw.RotationAboutSun, 0, 0, 1);
//gl.Translate(iw.X + 1 * this.Width / 2, iw.Y + 1 * this.Height / 2, 0);
gl.Translate(32,32, 0);
//gl.Rotate(iw.RotationAboutAxis, 0, 0, 1);
//
gl.Begin(SharpGL.Enumerations.BeginMode.Quads);
gl.Color(new float[] { 1f,1f,1f});
gl.TexCoord(0,0);
gl.Vertex(new double[] { 0 - iw.PixelWidth / 2, 0 - iw.PixelHeight / 2});
gl.TexCoord(0,1);
gl.Vertex(new double[] { 32 - iw.PixelWidth / 2, 0 - iw.PixelHeight / 2 });
gl.TexCoord(1,1);
gl.Vertex(new double[] { 32 - iw.PixelWidth / 2, 32 - iw.PixelHeight / 2 });
gl.TexCoord(1,0);
gl.Vertex(new double[] { 0 - iw.PixelWidth / 2, 32 - iw.PixelHeight / 2 });
gl.End();
gl.PopMatrix();
gl.Disable(OpenGL.GL_TEXTURE_2D);
}
我正在使用C#中的SharpGL库来实现这一点。gluOrtho2D()
不像您所期望的那样发出glLoadIdentity()
通常,每帧只设置一次投影矩阵
试着这样做:
void DrawFrame()
{
...
glMatrixMode( GL_PROJECTION );
glLoadIdentity();
gluOrtho2D(0, this.Width, 0, this.Height);
glMatrixMode( GL_MODELVIEW );
glLoadIdentity();
// "camera" transform(s)
foreach object
{
glPushMatrix();
// per-object matrix transform(s)
// draw object
glPopMatrix();
}
}
只是必须处理这个问题,所以我想我也应该插手。
我看到了被接受的答案,在我的例子中,我正确地重置了管道中的所有内容。在我的管道中,我需要渲染3D和2D对象。对于三维对象,我将切换到三维投影/模型视图,对于二维对象,我将切换到正交投影 但是,当我想要渲染两个文本块(使用四边形和纹理)时,只渲染第一个纹理。深度测试是我问题的根源。所以我修改了上面的代码以适应我的情况
void DrawFrame()
{
foreach object
{
drawObject(); // Is an abstract method
}
}
void _3DObject::drawObject() {
switchTo3D();
// Camera transform
glPushMatrix();
.
. // Draw
.
.glPopMatrix();
}
void _2DObject::drawObject() {
switchTo2D();
// Having depth testing enabled was causing
// problems when rendering textured quads.
glDisable(GL_DEPTH_TEST);
// Camera transform
glPushMatrix();
.
. // Draw
.
.glPopMatrix();
glEnable(GL_DEPTH_TEST);
}
注:“Just”指的是一个月前!不知道为什么我忘了早点发布这个答案:(我没有看到任何不好的地方。你确定m_图像中所有元素的像素成员都正确填充了吗?是的,我刚检查过。看起来没问题。好像你忘了呼叫。他们需要在纹理绑定之前被呼叫。嘻哈万岁!成功了!@mj:很高兴这是一个简单的修复:)@genpfault:只是吹毛求疵,你在每次渲染过程中设置一次投影矩阵,即一次用于3D场景,一次用于HUD等等。@datenwolf为什么在一帧中多次设置投影矩阵是一种不好的做法?如果你想绘制一些2D素材,然后是3D素材,然后是其他应该出现在t上的2D素材,这难道不是必要的吗@M2X:我从来没有说过,多次设置都是不好的做法。相反,我是OpenGL状态设置的支持者之一,只要有必要,就设置OpenGL状态,以确保你不会在没有确定的状态下绊倒。使用现代OpenGL,你无论如何都必须为每个着色器程序设置制服。