Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/127.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/opengl/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 圆环体的纹理应用不正确_C++_Opengl_Textures_Opengl Compat - Fatal编程技术网

C++ 圆环体的纹理应用不正确

C++ 圆环体的纹理应用不正确,c++,opengl,textures,opengl-compat,C++,Opengl,Textures,Opengl Compat,我正在创建一个带有6个圆环的开放式GL程序。当我应用纹理时,它以一种颜色显示。即使它不是单一的颜色 我正在从阵列中获取图像。除圆环纹理外,其他纹理(天空盒、行星、HUD)正在正确应用。我也尝试使用光源,但没有成功。有人能帮我做到这一点吗 下面是我的代码 glPushMatrix(); glEnable(GL_TEXTURE_2D); glTranslatef(xpos, ypos, zpos);

我正在创建一个带有6个圆环的开放式GL程序。当我应用纹理时,它以一种颜色显示。即使它不是单一的颜色

我正在从阵列中获取图像。除圆环纹理外,其他纹理(天空盒、行星、HUD)正在正确应用。我也尝试使用光源,但没有成功。有人能帮我做到这一点吗

下面是我的代码

                glPushMatrix();
                glEnable(GL_TEXTURE_2D);
                glTranslatef(xpos, ypos, zpos);
                glRotatef(fPlanetRot, 0.0f, -1.0f, 0.0f);
                glColor3f(0.0, 0.0, 0.0);

                // Select the texture object
                glBindTexture(GL_TEXTURE_2D, textures[3]);

                glutSolidTorus(0.1, 1.0, 30, 30);
                glDisable(GL_TEXTURE_2D);
                glPopMatrix();

//This is where I load the texture

void SetupRC()
{
    //textures

    GLuint texture;
    // allocate a texture name
    glGenTextures( 1, &texture );
    glPixelStorei(GL_UNPACK_ALIGNMENT,1);

    //there are quite a few ways of loading images
    // Load textures in a for loop
    glGenTextures(TEXTURE_COUNT, textures);
    //this puts the texture into OpenGL texture memory
 //   glTexParameteri(GL_TEXTURE_2D, GL_GENERATE_MIPMAP, GL_TRUE); - not defined so probably need to update GLEW - not needed here so ignore
    for(int iLoop = 0; iLoop < TEXTURE_COUNT; iLoop++)
    {
        // Bind to next texture object
        glBindTexture(GL_TEXTURE_2D, textures[iLoop]);
        
        // Load texture data, set filter and wrap modes
        //note that gltLoadTGA is in the glm.cpp file and not a built-in openGL function
        pBytes0 = gltLoadTGA(textureFiles[iLoop],&iWidth, &iHeight,
                             &iComponents, &eFormat);
        
        glTexImage2D(GL_TEXTURE_2D, 0, iComponents, iWidth, iHeight, 0, eFormat, GL_UNSIGNED_BYTE, pBytes0);
        
            //set up texture parameters
        
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
         glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
        //try these too
        glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_ADD);
         glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
        free(pBytes0);
    }
    
    //enable textures
    glEnable(GL_TEXTURE_2D);

    
    glEnable(GL_DEPTH_TEST);    // Hidden surface removal    
    glFrontFace(GL_CCW);// Counter clock-wise polygons face out
    glEnable(GL_CULL_FACE);     // Do not calculate inside

