Hi,
i am new to openGL, i am not getting how to draw 3d Cylinder and that should be rotate in x-direction.
Please guide me, Your answer is valuable for me..
waiting for reply.
Hi,
i am new to openGL, i am not getting how to draw 3d Cylinder and that should be rotate in x-direction.
Please guide me, Your answer is valuable for me..
waiting for reply.
Please be more specific -- what books or online articles have you looked at? What tools are you using C/C++? Posting your code always is a good start. It is quite difficult to answer such a broad question -- maybe looking at how to do an animation itself may help so see Post# 267635
That post shows a rotating cube, to get a rotating cylinder the code is modifed to use GLUquadricObj as follows;
Code :#include <GL/gl.h> #include <GL/glut.h> #include <stdlib.h> #include <stdio.h> GLfloat gAngle = 0.0; GLUquadricObj *IDquadric; void timer(int value) { const int desiredFPS=120; glutTimerFunc(1000/desiredFPS, timer, ++value); GLfloat dt = 1./desiredFPS; //put your specific idle code here //... this code will run at desiredFPS gAngle += dt*360./8.; //rotate 360 degrees every 8 seconds //end your specific idle code here glutPostRedisplay(); // initiate display() call at desiredFPS rate } void display() { // Will be called at FPS rate, ok to use global values now to rener scene glClear(GL_COLOR_BUFFER_BIT); glPushMatrix(); glTranslatef(0,0,-100); glRotatef(gAngle,1.,1.,1.); //glutWireCube(20.); //cube of size 20x20x20 gluCylinder(IDquadric,10.0f,10.0f,10.0f,32,32); glPopMatrix(); glutSwapBuffers(); } void cleanupQuadric(void) // Properly Kill The Window { gluDeleteQuadric(IDquadric); printf( "cleanupQuadric completed\n" ); } void init() { glClearColor(0.0, 0.0, 0.0, 0.0); IDquadric=gluNewQuadric(); // Create A Pointer To The Quadric Object ( NEW ) gluQuadricNormals(IDquadric, GLU_SMOOTH); // Create Smooth Normals ( NEW ) gluQuadricTexture(IDquadric, GL_TRUE); // Create Texture Coords ( NEW ) atexit(cleanupQuadric); GLdouble Vol = 10*1.8; GLdouble Left=-Vol; GLdouble Right=Vol; GLdouble Bottom=-Vol; GLdouble Top=Vol; GLdouble Near=0; GLdouble Far=2*Vol; glMatrixMode(GL_PROJECTION); glLoadIdentity(); glOrtho(Left, Right, Bottom, Top, Near, Far); GLdouble eyeX=0; GLdouble eyeY=0; GLdouble eyeZ=-100+Vol; GLdouble centerX=0; GLdouble centerY=0; GLdouble centerZ=-100; GLdouble upX=0; GLdouble upY=1; GLdouble upZ=0; glMatrixMode(GL_MODELVIEW); glLoadIdentity(); gluLookAt(eyeX,eyeY,eyeZ, centerX,centerY,centerZ, upX,upY,upZ); } void keyboard(unsigned char key, int x, int y) { switch (key) { case 27: // escape key exit(0); break; default: break; } } int main(int argc, char** argv) { glutInit(&argc, argv); glutInitDisplayMode(GLUT_DOUBLE); glutCreateWindow("FPS test /w glutTimerFunc"); glutTimerFunc(0,timer,0); glutDisplayFunc(display); glutKeyboardFunc(keyboard); init(); glutMainLoop(); return 0; }
Hi,
Thank you so much.
i checked your code, it's displaying perfect cylinder. i made other code to Display cylinder and rotation of that is mouse control. if you want to check the code means i will send it.
my assignment is to place bmp format images on the side surfaces of the Cylinder. i am using C in Ubuntu.
if i rotate the cylinder around the x-axis, it should highlight the current image from my point of view.
Please guide me, any valuable answer is appreciated.
i am thankful for any kind of help.
There is a nice image loading library called DevIL that is cross platform. Since you are on ubuntu it is a simple "sudo apt-get install libdevil-dev" command installation.
To use it see a previous post from earlier today at Post267979.
After you load the image like the post, you simply need to add two lines of code in the Display function before you start drawing the gluCylinder ...
Code :struct TextureHandle { ... identical from post267979, cut-n-paste }; TextureHandle logo; ILuint LoadImageDevIL (const char *szFileName, struct TextureHandle *T) { ... identical to post267979, cut-n-paste } void init() { ... add following two lines ilInit(); //initialize DevIL library required LoadImageDevIL ("your.bmp", &logo); } void display() { ... //add two line to bind texture glEnable (GL_TEXTURE_2D); glBindTexture ( GL_TEXTURE_2D, logo.genID); // your previous drawing of quadric cylinder glPushMatrix(); glTranslatef(0,0,-100); glRotatef(gAngle,1.,1.,1.); gluCylinder(IDquadric,10.0f,10.0f,10.0f,32,32); glPopMatrix(); ... }
someone forgot that's about it:
GLU spec 6.3 page 21Texture coordinate generation can be turned on and o with
gluQuadricTexture:
void gluQuadricTexture( GLUquadricObj *quadobj,GLboolean textureCoords );
Hi,
Thank You for your initiation.
I made the changes,what you sent above, but it's giving the error as "logo" is undefined, but it's already declared. i am not getting that.. placing the entire code below and there is two init() functions so i commented the below init()function :
Code :
#include <GL/gl.h>
#include <GL/glut.h>
#include <stdlib.h>
#include <stdio.h>
#include <IL/ilut.h>
GLfloat gAngle = 0.0;
GLUquadricObj *IDquadric;
struct TextureHandle {
ILubyte *p;
ILuint id;
ILint w;
ILint h;
ILenum DestFormat;
ILenum DestType;
GLuint genID;
};
TextureHandle wmap, logo, frac;
ILuint LoadImageDevIL (const char *szFileName, struct TextureHandle *T)
{
ilEnable(IL_ORIGIN_SET);
ilOriginFunc(IL_ORIGIN_LOWER_LEFT);
ILuint ImageNameID;
ilGenImages(1, &ImageNameID);
ilBindImage(ImageNameID);
if (!ilLoadImage(szFileName)) return 0;
ilConvertImage(IL_RGB, IL_UNSIGNED_BYTE);
T->id = ImageNameID;
T->p = ilGetData();
T->w = ilGetInteger(IL_IMAGE_WIDTH);
T->h = ilGetInteger(IL_IMAGE_HEIGHT);
T->DestFormat = ilGetInteger(IL_IMAGE_FORMAT);
T->DestType = ilGetInteger(IL_IMAGE_TYPE);
glGenTextures(1, &T->genID);
glBindTexture(GL_TEXTURE_2D, T->genID);
glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexImage2D (GL_TEXTURE_2D, 0, T->DestFormat, T->w, T->h, 0, T->DestFormat, T->DestType, T->p);
printf("%s %d %d %d\n",szFileName,T->id,T->w,T->h);
return 1;
}
void init() {
ilInit();
LoadImageDevIL ("/localhome/user/Temp/sample/bird.bmp", &logo);
}
void timer(int value)
{
const int desiredFPS=120;
glutTimerFunc(1000/desiredFPS, timer, ++value);
GLfloat dt = 1./desiredFPS;
gAngle += dt*360./8.;
glutPostRedisplay();
}
void display() {
glEnable (GL_TEXTURE_2D);
glBindTexture ( GL_TEXTURE_2D, logo.genID);
glClear(GL_COLOR_BUFFER_BIT);
glPushMatrix();
glTranslatef(0,0,-100);
glRotatef(gAngle,1.,1.,1.);
gluCylinder(IDquadric,10.0f,10.0f,10.0f,32,32);
glPopMatrix();
glutSwapBuffers();
}
void cleanupQuadric(void)
{
gluDeleteQuadric(IDquadric);
printf( "cleanupQuadric completed\n" );
}
/*
void init() {
glClearColor(0.0, 0.0, 0.0, 0.0);
IDquadric=gluNewQuadric();
gluQuadricNormals(IDquadric, GLU_SMOOTH);
gluQuadricTexture(IDquadric, GL_TRUE);
atexit(cleanupQuadric);
GLdouble Vol = 10*1.8;
GLdouble Left=-Vol;
GLdouble Right=Vol;
GLdouble Bottom=-Vol;
GLdouble Top=Vol;
GLdouble Near=0;
GLdouble Far=2*Vol;
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrtho(Left, Right, Bottom, Top, Near, Far);
GLdouble eyeX=0;
GLdouble eyeY=0;
GLdouble eyeZ=-100+Vol;
GLdouble centerX=0;
GLdouble centerY=0;
GLdouble centerZ=-100;
GLdouble upX=0;
GLdouble upY=1;
GLdouble upZ=0;
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
gluLookAt(eyeX,eyeY,eyeZ,
centerX,centerY,centerZ,
upX,upY,upZ);
}
*/
void keyboard(unsigned char key, int x, int y)
{
switch (key) {
case 27:
exit(0);
break;
default:
break;
}
}
int main(int argc, char** argv) {
glutInit(&argc, argv);
glutInitDisplayMode(GLUT_DOUBLE);
glutCreateWindow("FPS test /w glutTimerFunc");
glutTimerFunc(0,timer,0);
glutDisplayFunc(display);
glutKeyboardFunc(keyboard);
init();
glutMainLoop();
return 0;
}
and one more is it necessary to place this line
void gluQuadricTexture( GLUquadricObj *quadobj,GLboolean textureCoords );
if means, where i should i place ?
Compile: gcc cc1.c -o cc1 -I/usr/x11R6/include/ -L/usr/lib -lX11 -lXmu -lglut -lGL -lGLU
Is there any changes needed in above command, Guide me please.
i am thankful for any kind of help.
You need to place gluQuadricTexture(IDquadric, GL_TRUE); after you called your gluNewQuadric. This is what gives you texture coordinates.
The compile command I use is for C++ (filename.cpp)
Now if you have a .c extension instead of .cpp, then the gcc command will assume Ansi-C. In which case you have to declare with a "struct" explicitly.Code :g++ main.cpp -lGL -lglut -lIL but you can also use gcc main.cpp -lGL -lglut -lIL
so your gcc compile command looks fine as is as long as you change to make the "logo" declaration ANSI-C instead of my ANSI-C++ as done in following code ...Code :for .cpp: TextureHandle logo; gcc main.cpp -lGL -lglut -lIL for .c: struct TextureHandle logo; gcc main.c -lGL -lglut -lIL
Here's the code with the "struct" added for filename.c (ie c version)
Code :// on linux with gcc: g++ main.c -lGL -lglut -lIL #include <GL/gl.h> #include <GL/glut.h> #include <stdlib.h> #include <stdio.h> #include <IL/ilut.h> GLfloat gAngle = 0.0; GLUquadricObj *IDquadric; struct TextureHandle { ILubyte *p; ILuint id; ILint w; ILint h; ILenum DestFormat; ILenum DestType; GLuint genID; }; struct TextureHandle logo; ILuint LoadImageDevIL (const char *szFileName, struct TextureHandle *T) { ilEnable(IL_ORIGIN_SET); ilOriginFunc(IL_ORIGIN_LOWER_LEFT); ILuint ImageNameID; ilGenImages(1, &ImageNameID); ilBindImage(ImageNameID); if (!ilLoadImage(szFileName)) return 0; ilConvertImage(IL_RGB, IL_UNSIGNED_BYTE); T->id = ImageNameID; T->p = ilGetData(); T->w = ilGetInteger(IL_IMAGE_WIDTH); T->h = ilGetInteger(IL_IMAGE_HEIGHT); T->DestFormat = ilGetInteger(IL_IMAGE_FORMAT); T->DestType = ilGetInteger(IL_IMAGE_TYPE); glGenTextures(1, &T->genID); glBindTexture(GL_TEXTURE_2D, T->genID); glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); glTexImage2D (GL_TEXTURE_2D, 0, T->DestFormat, T->w, T->h, 0, T->DestFormat, T->DestType, T->p); printf("%s %d %d %d\n",szFileName,T->id,T->w,T->h); return 1; } void timer(int value) { const int desiredFPS=120; glutTimerFunc(1000/desiredFPS, timer, ++value); GLfloat dt = 1./desiredFPS; gAngle += dt*360./8.; glutPostRedisplay(); } void display() { glEnable (GL_TEXTURE_2D); glBindTexture ( GL_TEXTURE_2D, logo.genID); glClear(GL_COLOR_BUFFER_BIT); glPushMatrix(); glTranslatef(0,0,-100); glRotatef(gAngle,1.,1.,1.); gluCylinder(IDquadric,10.0f,10.0f,10.0f,32,32); glPopMatrix(); glutSwapBuffers(); } void cleanupQuadric(void) { gluDeleteQuadric(IDquadric); printf( "cleanupQuadric completed\n" ); } void init() { glClearColor(0.0, 0.0, 0.0, 0.0); IDquadric=gluNewQuadric(); gluQuadricNormals(IDquadric, GLU_SMOOTH); gluQuadricTexture(IDquadric, GL_TRUE); atexit(cleanupQuadric); GLdouble Vol = 10*1.8; GLdouble Left=-Vol; GLdouble Right=Vol; GLdouble Bottom=-Vol; GLdouble Top=Vol; GLdouble Near=0; GLdouble Far=2*Vol; glMatrixMode(GL_PROJECTION); glLoadIdentity(); glOrtho(Left, Right, Bottom, Top, Near, Far); GLdouble eyeX=0; GLdouble eyeY=0; GLdouble eyeZ=-100+Vol; GLdouble centerX=0; GLdouble centerY=0; GLdouble centerZ=-100; GLdouble upX=0; GLdouble upY=1; GLdouble upZ=0; glMatrixMode(GL_MODELVIEW); glLoadIdentity(); gluLookAt(eyeX,eyeY,eyeZ, centerX,centerY,centerZ, upX,upY,upZ); ilInit(); LoadImageDevIL ("/localhome/user/Temp/sample/bird.bmp", &logo); //LoadImageDevIL ("Logo.bmp", &logo); } void keyboard(unsigned char key, int x, int y) { switch (key) { case 27: exit(0); break; default: break; } } int main(int argc, char** argv) { glutInit(&argc, argv); glutInitDisplayMode(GLUT_DOUBLE); glutCreateWindow("FPS test /w glutTimerFunc"); glutTimerFunc(0,timer,0); glutDisplayFunc(display); glutKeyboardFunc(keyboard); init(); glutMainLoop(); return 0; }
Hi,
Thank You very much for your reply marshats,
The above code is working fine without any error messages.
i just changed width and height to get good clarity.
i dint get what exactly below line indicates, why cant we use directly value for IDquadric :
GLUquadricObj *IDquadric;
and i changed the line as
gluCylinder (30, 5.0f, 5.0f, 10.0f, 24, 8);
This shows segmentation fault. This means memory related are what.
one more thing requesting you is how to place many different images on the same cylinder ?
Please guide me.
i am thankful for any kind of help.
This is a C question, whenever you see an argument of the form "type * X" then it expects an address, not the value, to be passed into the function ... see glCylinder definition. Notice how the first argument it expects is a pointer to a GLUquadric. And reading further this pointer is defined by a very specific function, gluNewQuadric(). So you can't use the value of "30" for the first argument of your gluCylinder (30, 5.0f, 5.0f, 10.0f, 24, 8) -- the function is looking for the address not the value 30, this explains why you saw a segmentation fault.
The question about multiple textures on a single cylinder is more involved question. Do you have to do multiple textures or simply make a single texture in some drawing program that has the effect of multiple decals? The second approach easily maps to the code you already have. But if you have to do the first approach -- A quick google search lead to multitexturing tutorial that may help you get started. Also see Post90211.
I believe with this you will have to start using the openGL extensions -- you can get setup to use them with the GLEW library. On Ubuntu you can get it installed with a simple "sudo apt-get install libglew1.5-dev". To use it read Glew basic usage.
Here's code to simply add glew functionality (NOT multitexturing) -- a single include is added with a call to glewInit(). And note the compile command is
Code :gcc main.c -lGL -lglut -lIL -lGLEWThe changes of adding GLEW are just to help you have access to the commands like "glActiveTexture and glMultiTexCoord2f" that you will need for multi-texturing.Code :// on linux with gcc: gcc main.c -lGL -lglut -lIL -lGLEW #include <GL/glew.h> #include <GL/glut.h> #include <stdlib.h> #include <stdio.h> #include <IL/ilut.h> GLfloat gAngle = 0.0; GLUquadricObj *IDquadric; struct TextureHandle { ILubyte *p; ILuint id; ILint w; ILint h; ILenum DestFormat; ILenum DestType; GLuint genID; }; struct TextureHandle logo; ILuint LoadImageDevIL (const char *szFileName, struct TextureHandle *T) { ilEnable(IL_ORIGIN_SET); ilOriginFunc(IL_ORIGIN_LOWER_LEFT); ILuint ImageNameID; ilGenImages(1, &ImageNameID); ilBindImage(ImageNameID); if (!ilLoadImage(szFileName)) return 0; ilConvertImage(IL_RGB, IL_UNSIGNED_BYTE); T->id = ImageNameID; T->p = ilGetData(); T->w = ilGetInteger(IL_IMAGE_WIDTH); T->h = ilGetInteger(IL_IMAGE_HEIGHT); T->DestFormat = ilGetInteger(IL_IMAGE_FORMAT); T->DestType = ilGetInteger(IL_IMAGE_TYPE); glGenTextures(1, &T->genID); glBindTexture(GL_TEXTURE_2D, T->genID); glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); glTexImage2D (GL_TEXTURE_2D, 0, T->DestFormat, T->w, T->h, 0, T->DestFormat, T->DestType, T->p); printf("%s %d %d %d\n",szFileName,T->id,T->w,T->h); return 1; } void timer(int value) { const int desiredFPS=120; glutTimerFunc(1000/desiredFPS, timer, ++value); GLfloat dt = 1./desiredFPS; gAngle += dt*360./8.; glutPostRedisplay(); } void display() { glEnable (GL_TEXTURE_2D); glBindTexture ( GL_TEXTURE_2D, logo.genID); glClear(GL_COLOR_BUFFER_BIT); glMatrixMode(GL_MODELVIEW); glPushMatrix(); glTranslatef(0,0,-100); glRotatef(gAngle,1.,1.,1.); gluCylinder(IDquadric,10.0f,10.0f,10.0f,32,32); glPopMatrix(); glutSwapBuffers(); } void cleanupQuadric(void) { gluDeleteQuadric(IDquadric); printf( "cleanupQuadric completed\n" ); } void init() { glClearColor(0.0, 0.0, 0.0, 0.0); IDquadric=gluNewQuadric(); gluQuadricNormals(IDquadric, GLU_SMOOTH); gluQuadricTexture(IDquadric, GL_TRUE); atexit(cleanupQuadric); GLdouble Vol = 10*1.8; GLdouble Left=-Vol; GLdouble Right=Vol; GLdouble Bottom=-Vol; GLdouble Top=Vol; GLdouble Near=0; GLdouble Far=2*Vol; glMatrixMode(GL_PROJECTION); glLoadIdentity(); glOrtho(Left, Right, Bottom, Top, Near, Far); GLdouble eyeX=0; GLdouble eyeY=0; GLdouble eyeZ=-100+Vol; GLdouble centerX=0; GLdouble centerY=0; GLdouble centerZ=-100; GLdouble upX=0; GLdouble upY=1; GLdouble upZ=0; glMatrixMode(GL_MODELVIEW); glLoadIdentity(); gluLookAt(eyeX,eyeY,eyeZ, centerX,centerY,centerZ, upX,upY,upZ); ilInit(); LoadImageDevIL ("/localhome/user/Temp/sample/bird.bmp", &logo); //LoadImageDevIL ("Logo.bmp", &logo); } void keyboard(unsigned char key, int x, int y) { switch (key) { case 27: exit(0); break; default: break; } } int main(int argc, char** argv) { glutInit(&argc, argv); glutInitDisplayMode(GLUT_DOUBLE); glutCreateWindow("FPS test /w glutTimerFunc"); glewInit(); glutTimerFunc(0,timer,0); glutDisplayFunc(display); glutKeyboardFunc(keyboard); init(); glutMainLoop(); return 0; }
Hi,
i got the idea about segmentation fault. Thank you very much.
Regarding multitexturing, the code which is in above link is in shading language is it same for C. Sorry for asking simple question.
Guide me please.