small problems with beam program + ligtht position

Hi,

First I post the code and then I ask the question:


#!/usr/bin/python
from OpenGL.GLUT import *
from OpenGL.GLU import *
from OpenGL.GL import *
from math import * # cos, atan2 etc

rotate = 0
beginx = 0.
beginy = 0.
rotx = 0.
roty = 0.

def display():
    glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT)
    glLoadIdentity()
    gluLookAt(0,0,10,0,0,0,0,1,0)
    glRotatef(roty,0,1,0)
    glRotatef(rotx,1,0,0)
    glCallList(1)
    glutSwapBuffers()
    return

def mouse(button,state,x,y):
    global beginx,beginy,rotate
    if button == GLUT_LEFT_BUTTON and state == GLUT_DOWN:
        rotate = 1
        beginx = x
        beginy = y
    if button == GLUT_LEFT_BUTTON and state == GLUT_UP:
        rotate = 0
    return

def motion(x,y):
    global rotx,roty,beginx,beginy,rotate
    if rotate:
        rotx = rotx + (y - beginy)
        roty = roty + (x - beginx)
        beginx = x
        beginy = y
        glutPostRedisplay()
    return

def keyboard(*args):
    # If escape is pressed, kill everything.
    if args[0] == '\x1b':
        sys.exit()
    elif args[0] == 'q':
        sys.exit()
    return

def drawCoordSys(x, y, z, coordLength = 100):
    glPushAttrib(GL_CURRENT_BIT); # save, because color is changing below!
    glPushAttrib(GL_ENABLE_BIT); # save, because color is changing below!
    glDisable(GL_LIGHTING); # or else x-/y-/z- axis doesn't have same color...
    #---    
    glBegin(GL_LINES);    
    glColor3f(1.0, 0.0, 0.0); # red
    glVertex3f(x, y, z);
    glVertex3f(x+coordLength, y, z); # x-axis
    
    glColor3f(0.0, 1.0, 0.0); # green
    glVertex3f(x, y, z);
    glVertex3f(x, y+coordLength, z); # y-axis
    
    glColor3f(0.0, 0.0, 1.0); # blue
    glVertex3f(x, y, z);
    glVertex3f(x, y, z+coordLength); # z-axis
    glEnd();
    #---
    glPopAttrib(); # pop, because color was changed above!
    glPopAttrib(); # pop, because color was changed above!


def makeBeam(x, y, z, dx, dy, dz):

    # ---------------------------
    if len(x) != len(y):
        print "Error: len(x) != len(y), i.e. (", len(x), "!=", len(y), ")"
        sys.exit(1)
    if len(y) != len(z):
        print "Error: len(y) != len(z), i.e. (", len(y), "!=", len(z), ")"
        sys.exit(1)
    # ---------------------------
    if len(z) != len(dx):
        print "Error: len(z) != len(dx), i.e. (", len(z), "!=", len(dx), ")"
        sys.exit(1)
    # ---------------------------
    if len(dx) != len(dy):
        print "Error: len(dx) != len(dy), i.e. (", len(dx), "!=", len(dy), ")"
        sys.exit(1)
    if len(dy) != len(dz):
        print "Error: len(dy) != len(dz), i.e. (", len(dy), "!=", len(dz), ")"
        sys.exit(1)
    # ---------------------------
    N = len(dz)
    
    for i in range(N):
        glBegin(GL_QUAD_STRIP)
        v1 = [x[i] +  dx[i], y[i] + -dy[i], z[i] +  dz[i]]
        v2 = [x[i] +  dx[i], y[i] +  dy[i], z[i] +  dz[i]]
        v3 = [x[i] +  dx[i], y[i] + -dy[i], z[i] + -dz[i]]
        v4 = [x[i] +  dx[i], y[i] +  dy[i], z[i] + -dz[i]]
        v5 = [x[i] + -dx[i], y[i] + -dy[i], z[i] + -dz[i]]
        v6 = [x[i] + -dx[i], y[i] +  dy[i], z[i] + -dz[i]]
        v7 = [x[i] + -dx[i], y[i] + -dy[i], z[i] +  dz[i]]
        v8 = [x[i] + -dx[i], y[i] +  dy[i], z[i] +  dz[i]]

        # +quad 1 begins
        glVertex3f( v3[0], v3[1], v3[2] ) # V3
        glVertex3f( v1[0], v1[1], v1[2] ) # V1
        # +quad 2 begins
        glVertex3f( v4[0], v4[1], v4[2] ) # V4
        glVertex3f( v2[0], v2[1], v2[2] ) # V2
        # -quad 1 ends, +quad 3 begins
        glVertex3f( v6[0], v6[1], v6[2] ) # V6
        glVertex3f( v8[0], v8[1], v8[2] ) # V8
        # -quad 2 ends, +quad 4 begins
        glVertex3f( v5[0], v5[1], v5[2] ) # V5
        glVertex3f( v7[0], v7[1], v7[2] ) # V7
        # -quad 3 ends
        glVertex3f( v3[0], v3[1], v3[2] ) # V3 - again
        glVertex3f( v1[0], v1[1], v1[2] ) # V1 - again
        # -quad 4 ends
        glEnd();

        # Front and back:
        glBegin(GL_QUADS); # NB! This is not QUAD_STRIPS !!!
        # +quad 5 begins
        glVertex3f( v3[0], v3[1], v3[2] ) # V3
        glVertex3f( v4[0], v4[1], v4[2] ) # V4    
        glVertex3f( v6[0], v6[1], v6[2] ) # V6
        glVertex3f( v5[0], v5[1], v5[2] ) # V5
        # -quad 5 ends, +quad 6 begins
        glVertex3f( v1[0], v1[1], v1[2] ) # V1
        glVertex3f( v2[0], v2[1], v2[2] ) # V2
        glVertex3f( v8[0], v8[1], v8[2] ) # V8
        glVertex3f( v7[0], v7[1], v7[2] ) # V7    
        # -quad 6 ends
        glEnd();


