Texture 3D OpenGL

He,

Using OpenGL with C++, I am trying to add textures to spheres (nodes) of an Oriented Graph.

The spheres are located in a 3D plane and zoom in, zoom out and rotate depending on mouse movements.

It turns out that the spheres are colored with the color of the texture but they do not show the complete texture (which contains the name of the node or another image).

I put the code and the image that is shown to see if someone can help me in this objective.

Thank,

René
Grapho

void __fastcall TForm2::LoadTextures(AnsiString nomfile)
    {
    int x,y;
    GLuint texture;
    bitmap = new Graphics::TBitmap;
    bitmap->LoadFromFile(nomfile);
    x=bitmap->Width;
    y=bitmap->Height;
    GLubyte bits[200][200][4];
    for(int i = 0; i < x; i++)
    {
    	for(int j = 0; j < y; j++)
        {
            bits[i][j][0]= (GLbyte)GetRValue(bitmap->Canvas->Pixels[i][j]);
            bits[i][j][1]= (GLbyte)GetGValue(bitmap->Canvas->Pixels[i][j]);
            bits[i][j][2]= (GLbyte)GetBValue(bitmap->Canvas->Pixels[i][j]);
            bits[i][j][3]= (GLbyte)255;
        }
    }
    glColor3f(255,255,255);
    glPixelStorei(GL_UNPACK_ALIGNMENT, 4);
    glGenTextures(1, &texture);
    glBindTexture(GL_TEXTURE_2D, texture);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S,  GL_REPEAT);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T,  GL_REPEAT);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S,  GL_REPEAT);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T,  GL_REPEAT);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 64, 64, 0, GL_RGBA,     GL_UNSIGNED_BYTE, bits);
 }

void TForm2::DibujarEquipos(int pieza)
{
  glPushMatrix();
  for (int x = 0; x < conexiones->Get_cant_equipos() ; x++)
    {
      glPushMatrix();
      glColor3f(1.0f, 1.0f, 1.0f);
. 
     //Here the name of the file containing the texture is passed as a parameter.
     //There can be several calls depending on the type of node.
      LoadTextures("texturefile.bmp");
      glTranslated(conexiones->Get_coordenadas()[pieza][x][0] ,    conexiones->Get_coordenadas()[pieza][x][1] ,conexiones->Get_coordenadas()[pieza][x][2]);
      gluSphere(quadratic , 0.5 , 32 , 32);
      glPopMatrix();
      }
    glPopMatrix();
  }

So is it 200x200 or 64x64? The dimensions used in the declaration of bits will determine how it’s stored in memory. Even if the texture is less than 200 pixels wide, the stride (offset between consecutive rows) will be 800 bytes, but glTexImage2D will assume a stride of 256 bytes (64x4).

Either:

  1. store the data without any space between rows, e.g.
GLubyte *bits = malloc(x * y * 4);
...
    bits[(j*x+i)*4+0] = (GLbyte)GetRValue(bitmap->Canvas->Pixels[i][j]);
    bits[(j*x+i)*4+1] = (GLbyte)GetGValue(bitmap->Canvas->Pixels[i][j]);
    bits[(j*x+i)*4+2] = (GLbyte)GetBValue(bitmap->Canvas->Pixels[i][j]);
    bits[(j*x+i)*4+3] = 255;

or

  1. use glPixelStorei(GL_UNPACK_ROW_LENGTH, 200) to force a specific length for each row independent of the width of the texture.

Hello GClements,
Thank you for your reply, I have tried your two suggestions and the above situation remains: not all the textures on the spheres are displayed.

void __fastcall TForm2::LoadTextures(AnsiString nomfile)
    {
    int x,y;
    GLuint texture;
    bitmap = new Graphics::TBitmap;
    bitmap->LoadFromFile(nomfile);
    x=bitmap->Width;
    y=bitmap->Height;
    GLubyte *bits = (GLbyte *) malloc(x*y*4);
    for(int i = 0; i < x; i++)
    {
    	for(int j = 0; j < y; j++)
        {
             bits[(j*x+i)*4+0] = (GLbyte)GetRValue(bitmap->Canvas->Pixels[i][j]);
             bits[(j*x+i)*4+1] = (GLbyte)GetGValue(bitmap->Canvas->Pixels[i][j]);
             bits[(j*x+i)*4+2] = (GLbyte)GetBValue(bitmap->Canvas->Pixels[i][j]);
             bits[(j*x+i)*4+3] = 255;
         }
    }
......
   }

Also does not work:

....
glPixelStorei(GL_UNPACK_ROW_LENGTH, 200) 
.....

Please, if you would like to help me, could send to your EMail this part of the application for you to analyze.
I would be very grateful,
René