CUFP
orange
this example is a toy, your child or grandchild may enjoy seeing his/her picture on a face of a rotating cube while his/her pets pictures on other sides of the cube.<br>
a picture of the example <A HREF="https://sites.google.com/site/zak31415/Home/cube.JPG">here...</A> <br>
the perl source with the 6 suitable pictures <A HREF="https://sites.google.com/site/zak31415/Home/cubeGL.rar">here...</A> <br>
all the modules used in this example can be installed for windows users from <br>
ppm install http://www.bribes.org/perl/ppm/OpenGL-Image.ppd<br>
ppm install http://www.bribes.org/perl/ppm/OpenGL.ppd<br>
i have tried the example on windows xp /sp2, activestate perl 5.10, it should work on other platforms.<br>
multiple textures on the cube faces means that every face has its unique picture, normally we define a cube by defining its 6 sides inside :<br><br>
glBegin (GL_QUADS);<br>
all six faces definitions here.....<br>
glEnd();<br>
<br>
but we can partition the one block of definitions to 6 blocks of <br><br>
glBegin (GL_QUADS);<br>
one face definition here.....<br>
glEnd();<br><br>
in which every block have one face only<br>
in this way we can insert the reference to some picture before every block.
at first i prepared 6 pictures of the same type (here it is jpg) and resized it to the same dimensions (multiples of 2's)(here it is 256) using irfanView,<br>
then we use OpenGL::Image to assign 6 pictures to 6 variables ($tex1 to $tex6)<br>
then Get GL info for one of those pictures.
you can implement code to move the cube around the screen by manipulating the x,y,z parameters of glTranslatef, i have used here<br> glTranslatef(0.0, 0.0, -5.0); <br>
use the key s to stop cube rotating, n,h,v normal,horizontal,vertical rotation, you can devise more intellegent rotations. if you want to move the cube by mouse then download the demos.zip from [http://www.bribes.org/perl/wopengl.html#ex] and look in the example teapot.pl ->sub mouse {...}, also look the example glutmech.pl<br>
if someone devised more amusing movements please post<br>
thank you<br>
<p>
<readmore>
<code>
use OpenGL qw/ :all /;
use OpenGL::Image;
my $tex1 = new OpenGL::Image(source=>'sunrise.jpg');
my $tex2 = new OpenGL::Image(source=>'city.jpg');
my $tex3 = new OpenGL::Image(source=>'flowers.jpg');
my $tex4 = new OpenGL::Image(source=>'umbrella.jpg');
my $tex5 = new OpenGL::Image(source=>'kid.jpg');
my $tex6 = new OpenGL::Image(source=>'cat.jpg');
# Get GL info
my($ifmt,$fmt,$type) = $tex1->Get('gl_internalformat','gl_format','gl_type');
my($w,$h) = $tex1->Get('width','height');
use constant ESCAPE => 27;
# Global variable for our window
my $window;
my $CubeRot = 0;
my $xCord = 1;
my $yCord = 1;
my $zCord = 0;
my $rotSpeed = 0.5;
# A general GL initialization function
# Called right after our OpenGL window is created
# Sets all of the initial parameters
sub InitGL {
# Shift the width and height off of @_, in that order
my ($width, $height) = @_;
# Set the background "clearing color" to black
glClearColor(0.0, 0.0, 0.0, 0.0);
# Enables clearing of the Depth buffer
glClearDepth(1.0);
# The type of depth test to do
glDepthFunc(GL_LESS);
# Enables depth testing with that type
glEnable(GL_DEPTH_TEST);
# Enables smooth color shading
glShadeModel(GL_SMOOTH);
# Reset the projection matrix
glMatrixMode(GL_PROJECTION);
glLoadIdentity;
# Reset the modelview matrix
glMatrixMode(GL_MODELVIEW);
}
# The function called when our window is resized
# This shouldn't happen, because we're fullscreen
sub ReSizeGLScene {
# Shift width and height off of @_, in that order
my ($width, $height) = @_;
# Prevent divide by zero error if window is too small
if ($height == 0) { $height = 1; }
# Reset the current viewport and perspective transformation
glViewport(0, 0, $width, $height);
# Re-initialize the window (same lines from InitGL)
glMatrixMode(GL_PROJECTION);
glLoadIdentity;
# Calculate the aspect ratio of the Window
gluPerspective(45.0, $width/$height, 0.1, 100.0);
glMatrixMode(GL_MODELVIEW);
}
# The main drawing function.
sub DrawGLScene {
# Clear the screen and the depth buffer
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
# Reset the view
glLoadIdentity;
# Move to the away from us 5.0 units
glTranslatef(0.0, 0.0, -5.0);
glPushMatrix();
glRotatef($CubeRot, $xCord, $yCord, $zCord);
my $texid = glGenTextures_p(5);
glEnable(GL_TEXTURE_2D);
glBindTexture(GL_TEXTURE_2D, $texid);
#glTexImage2D_c(GL_TEXTURE_2D, 0, 3, $w, $h, 0, GL_RGB, GL_BYTE,$tex);
glTexImage2D_c(GL_TEXTURE_2D, 0, $ifmt, $w, $h, 0, $fmt, $type, $tex1->Ptr());
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glBegin (GL_QUADS);
# Front Face
glColor3f(1.0,1.0,1.0); #white to display the texture
glTexCoord2d(0.0, 0.0); glVertex3f(-1.0,-1.0,1.0);
glTexCoord2d(1.0, 0.0); glVertex3f(1.0,-1.0,1.0);
glTexCoord2d(1.0, 1.0); glVertex3f(1.0,1.0,1.0);
glTexCoord2d(0.0, 1.0); glVertex3f(-1.0,1.0,1.0);
glEnd();
#glBindTexture(GL_TEXTURE_2D, $texid);
glTexImage2D_c(GL_TEXTURE_2D, 0, $ifmt, $w, $h, 0, $fmt, $type, $tex2->Ptr());
glBegin (GL_QUADS);
# Back Face
glColor3f(1.0,1.0,1.0); #white to display the texture on
glTexCoord2d(1.0, 0.0); glVertex3f(-1.0,-1.0,-1.0);
glTexCoord2d(1.0, 1.0); glVertex3f(-1.0,1.0,-1.0);
glTexCoord2d(0.0, 1.0); glVertex3f(1.0,1.0,-1.0);
glTexCoord2d(0.0, 0.0); glVertex3f(1.0,-1.0,-1.0);
glEnd();
#glDisable(GL_TEXTURE_2D);
#glBindTexture(GL_TEXTURE_2D, $texid);
glTexImage2D_c(GL_TEXTURE_2D, 0, $ifmt, $w, $h, 0, $fmt, $type, $tex3->Ptr());
glBegin (GL_QUADS);
# Top Face
glTexCoord2d(0.0, 1.0); glVertex3f(-1.0, 1.0, -1.0);
glTexCoord2d(0.0, 0.0); glVertex3f(-1.0,1.0,1.0);
glTexCoord2d(1.0, 0.0); glVertex3f(1.0,1.0,1.0);
glTexCoord2d(1.0, 1.0); glVertex3f(1.0,1.0,-1.0);
glEnd();
#glBindTexture(GL_TEXTURE_2D, $texid);
glTexImage2D_c(GL_TEXTURE_2D, 0, $ifmt, $w, $h, 0, $fmt, $type, $tex4->Ptr());
glColor3f(1.0,1.0,0.0); #background color yellow
glBegin (GL_QUADS);
# Bottom Face
glTexCoord2d(1.0, 1.0); glVertex3f(-1.0,-1.0,-1.0);
glTexCoord2d(0.0, 1.0); glVertex3f(1.0,-1.0,-1.0);
glTexCoord2d(0.0, 0.0); glVertex3f(1.0,-1.0,1.0);
glTexCoord2d(1.0, 0.0); glVertex3f(-1.0,-1.0,1.0);
glEnd();
# glBindTexture(GL_TEXTURE_2D, $texid);
glTexImage2D_c(GL_TEXTURE_2D, 0, $ifmt, $w, $h, 0, $fmt, $type, $tex5->Ptr());
glColor3f(1.0,1.0,1.0); # reset background color white
glBegin (GL_QUADS);
# Right Face
glTexCoord2d(1.0, 0.0); glVertex3f(1.0,-1.0,-1.0);
glTexCoord2d(1.0, 1.0); glVertex3f(1.0,1.0,-1.0);
glTexCoord2d(0.0, 1.0); glVertex3f(1.0,1.0,1.0);
glTexCoord2d(0.0, 0.0); glVertex3f(1.0,-1.0,1.0);
glEnd();
#glBindTexture(GL_TEXTURE_2D, $texid);
glTexImage2D_c(GL_TEXTURE_2D, 0, $ifmt, $w, $h, 0, $fmt, $type, $tex6->Ptr());
glBegin (GL_QUADS);
# Left Face
glTexCoord2d(0.0, 0.0); glVertex3f(-1.0,-1.0,-1.0);
glTexCoord2d(1.0, 0.0); glVertex3f(-1.0,-1.0,1.0);
glTexCoord2d(1.0, 1.0); glVertex3f(-1.0,1.0,1.0);
glTexCoord2d(0.0, 1.0); glVertex3f(-1.0,1.0,-1.0);
glEnd();
glPopMatrix();
$CubeRot += $rotSpeed;
glFlush();
glutSwapBuffers;
}
# The function called whenever a key is pressed.
sub keyPressed {
# Shift the unsigned char key, and the x,y placement off @_, in
# that order.
my ($key, $x, $y) = @_;
#sleep(1);
# If f key pressed, undo fullscreen and resize to 640x480
if ($key == ord('h')) {
$xCord = 0;$yCord = 1; $zCord = 0;}
elsif ($key == ord('v')) {$xCord = 1; $yCord = 0;$zCord = 0;}
elsif ($key == ord('n')) {$xCord = 1; $yCord = 1;$zCord = 0;}
if ($key == ord('s')) {
if ($rotSpeed == 0.5)
{$rotSpeed = 0;}
else
{$rotSpeed = 0.5;}
}
# If escape is pressed, kill everything.
if ($key == ESCAPE)
{
# Shut down our window
glutDestroyWindow($window);
# Exit the program...normal termination.
exit(0);
}
}
# --- Main program ---
# Initialize GLUT state
glutInit;
# Depth buffer */
glutInitDisplayMode(GLUT_RGB | GLUT_DOUBLE | GLUT_DEPTH);
# Get a 640 x 480 window
glutInitWindowSize(640, 480);
# The window starts at the upper left corner of the screen
glutInitWindowPosition(0, 0);
# Open the window
$window = glutCreateWindow("Texturing, Press n,h,v to change rotation , press s to toggle stop");
# Register the function to do all our OpenGL drawing.
glutDisplayFunc(\&DrawGLScene);
# Go fullscreen. This is as soon as possible.
#glutFullScreen;
# Even if there are no events, redraw our gl scene.
glutIdleFunc(\&DrawGLScene);
# Register the function called when our window is resized.
glutReshapeFunc(\&ReSizeGLScene);
# Register the function called when the keyboard is pressed.
glutKeyboardFunc(\&keyPressed);
# Initialize our window.
InitGL(640, 480);
# Start Event Processing Engine
glutMainLoop;
return 1;
</code>
</readmore>
</p>