In my previous article [here] I have shown you how to map texture in solid sphere. In that method whole sphere is render using triangles and providing texture co-ordinates which seems difficult to understand. Now in this article I am going to show you simple method to map texture on Sphere. We first draw a sphere using gluSphere and texture co-ordinates are automatically generated by gluQuadricTexture function for Sphere.
gluSphere:
syntax:
void WINAPI gluSphere( GLUquadric *qobj, GLdouble radius, GLint slices, GLint stacks);
Parameters
If the orientation is set to GLU_OUTSIDE (with gluQuadricOrientation), any normals generated point away from the center of the sphere. Otherwise, they point toward the center of the sphere.
If texturing is turned on (with gluQuadricTexture): texture coordinates are generated so that t ranges from 0.0 at z = -radius to 1.0 at z = radius (t increases linearly along longitudinal lines); and s ranges from 0.0 at the positive y-axis, to 0.25 at the positive x-axis, to 0.5 at the negative y-axis, to 0.75 at the negative x-axis, and back to 1.0 at the positive y-axis.
gluQuadricTexture:
syntax:
void WINAPI gluQuadricTexture( GLUquadric *quadObject, GLboolean textureCoords);
A flag indicating whether texture coordinates are to be generated. The following values are valid.
Value
GL_TRUE :-Generate texture coordinates. GL_FALSE :-Do not generate texture coordinates. This is the default value.
The manner in which texture coordinates are generated depends upon the specific quadric rendered.
gluSphere:
syntax:
void WINAPI gluSphere( GLUquadric *qobj, GLdouble radius, GLint slices, GLint stacks);
Parameters
- qobj
- radius
- slices
- stacks
Return value
This function does not return a value.Remarks
The gluSphere function draws a sphere of the given radius centered around the origin. The sphere is subdivided around the z-axis into slices and along the z-axis into stacks (similar to lines of longitude and latitude).If the orientation is set to GLU_OUTSIDE (with gluQuadricOrientation), any normals generated point away from the center of the sphere. Otherwise, they point toward the center of the sphere.
If texturing is turned on (with gluQuadricTexture): texture coordinates are generated so that t ranges from 0.0 at z = -radius to 1.0 at z = radius (t increases linearly along longitudinal lines); and s ranges from 0.0 at the positive y-axis, to 0.25 at the positive x-axis, to 0.5 at the negative y-axis, to 0.75 at the negative x-axis, and back to 1.0 at the positive y-axis.
gluQuadricTexture:
syntax:
void WINAPI gluQuadricTexture( GLUquadric *quadObject, GLboolean textureCoords);
Parameters
quadObject
The quadric object (created with gluNewQuadric).
textureCoords
Value
GL_TRUE :-Generate texture coordinates.
Return value
This function does not return a value.Remarks
The gluQuadricTexture function specifies whether texture coordinates are to be generated for quadrics rendered with quadObject.The manner in which texture coordinates are generated depends upon the specific quadric rendered.
Here I will show you only source code of main function, complete source code you can download from below.
main.cpp
#include <windows.h>#include <iostream>#include <stdlib.h>#include <GL/glut.h>#include "imageloader.h"
using namespace std;void handleKeypress(unsigned char key, int x, int y) {switch (key) {
case 27: //Escape keyexit(0);}}//Makes the image into a texture, and returns the id of the texture
GLuint loadTexture(Image* image) {GLuint textureId;glGenTextures(1, &textureId); //Make room for our texture
glBindTexture(GL_TEXTURE_2D, textureId); //Tell OpenGL which texture to edit
//Map the image to the texture
glTexImage2D(GL_TEXTURE_2D, //Always GL_TEXTURE_2D
0, //0 for now
GL_RGB, //Format OpenGL uses for image
image->width, image->height, //Width and height
0, //The border of the image
GL_RGB, //GL_RGB, because pixels are stored in RGB format
GL_UNSIGNED_BYTE, //GL_UNSIGNED_BYTE, because pixels are stored
//as unsigned numbers
image->pixels); //The actual pixel data
return textureId; //Returns the id of the texture}GLuint _textureId; //The id of the textur
GLUquadric *quad;float rotate;
//GLUquadricObj quad;
void initRendering() {
glEnable(GL_DEPTH_TEST);//glEnable(GL_LIGHTING);
//glEnable(GL_LIGHT0);
glEnable(GL_NORMALIZE);glEnable(GL_COLOR_MATERIAL);quad = gluNewQuadric();Image* image = loadBMP("earth.bmp");
_textureId = loadTexture(image);delete image;
}void handleResize(int w, int h) {glViewport(0, 0, w, h);glMatrixMode(GL_PROJECTION);glLoadIdentity();gluPerspective(45.0, (float)w / (float)h, 1.0, 200.0);}void drawScene() {
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);glMatrixMode(GL_MODELVIEW);glLoadIdentity();glTranslatef(0.0f, 1.0f, -16.0f);glEnable(GL_TEXTURE_2D);glBindTexture(GL_TEXTURE_2D, _textureId);//Bottom
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);//glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
//glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glRotatef(90,1.0f,0.0f,0.0f);glRotatef(rotate,0.0f,0.0f,1.0f);gluQuadricTexture(quad,1);gluSphere(quad,2,20,20);glutSwapBuffers();}void update(int value){rotate+=2.0f;if(rotate>360.f)
{rotate-=360;}glutPostRedisplay();glutTimerFunc(25,update,0);}int main(int argc, char** argv) {glutInit(&argc, argv);glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH);glutInitWindowSize(800, 800);glutCreateWindow("Textures-codeincodeblock.blogspot.com");
initRendering();glutTimerFunc(25,update,0);glutDisplayFunc(drawScene);glutKeyboardFunc(handleKeypress);glutReshapeFunc(handleResize);glutMainLoop();return 0;
}
Project Output is like this
Works perfectly. Awesome.
ReplyDeletegood that you got it..can u please help me how to get past this error??
Delete"input.open(filename, ifstream::binary);
assert(!input.fail() || !"Could not find file");"
It means your program doesn't found the image file. So keep the image file together with .exe file.
DeleteHi i got a error with the rotate variable, it say that is ambigous... any idea?
DeleteReally superb!! Thank you very much.
ReplyDeleteDoesn't even run, one error that VS can't even pick up
ReplyDeletethe code compiles without showing any error. but during run time,this statement gives an error..(imageloader.cpp line 118)
ReplyDelete"input.open(filename, ifstream::binary);
assert(!input.fail() || !"Could not find file");"
please help me overcome this problem.
thanks in advance
It means your program doesn't found the image file. So keep the image file together with .exe file.
Deletethanks for posting the code here..it helped me out a long way..
ReplyDelete~cheers from kiran to the admin
THANK YOU!!!!! I have been spending days trying to understand this concept and your code helped me work it through!
ReplyDeleteHuaaaaa D': It works! well I just take some lines, but it really is work! THANK YOU SOOOO VERY MUCH you kind soul :'D
ReplyDeletehow do i run the program there are 2 .cpp files.
ReplyDeletei got the output, but the image is inverted
ReplyDeletei have error please can you help me??
ReplyDeletecan you specify #include"imageloder.h" in detail. or please post its source code
ReplyDelete||=== Build file: "no target" in "no project" (compiler: unknown) ===|
ReplyDeleteD:\NOTES\2016\2 - Summer -16\Graphics\texture\earth.o:earth.cpp|| undefined reference to `loadBMP(char const*)'|
D:\NOTES\2016\2 - Summer -16\Graphics\texture\earth.o:earth.cpp|| undefined reference to `Image::~Image()'|
||error: ld returned 1 exit status|
||=== Build failed: 3 error(s), 0 warning(s) (0 minute(s), 0 second(s)) ===|
these are the errors i have. can someone help me to solve them??