#---------------------------------------
name = "Beam testing..."
width = 800
height = 600

glutInit(name)
glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH)
glutInitWindowSize(width, height)
glutCreateWindow(name)
glClearColor(0., 0., 0.,1.)

# setup display list
glNewList(1,GL_COMPILE)
glPushMatrix()
drawCoordSys(0, 0, 0, 2)
dx = [0.5, 0.4, 0.5, 0.6]
dy = [0.5, 0.4, 0.5, 0.6]
dz = [0.5, 0.4, 0.5, 0.6]
x = [0, 0, 0, 0]
y = [0, 0, 0, 0]
z = [0, 1, 2, 3]
makeBeam(x, y, z, dx, dy, dz)
#
glTranslatef(0.,-2.,0.) # move to where we want to put object
cyl = gluNewQuadric()
# gluCylinder: quadr., base, top, hgt, slices, stack
gluCylinder(cyl, 0.3, 0.3, 0.5, 12, 12)
glPopMatrix()
glEndList()

glDisable(GL_CULL_FACE)
glEnable(GL_DEPTH_TEST)

#----------
# setup lighting
if 1:
    glEnable(GL_LIGHTING)

    lightZeroPosition = [1.5, 1.5, 1.5]
    glLightfv(GL_LIGHT0, GL_POSITION, lightZeroPosition)

    glPointSize(12.0) # mark light source
    glBegin(GL_POINTS)
    glVertex3fv(lightZeroPosition)
    glEnd()
    glEnable(GL_LIGHT0)

#=============================================
# setup cameras
glMatrixMode(GL_PROJECTION)
aspect = float(width)/float(height)
print "aspect = ", aspect
gluPerspective(40., aspect, 1., 40.)
glMatrixMode(GL_MODELVIEW)
gluLookAt(0,0,10,  0,0,0,  0,1,0)
glPushMatrix()
glutDisplayFunc(display)
glutMouseFunc(mouse)
glutMotionFunc(motion)
glutKeyboardFunc(keyboard)

glutMainLoop()

If you run the program, you’ll see a beam extended. However, I think this method is not the best. I want to start the beam somewhere (x0,y0,z0) and then increment it in maybe 10-30 steps so it can bend (and maybe twist later) in any xyz-direction. Giving the positions and the dx, dy, dz is maybe a stupid way of doing it - when I change the dx/dy/dz (“beam thickness”) the program actually just maxes a lot of individual boxes - instead of connecting the boxes into a long beam… Understand my point?

2a)
And then I have two small problems with lighting: One is that I use:


    glPointSize(0.4) # mark light source
    glBegin(GL_POINTS)
    glVertex3fv(lightZeroPosition)
    glEnd()
    glEnable(GL_LIGHT0)

Because I thought this would make a big white dot at “lightZeroPosition” - but I don’t see any dot… How come?

2b)
Related to 2a, I think that when I rotate this frustrum (isn’t it called that?) with the mouse, then sometimes the beam is REALLY REALLY black, and I find this very odd/strange/incorrect in my code… However, because I cannot solve 2a, I cannot solve/understand the problem in my question 2b (I have a feeling that I should add ambient light, but I don’t understand completely why my light source isn’t good enough)…

BTW: The code is copy/pastable and runs without problems using python…

Please help/advice - any help is greatly appreciated, thanks!

Another thing: I’m making this beam-function, because I want it to be able to bend animated, like in this video:

http://www.youtube.com/watch?v=EVE2UUH3WNw