//    glCullFace(GL_FRONT_AND_BACK);
    
    // Enable lighting
    glEnable(GL_LIGHTING);
    glEnable(GL_POINT_SMOOTH);
    // Setup and enable light 0
    glLightModelfv(GL_LIGHT_MODEL_AMBIENT,whiteLightLessBright);
    glLightfv(GL_LIGHT0,GL_DIFFUSE,redLight);
    glLightfv(GL_LIGHT0,GL_POSITION,lightPos);
    glEnable(GL_LIGHT0);

    // Enable colour tracking
    glEnable(GL_COLOR_MATERIAL);
    
    // Set Material properties to follow glColor values
    glColorMaterial(GL_FRONT, GL_AMBIENT_AND_DIFFUSE);
    
    // Black blue background
    glClearColor(0.0f, 0.0f, 0.03f, 1.0f );
}
glPushMatrix();
glEnable(GL_纹理_2D);
GLTRANSTEF(XPO、YPO、zpos);
glRotatef(fPlanetRot,0.0f,-1.0f,0.0f);
GL3F(0.0,0.0,0.0);
//选择纹理对象
glBindTexture(GL_TEXTURE_2D,纹理[3]);
固形环(0.1,1.0,30,30);
glDisable(GL_纹理_2D);
glPopMatrix();
//这是我加载纹理的地方
void SetupRC()
{
//质地
胶合结构;
//分配纹理名称
glGenTextures(1,&纹理);
glPixelStorei(GLU解包对齐,1);
//加载图像的方法有很多种
//在for循环中加载纹理
glGenTextures(纹理数量、纹理);
//这会将纹理放入OpenGL纹理内存中
//glTexParameteri(GL_纹理_2D,GL_生成_MIPMAP,GL_真);-未定义,因此可能需要更新GLEW-此处不需要,因此忽略
对于(int-iLoop=0;iLoop
简而言之:

glutSolidTorus()
只是不为圆环体发射纹理坐标,而只发射坐标和逐顶点法线

长话短说:

出于好奇,我在谷歌上搜索了一下,我相信我找到了对OPs观察的解释

除圆环纹理外,其他纹理(天空盒、行星、HUD)正在正确应用

首先我看了一下医生。但我找不到任何关于纹理坐标是否受支持的提示。我尝试了一些其他的文档,但大多数都是这个文档的副本,或者没有提到纹理

下一步,我试图找到“glutSolidTorus纹理”的样本图像,但我找不到

非常可疑

因此,我终于了解了github上的源代码:

void APIENTRY
glutSolidTorus(GLdouble innerRadius, GLdouble outerRadius,
  GLint nsides, GLint rings)
{
  doughnut(innerRadius, outerRadius, nsides, rings);
}
该函数在同一源文件中定义:

static void
doughnut(GLfloat r, GLfloat R, GLint nsides, GLint rings)
{
  int i, j;
  GLfloat theta, phi, theta1;
  GLfloat cosTheta, sinTheta;
  GLfloat cosTheta1, sinTheta1;
  GLfloat ringDelta, sideDelta;

  ringDelta = 2.0 * M_PI / rings;
  sideDelta = 2.0 * M_PI / nsides;

  theta = 0.0;
  cosTheta = 1.0;
  sinTheta = 0.0;
  for (i = rings - 1; i >= 0; i--) {
    theta1 = theta + ringDelta;
    cosTheta1 = cos(theta1);
    sinTheta1 = sin(theta1);
    glBegin(GL_QUAD_STRIP);
    phi = 0.0;
    for (j = nsides; j >= 0; j--) {
      GLfloat cosPhi, sinPhi, dist;

      phi += sideDelta;
      cosPhi = cos(phi);
      sinPhi = sin(phi);
      dist = R + r * cosPhi;

      glNormal3f(cosTheta1 * cosPhi, -sinTheta1 * cosPhi, sinPhi);
      glVertex3f(cosTheta1 * dist, -sinTheta1 * dist, r * sinPhi);
      glNormal3f(cosTheta * cosPhi, -sinTheta * cosPhi, sinPhi);
      glVertex3f(cosTheta * dist, -sinTheta * dist,  r * sinPhi);
    }
    glEnd();
    theta = theta1;
    cosTheta = cosTheta1;
    sinTheta = sinTheta1;
  }
}
void APIENTRY
glutSolidSphere(GLdouble radius, GLint slices, GLint stacks)
{
  QUAD_OBJ_INIT();
  gluQuadricDrawStyle(quadObj, GLU_FILL);
  gluQuadricNormals(quadObj, GLU_SMOOTH);
  /* If we ever changed/used the texture or orientation state
     of quadObj, we'd need to change it to the defaults here
     with gluQuadricTexture and/or gluQuadricOrientation. */
  gluSphere(quadObj, radius, slices, stacks);
}
答案很简单也很明显–
glutSolidTorus()
只是不为环面发射纹理坐标,而只发射坐标和逐顶点法线。因此,所有像素从一开始就具有相同且唯一的纹理坐标。这将产生一个颜色均匀的圆环体(如OP观察到的)

那么,当
glutSolidTorus()
不支持纹理时,例如为什么?答案在同一源文件中给出:

static void
doughnut(GLfloat r, GLfloat R, GLint nsides, GLint rings)
{
  int i, j;
  GLfloat theta, phi, theta1;
  GLfloat cosTheta, sinTheta;
  GLfloat cosTheta1, sinTheta1;
  GLfloat ringDelta, sideDelta;

  ringDelta = 2.0 * M_PI / rings;
  sideDelta = 2.0 * M_PI / nsides;

  theta = 0.0;
  cosTheta = 1.0;
  sinTheta = 0.0;
  for (i = rings - 1; i >= 0; i--) {
    theta1 = theta + ringDelta;
    cosTheta1 = cos(theta1);
    sinTheta1 = sin(theta1);
    glBegin(GL_QUAD_STRIP);
    phi = 0.0;
    for (j = nsides; j >= 0; j--) {
      GLfloat cosPhi, sinPhi, dist;

      phi += sideDelta;
      cosPhi = cos(phi);
      sinPhi = sin(phi);
      dist = R + r * cosPhi;

      glNormal3f(cosTheta1 * cosPhi, -sinTheta1 * cosPhi, sinPhi);
      glVertex3f(cosTheta1 * dist, -sinTheta1 * dist, r * sinPhi);
      glNormal3f(cosTheta * cosPhi, -sinTheta * cosPhi, sinPhi);
      glVertex3f(cosTheta * dist, -sinTheta * dist,  r * sinPhi);
    }
    glEnd();
    theta = theta1;
    cosTheta = cosTheta1;
    sinTheta = sinTheta1;
  }
}
void APIENTRY
glutSolidSphere(GLdouble radius, GLint slices, GLint stacks)
{
  QUAD_OBJ_INIT();
  gluQuadricDrawStyle(quadObj, GLU_FILL);
  gluQuadricNormals(quadObj, GLU_SMOOTH);
  /* If we ever changed/used the texture or orientation state
     of quadObj, we'd need to change it to the defaults here
     with gluQuadricTexture and/or gluQuadricOrientation. */
  gluSphere(quadObj, radius, slices, stacks);
}
也就是说,
glutSolidSphere()
只是
glutsphere()
的包装。医生。明确提到纹理:

如果启用了纹理(使用GluQuadractTexture),则生成纹理坐标,使t的范围从z=半径处的0.0到z=半径处的1.0(t沿纵线线性增加),s的范围从+y轴处的0.0到+x轴处的0.25到-y轴处的0.5到-x轴处的0.75,然后在+y轴返回到1.0


如果OP想要有一个纹理环面,那么必须用一个发出纹理坐标的自定义版本替换
glutSolidTorus()
。 对于给定的源代码,扩展函数resp应该不会太难。 (请不要忘记给它一个新名称,以防止重复定义symbol
glutSolidTorus()
…)时出现链接错误)


我后来找到的有用链接:


  • (可能重复,但
    [已关闭]

谢谢@Scheff的回答。我遵循了你的第二个链接,能够将纹理应用于圆环+1