void updateCameraPosition() { // check values if (cameraDistance < 0.1) { cameraDistance = 0.1; } if (cameraAngleV > 89) { cameraAngleV = 89; } if (cameraAngleV < 10) { cameraAngleV = 10; } // compute position of camera in space cVector3d pos = cAdd( cameraPosition, cVector3d( cameraDistance * cCosDeg(cameraAngleH) * cCosDeg(cameraAngleV), cameraDistance * cSinDeg(cameraAngleH) * cCosDeg(cameraAngleV), cameraDistance * cSinDeg(cameraAngleV) ) ); // compute lookat position cVector3d lookat = cameraPosition; // define role orientation of camera cVector3d up(0.0, 0.0, 1.0); // set new position to camera camera->set(pos, lookat, up); // recompute global positions world->computeGlobalPositions(true); }
//=========================================================================== void cSpotLight::render(cRenderOptions& a_options) { // is display rendering of light source enabled? if (!m_displayEnabled) { return; } ///////////////////////////////////////////////////////////////////////// // Render parts that are always opaque ///////////////////////////////////////////////////////////////////////// if (SECTION_RENDER_OPAQUE_PARTS_ONLY(a_options) && (!a_options.m_creating_shadow_map)) { // disable lighting glDisable(GL_LIGHTING); // render cone double sizeS = m_displayConeLength * cSinDeg(m_cutOffAngleDEG); double sizeX = m_displayConeLength * cCosDeg(m_cutOffAngleDEG); glLineWidth(1.0); m_displayConeColor.render(); glEnable(GL_LINE_STIPPLE); glPushAttrib (GL_LINE_BIT); glLineStipple (1, 0xF0F0); glBegin(GL_LINES); glVertex3d( 0.0, 0.0, 0.0); glVertex3d( sizeX, sizeS, sizeS); glVertex3d( 0.0, 0.0, 0.0); glVertex3d( sizeX,-sizeS, sizeS); glVertex3d( 0.0, 0.0, 0.0); glVertex3d( sizeX,-sizeS,-sizeS); glVertex3d( 0.0, 0.0, 0.0); glVertex3d( sizeX, sizeS,-sizeS); glVertex3d( sizeX, sizeS, sizeS); glVertex3d( sizeX,-sizeS, sizeS); glVertex3d( sizeX,-sizeS, sizeS); glVertex3d( sizeX,-sizeS,-sizeS); glVertex3d( sizeX,-sizeS,-sizeS); glVertex3d( sizeX, sizeS,-sizeS); glVertex3d( sizeX, sizeS,-sizeS); glVertex3d( sizeX, sizeS, sizeS); glEnd(); glPopAttrib(); glDisable(GL_LINE_STIPPLE); // render light source if (m_enabled) m_displaySourceColor.render(); else glColor3f(0.2f, 0.2f, 0.2f); cDrawSphere(m_displaySourceRadius, 8, 8); // enable lighting again glEnable(GL_LIGHTING); } }
int main(int argc, char* argv[]) { //----------------------------------------------------------------------- // INITIALIZATION //----------------------------------------------------------------------- printf ("\n"); printf ("-----------------------------------\n"); printf ("CHAI 3D\n"); printf ("Demo: 12-polygons\n"); printf ("Copyright 2003-2009\n"); printf ("-----------------------------------\n"); printf ("\n\n"); printf ("Keyboard Options:\n\n"); printf ("[1] - Wireframe (ON/OFF)\n"); printf ("[x] - Exit application\n"); printf ("\n\n"); // parse first arg to try and locate resources resourceRoot = string(argv[0]).substr(0,string(argv[0]).find_last_of("/\\")+1); //----------------------------------------------------------------------- // 3D - SCENEGRAPH //----------------------------------------------------------------------- // create a new world. world = new cWorld(); // set the background color of the environment // the color is defined by its (R,G,B) components. world->setBackgroundColor(0.15, 0.15, 0.15); // create a camera and insert it into the virtual world camera = new cCamera(world); world->addChild(camera); // position and oriente the camera camera->set( cVector3d (3.0, 0.0, 0.0), // camera position (eye) cVector3d (0.0, 0.0, 0.0), // lookat position (target) cVector3d (0.0, 0.0, 1.0)); // direction of the "up" vector // set the near and far clipping planes of the camera // anything in front/behind these clipping planes will not be rendered camera->setClippingPlanes(0.01, 10.0); // create a light source and attach it to the camera light = new cLight(world); camera->addChild(light); // attach light to camera light->setEnabled(true); // enable light source light->setPos(cVector3d( 2.0, 0.5, 1.0)); // position the light source light->setDir(cVector3d(-2.0, 0.5, 1.0)); // define the direction of the light beam //----------------------------------------------------------------------- // 2D - WIDGETS //----------------------------------------------------------------------- // create a 2D bitmap logo logo = new cBitmap(); // add logo to the front plane camera->m_front_2Dscene.addChild(logo); // load a "chai3d" bitmap image file bool fileload; fileload = logo->m_image.loadFromFile(RESOURCE_PATH("resources/images/chai3d.bmp")); if (!fileload) { #if defined(_MSVC) fileload = logo->m_image.loadFromFile("../../../bin/resources/images/chai3d.bmp"); #endif } // position the logo at the bottom left of the screen (pixel coordinates) logo->setPos(10, 10, 0); // scale the logo along its horizontal and vertical axis logo->setZoomHV(0.4, 0.4); // here we replace all wite pixels (1,1,1) of the logo bitmap // with transparent black pixels (1, 1, 1, 0). This allows us to make // the background of the logo look transparent. logo->m_image.replace( cColorb(0x00, 0x00, 0x00), // original RGB color cColorb(0x00, 0x00, 0x00, 0x00) // new RGBA color ); // enable transparency logo->enableTransparency(true); //----------------------------------------------------------------------- // HAPTIC DEVICES / TOOLS //----------------------------------------------------------------------- // create a haptic device handler handler = new cHapticDeviceHandler(); // get access to the first available haptic device cGenericHapticDevice* hapticDevice; handler->getDevice(hapticDevice, 0); // retrieve information about the current haptic device cHapticDeviceInfo info; if (hapticDevice) { info = hapticDevice->getSpecifications(); } // create a 3D tool and add it to the world tool = new cGeneric3dofPointer(world); world->addChild(tool); // connect the haptic device to the tool tool->setHapticDevice(hapticDevice); // initialize tool by connecting to haptic device tool->start(); // map the physical workspace of the haptic device to a larger virtual workspace. tool->setWorkspaceRadius(1.0); // define a radius for the tool (graphical display) tool->setRadius(0.1); // hide the device sphere. only show proxy. tool->m_deviceSphere->setShowEnabled(false); // set the physical readius of the proxy. proxyRadius = 0.1; tool->m_proxyPointForceModel->setProxyRadius(proxyRadius); // enable if objects in the scene are going to rotate of translate // or possibly collide against the tool. If the environment // is entirely static, you can set this parameter to "false" tool->m_proxyPointForceModel->m_useDynamicProxy = true; // read the scale factor between the physical workspace of the haptic // device and the virtual workspace defined for the tool double workspaceScaleFactor = tool->getWorkspaceScaleFactor(); // define a maximum stiffness that can be handled by the current // haptic device. The value is scaled to take into account the // workspace scale factor double stiffnessMax = info.m_maxForceStiffness / workspaceScaleFactor; //----------------------------------------------------------------------- // COMPOSE THE VIRTUAL SCENE //----------------------------------------------------------------------- // create a virtual mesh object = new cMesh(world); // add object to world world->addChild(object); // set the position of the object at the center of the world object->setPos(0.0, 0.0, 0.0); // Since we want to see our polygons from both sides, we disable culling. object->setUseCulling(false, true); // here we create a small cloud of triangles double ang = 0; double angStep = 5; while (ang < 360) { double radius = 0.2; double radiusStep = 0.1; double tang = ang; while (radius < 1.0) { // we create three vectors p0, p1, p2 that describe the position of the vertices cVector3d p0 = cVector3d(0.0, radius * cCosDeg(tang), radius * cSinDeg(tang)); cVector3d p1 = cVector3d(0.0, (radius + radiusStep) * cCosDeg(tang+angStep), (radius + radiusStep) * cSinDeg(tang+angStep)); cVector3d p2 = cVector3d(0.0, (radius + radiusStep) * cCosDeg(tang-angStep), (radius + radiusStep) * cSinDeg(tang-angStep)); // we generate a triangles by passing the position of the new vertices unsigned int index = object->newTriangle(p0, p1, p2); // for each triangle we define a color cColorf color; color.set(ang / 360, 1.0 - ang/360, radius); // we get a pointer to the latest created triangle cTriangle* triangle = object->getTriangle(index); // we get pointers to its respective vertices. cVertex* vertex0 = triangle->getVertex0(); cVertex* vertex1 = triangle->getVertex1(); cVertex* vertex2 = triangle->getVertex2(); // for each vertex we attribute the new color. In this example // the color is the same for all vertices, but it is of course // possible to define a specific color for each vertex vertex0->setColor(color); vertex1->setColor(color); vertex2->setColor(color); // we increment the different counters radiusStep = 1.1 * radiusStep; radius = radius + 1.2 * radiusStep; tang = tang + 0.5 * angStep; } ang = ang + 3 * angStep; } // we indicate that we ware rendering the triangle by using the specific // colors for each of them (see abov) object->setUseVertexColors(true); // compute a boundary box object->computeBoundaryBox(true); // compute collision detection algorithm object->createAABBCollisionDetector(1.01 * proxyRadius, true, false); // define a default stiffness for the object object->setStiffness(stiffnessMax, true); // define some haptic friction properties object->setFriction(0.1, 0.2, true); //----------------------------------------------------------------------- // OPEN GL - WINDOW DISPLAY //----------------------------------------------------------------------- // initialize GLUT glutInit(&argc, argv); // retrieve the resolution of the computer display and estimate the position // of the GLUT window so that it is located at the center of the screen int screenW = glutGet(GLUT_SCREEN_WIDTH); int screenH = glutGet(GLUT_SCREEN_HEIGHT); int windowPosX = (screenW - WINDOW_SIZE_W) / 2; int windowPosY = (screenH - WINDOW_SIZE_H) / 2; // initialize the OpenGL GLUT window glutInitWindowPosition(windowPosX, windowPosY); glutInitWindowSize(WINDOW_SIZE_W, WINDOW_SIZE_H); glutInitDisplayMode(GLUT_RGB | GLUT_DEPTH | GLUT_DOUBLE); glutCreateWindow(argv[0]); glutDisplayFunc(updateGraphics); glutKeyboardFunc(keySelect); glutReshapeFunc(resizeWindow); glutSetWindowTitle("CHAI 3D"); // create a mouse menu (right button) glutCreateMenu(menuSelect); glutAddMenuEntry("full screen", OPTION_FULLSCREEN); glutAddMenuEntry("window display", OPTION_WINDOWDISPLAY); glutAttachMenu(GLUT_RIGHT_BUTTON); //----------------------------------------------------------------------- // START SIMULATION //----------------------------------------------------------------------- // simulation in now running simulationRunning = true; // create a thread which starts the main haptics rendering loop cThread* hapticsThread = new cThread(); hapticsThread->set(updateHaptics, CHAI_THREAD_PRIORITY_HAPTICS); // start the main graphics rendering loop glutMainLoop(); // close everything close(); // exit return (0); }