views:

247

answers:

1

I need to have a hemisphere in opengl. I found a drawSphere function which I modified to draw half the lats (which ends up drawing half of the sphere) which is what I wanted. It does this correctly.

However, I don't know what i should do with glTexCoordf to get the textures to map properly onto this half sphere. I'm really not great with opengl, and I've tried countless variations but I just can't get the textures to appear properly on it.

void drawHemisphere(double r, int lats, int longs) 
{
    int i, j;
    int halfLats = lats / 2; 
    for(i = 0; i <= halfLats; i++) 
    {
        double lat0 = M_PI * (-0.5 + (double) (i - 1) / lats);
        double z0 = sin(lat0);
        double zr0 = cos(lat0);

        double lat1 = M_PI * (-0.5 + (double) i / lats);
        double z1 = sin(lat1);
        double zr1 = cos(lat1);

        glBegin(GL_QUAD_STRIP);
        for(j = 0; j <= longs; j++)
        {
            double lng = 2 * M_PI * (double) (j - 1) / longs;
            double x = cos(lng);
            double y = sin(lng);

            // glTexCoordf()
            glNormal3f(x * zr0, y * zr0, z0);
            glVertex3f(x * zr0, y * zr0, z0);       

            // glTexCoordf()
            glNormal3f(x * zr1, y * zr1, z1);
            glVertex3f(x * zr1, y * zr1, z1);
        }
        glEnd();
    }
}

Does anyone have any idea of what values I should be putting in? Or what I need to calculate for it?

Thanks!

A: 

Basically, you shouldn't need anything fancy there. The texture coordinate space ranges from zero to one. So pick some intermediate values for the vertices in between. I can't explain it more thoroughly without image, so the best I can do is to point You to this article: UV mapping, it's a good starting point. Hope this helps as a starter.

Here's my guess:

{
    double lng = 2 * M_PI * (double) (j - 1) / longs;
    double x = cos(lng);
    double y = sin(lng);

    double s1, s2, t;
    s1 = ((double) i) / halfLats;
    s2 = ((double) i + 1) / halfLats;
    t = ((double) j) / longs;

    glTexCoord2d(s1, t);
    glNormal3d(x * zr0, y * zr0, z0);
    glVertex3d(x * zr0, y * zr0, z0);

    glTexCoord2d(s2, t);
    glNormal3d(x * zr1, y * zr1, z1);
    glVertex3d(x * zr1, y * zr1, z1);
}

Remember to properly set texture in OpenGL. An example call with texture:

    glActiveTexture(GL_TEXTURE0);
    glMatrixMode(GL_TEXTURE);
    glLoadIdentity();
    glMatrixMode(GL_MODELVIEW);

    // texture must be bound & enabled
    texture.bind();
    texture.enable();
    drawHemisphere(1, 40, 40);
    texture.disable();

I used Java + JOGL to test it, so it's not one-to-one C++ solution, but conceptually it should be the same. At least You have proper glTexCoord2d() calls.

Rekin