//------------------------------------------------------------------------- void MontanaRusa::draw(bool relleno,bool dibujaNormales,bool derrapa){ Malla::draw(relleno,dibujaNormales); // Dibuja la malla PV3D* fderivate = fDerivate(carPos); PV3D* sderivate = sDerivate(carPos); PV3D* Tt=fDerivate(carPos); Tt->normalize(); // Tt = C' PV3D* Bt=fderivate->crossProduct(sderivate); Bt->normalize(); // Bt = C'.C'' PV3D* Nt=Bt->crossProduct(Tt); // Nt = Bt.Tt PV3D* Ct=function(carPos); // Ct = C GLfloat m[] ={ Nt->getX(), Nt->getY(), Nt->getZ(), 0, // Se niega Bt porque al ser -Bt->getX(),-Bt->getY(),-Bt->getZ(),0, // un producto escalar es perpendicular Tt->getX(), Tt->getY(), Tt->getZ(), 0, // al plano definido por C'.C'' Ct->getX(), Ct->getY(), Ct->getZ(), 1}; // pero en sentido contrario glMatrixMode(GL_MODELVIEW); glPushMatrix(); glMultMatrixf(m); if (derrapa) glTranslated(0,0,-1.3); //glTranslated(Ct->getX(),Ct->getY(),Ct->getZ()); // lo pone en la posición pero no con la torsión necesaria car->draw(); glPopMatrix(); //deletes de los objetos ya no necesarios delete sderivate; delete fderivate; delete Tt; delete Bt; delete Nt; delete Ct; }
void buildSceneObjects() { //Cámara PV3D* eye = new PV3D(eyeX, eyeY, eyeZ, 1); PV3D* look = new PV3D(lookX, lookY, lookZ, 0); PV3D* up = new PV3D(upX, upY, upZ, 0); cam = new Camara(eye, look, up, xRight, xLeft, yTop, yBot,N,F); escena = new Escena(200.0); carDir = NONE; angleDoor = 0; //Farola light position PV3D* pFarola = escena->farolas[escena->numFarolas/2]->mt->getPos(); p1[0] = pFarola->getX(); p1[1] = pFarola->getY()+15; p1[2] = pFarola->getZ(); p1[3] = 1.0; //Car Lights Position PV3D* luz1 = escena->coche->faro1->mt->getPos(); p2[0] = luz1->getX()-1;p2[1] = luz1->getY(); p2[2]= luz1->getZ(); p2[3]= 1.0; PV3D* luz2 = escena->coche->faro2->mt->getPos(); p3[0] = luz2->getX()-1;p3[1] = luz2->getY(); p3[2]= luz2->getZ(); p3[3]= 1.0; dir2[0] = -1.0; dir2[1] = 0.0; dir2[2] = 0.0; cam->setLookAt(new PV3D(0,0,0,0), escena->coche->mt->getPos()); }
//------------------------------------------------------------------------- void MontanaRusa::build(){ GLfloat intervaloToma = 2*2*M_PI/NQ; // Hay que dar dos vueltas porque hay puntos con 2 valores Poligon *poli = new Poligon(new PV3D(),NP,tam); // un polígono del tamaño y con los lados que queremos vector<PV3D*>* puntos= poli->getVertex(); for(int i=0;i<NQ;i++){ // Esto ocurre en cada "sección" del gusano GLfloat toma=intervaloToma*i; // Este valor hace que a cada vuelta la "matriz" sea única PV3D* fderivate = fDerivate(toma); // Se calculan los valores que ayudan al cálculo de los puntos PV3D* sderivate = sDerivate(toma); PV3D* Tt=fDerivate(toma); Tt->normalize(); PV3D* Bt=fderivate->crossProduct(sderivate); Bt->normalize(); PV3D* Nt=Bt->crossProduct(Tt); PV3D* Ct=function(toma); for(int j=0;j<NP;j++){ // Esto ocurre con cada uno de los vértices del polígono int numV=NP*i+j; PV3D* clon=puntos->at(j)->clone(); // Un clon del punto del polígono para trabajar PV3D* punto=clon->matrixProduct(Nt,Bt,Tt,Ct); vertex->at(numV)=punto; // El punto recibe un identificador y siempre con sentido delete clon; } //deletes de los objetos ya no necesarios delete sderivate; delete fderivate; delete Tt; delete Bt; delete Nt; delete Ct; } // Se construyen las caras for(int numFace=0;numFace<faces->size();numFace++){ // |>Recorremos todas las caras en orden faces->at(numFace)= new Cara(4); vector<VerticeNormal*>* auxNormals= new vector<VerticeNormal*>(4); int a= (numFace) % (NP*NQ); int b= (nextVertex(numFace) )% (NP*NQ); // Teniendo cuidado de cerrar bien el círculo int c= (nextVertex(numFace) +NP)% (NP*NQ); int d= (numFace+NP)% (NP*NQ); auxNormals->at(0)=new VerticeNormal(a,numFace); auxNormals->at(1)=new VerticeNormal(b,numFace); auxNormals->at(2)=new VerticeNormal(c,numFace); auxNormals->at(3)=new VerticeNormal(d,numFace); faces->at(numFace)->setIndicesVN(auxNormals); } // Se hacen las normales for(int i=0;i<this->numFaces;i++){ normals->at(i)= this->doVectorNormalNewell(faces->at(i)); } delete poli; }
PV3D* MontanaRusa::vNormal(GLfloat t){ PV3D* bin = vBinormal(t); PV3D* tang = vTangente(t); PV3D* norm = bin->productoVectorial(tang); norm->normaliza(); return norm; }
PV3D* MontanaRusa::vBinormal(GLfloat t){ PV3D* deriv1 = new PV3D(-3 * sin(t), 6 * cos(2 * t), 3 * cos(t), 0); PV3D* deriv2 = new PV3D(-3 * cos(t), -12 * sin(2 * t), -3 * sin(t), 0); PV3D* bin = deriv1->productoVectorial(deriv2); bin->normaliza(); return bin; }
void modificarPosicionSistema(GLdouble t) { PV3D desp; //desplazamiento de la esfera y satelite en "t" GLdouble m[16]; //matriz de deplazamiento _espiral.calculaMatrizTransformacion(m, t); desp = _espiral.aplicaMatrizAPunto(m, PV3D()); _posiX_sistema = desp.get_x(); _posiZ_sistema = desp.get_z(); }
PV3D* PV3D::normaliza(){ // Same direction but module = 1 PV3D* newV = new PV3D(); GLdouble moduleVector = module(this); newV->setX((1 / moduleVector) * this->getX()); newV->setY((1 / moduleVector) * this->getY()); newV->setZ((1 / moduleVector) * this->getZ()); newV->setPV(0); //vector return newV; }
PV3D Matr::prodVect(PV3D vect){ float vectArray[4] = {vect.getX(), vect.getY(), vect.getZ(), vect.getPV()}; float vectResult[4]; for(int i=0; i<ancho; i++){ vectResult[i] = 0.0; for (int k=0; k<alto; k++){ vectResult[i] += this->data[i][k] * vectArray[k]; } } return PV3D(vectResult[0], vectResult[1], vectResult[2], vectResult[3]); }
void MontanaRusa::creaTuboFrenet(){ //Lo multiplicamos por el numero de vueltas GLfloat intervalo = 2*M_PI*2/NQ; PV3D** vertices = getVertices(); //Construimos los vertices de cada cara del tubo for(int i=0; i<NQ; i++){ GLfloat valor = i*intervalo; PV3D* T = primeraDerivada(valor); T->normaliza(); PV3D* B = primeraDerivada(valor)->productoVectorial(segundaDerivada(valor)); B->normaliza(); PV3D* N = B->productoVectorial(T); PV3D* C = funcion(valor); for(int j=0; j<NP; j++){ int indiceVertice = NP*i+j; PV3D* vertice = perfil[j]->multiplicaMatriz(N,B,T,C); vertices[indiceVertice] = vertice; } } //Construimos las caras for(int i=0; i<NQ; i++){ for (int j=0; j<NP; j++){ int indiceCara = NP*i+j; caras[indiceCara] = new Cara(4); VerticeNormal** normalesCara = new VerticeNormal*[4]; int verticeBase = indiceCara; int v0 = verticeBase % (NP*NQ); int v1 = sucesor(verticeBase % (NP*NQ)); int v2 = (sucesor(verticeBase)+NP) % (NP*NQ); int v3 = (verticeBase + NP) % (NP*NQ); normalesCara[0] = new VerticeNormal(v0,indiceCara); normalesCara[1] = new VerticeNormal(v1,indiceCara); normalesCara[2] = new VerticeNormal(v2,indiceCara); normalesCara[3] = new VerticeNormal(v3,indiceCara); caras[indiceCara]->addVerticeNormal(normalesCara); } } //Calculamos las normales de cada cara for(int i=0; i<numCaras; i++){ normales[i] = CalculoVectorNormalPorNewell(caras[i]); } }
PV3D* Malla::normalCaraNewell(Cara* cara){ PV3D* n = new PV3D(0.0, 0.0, 0.0, 0); for (int i=0; i<cara->getNumVertices(); i++) { PV3D* vertActual= perfil[cara->getIndiceVerticeK(i)]; PV3D* vertSiguiente= perfil[cara->getIndiceVerticeK((i+1) % cara->getNumVertices())]; n->setCoordenadaX(n->getCoordenadaX() + ((vertActual->getCoordenadaY() - vertSiguiente->getCoordenadaY()) * (vertActual->getCoordenadaZ() + vertSiguiente->getCoordenadaZ()))); n->setCoordenadaY(n->getCoordenadaY() + ((vertActual->getCoordenadaZ() - vertSiguiente->getCoordenadaZ()) * (vertActual->getCoordenadaX() + vertSiguiente->getCoordenadaX()))); n->setCoordenadaZ(n->getCoordenadaZ() + ((vertActual->getCoordenadaX() - vertSiguiente->getCoordenadaX()) * (vertActual->getCoordenadaY() + vertSiguiente->getCoordenadaY()))); } n->normalizarVector(); return n; }
void Malla::dibuja(){ if (this->rotateAngleX != 0 || this->rotateAngleY != 0 || this->rotateAngleZ != 0){ glMatrixMode(GL_MODELVIEW); glPushMatrix(); glRotatef(this->rotateAngleX, 1, 0, 0); glRotatef(this->rotateAngleY, 0, 1, 0); glRotatef(this->rotateAngleZ, 0, 0, 1); } for (int i = 0; i<numCaras; i++) { glLineWidth(1.0); glColor3f(cara[i]->getRed(), cara[i]->getGreen(), cara[i]->getBlue()); if (this->displayModel == 1){ glBegin(GL_POLYGON); } else if(this->displayModel == 0){ glBegin(GL_LINE_LOOP); } for (int j = 0; j < cara[i]->getNumeroVertices(); j++) { int iN = cara[i]->getIndiceNormal(j); int iV = cara[i]->getIndiceVertice(j); glNormal3f(normal[iN]->getX(), normal[iN]->getY(), normal[iN]->getZ()); //Si hubiera coordenadas de textura, aquí se suministrarían //las coordenadas de textura del vértice j con glTexCoor2f(…); glVertex3f(vertice[iV]->getX(), vertice[iV]->getY(), vertice[iV]->getZ()); } glEnd(); if (this->showN){ PV3D* centro = getCentroDeCara(*cara[i]); glBegin(GL_LINES); glColor3f(1.0 - cara[i]->getRed(), 1.0 - cara[i]->getGreen(), 1.0 - cara[i]->getBlue()); glVertex3f(centro->getX(), centro->getY(), centro->getZ()); glVertex3f(centro->getX() + normal[cara[i]->getIndiceNormal(0)]->getX(), centro->getY() + normal[cara[i]->getIndiceNormal(0)]->getY(), centro->getZ() + normal[cara[i]->getIndiceNormal(0)]->getZ()); glEnd(); } } if (this->rotateAngleX != 0 || this->rotateAngleY != 0 || this->rotateAngleZ != 0){ glPopMatrix(); } }
void key(unsigned char key, int x, int y){ float angleLamp; bool need_redisplay = true; switch (key) { case 27: /* Escape key */ //continue_in_main_loop = false; // (**) //Freeglut's sentence for stopping glut's main loop (*) glutLeaveMainLoop (); break; /*case 'a': //Eje X angleX += 1.0; break; case 'z': //Eje X angleX -= 1.0; break; case 's': //Eje Y angleY += 1.0; break; case 'x': //Eje Y angleY -= 1.0; break; case 'd': //Eje Z angleZ += 1.0; break; case 'c': //Eje Z angleZ -= 1.0; break;*/ case 'u': //roll camera.roll(0.09); //0.09 radianes = 5 grados break; case 'i': camera.roll(-0.09); break; case 'j': //yaw camera.yaw(0.01); break; case 'k': camera.yaw(-0.01); break; case 'n': //pitch camera.pitch(0.01); break; case 'm': camera.pitch(-0.01); break; case 'e': //Along axis X recorridoX = 10.0; recorridoY = 0.0; recorridoZ = 0.0; camera.recorridoEje(recorridoX, recorridoY, recorridoZ); break; case 'r': recorridoX = -10.0; recorridoY = 0.0; recorridoZ = 0.0; camera.recorridoEje(recorridoX, recorridoY, recorridoZ); break; case 'd': //Along axis Y recorridoY = 10.0; recorridoX = 0.0; recorridoZ = 0.0; camera.recorridoEje(recorridoX, recorridoY, recorridoZ); break; case 'f': recorridoY = -10.0; recorridoX = 0.0; recorridoZ = 0.0; camera.recorridoEje(recorridoX, recorridoY, recorridoZ); break; case 'c': //Along axis Z recorridoZ = 10.0; recorridoX = 0.0; recorridoY = 0.0; camera.recorridoEje(recorridoX, recorridoY, recorridoZ); break; case 'v': recorridoZ = -10.0; recorridoX = 0.0; recorridoY = 0.0; camera.recorridoEje(recorridoX, recorridoY, recorridoZ); break; case 's': //Desplazar desplazaY = 2.0; camera.desplazar(0.0, desplazaY, 0.0); break; case 'x': desplazaY = -2.0; camera.desplazar(0.0, desplazaY, 0.0); break; case '1': //Gira X //angleGiraX += 0.1; camera.giraX(0.1); break; case '2': //Gira Y //angleGiraY += 0.1; camera.giraY(0.1); break; case '3': //Gira Z //angleGiraZ += 0.1; camera.giraZ(0.1); break; case '4': //Lateral camera.lateral(); break; case '5': //Frontal camera.frontal(); break; case '6': //Cenital camera.cenital(); break; case '7': //Esquina camera.esquina(); break; case 'o': //Ortogonal glMatrixMode(GL_PROJECTION); glLoadIdentity(); glOrtho(xLeft, xRight, yBot, yTop, N, F); break; case 'p': //Perspectiva glMatrixMode(GL_PROJECTION); glLoadIdentity(); gluPerspective(45, 1, N, F); break; case 'l': //Oblicua glMatrixMode(GL_PROJECTION); glLoadIdentity(); d.normaliza(); if(d.getZ() != 0.0 && (d.getX() != 0 || d.getY() != 0 || d.getZ() != 1)){ GLfloat m[16] = { 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1 }; m[8] = -(d.getX()) / d.getZ(); m[9] = -(d.getY()) / d.getZ(); m[12] = -N * (d.getX() / d.getZ()); m[13] = -N * (d.getY() / d.getZ()); glOrtho(xLeft, xRight, yBot, yTop, N, F); glMultMatrixf(m); } break; case 'y': //Trasladar escena escena->traslacionEscena(1, 0, 0); break; case 'h': escena->traslacionEscena(-1, 0, 0); break; case 'g': //Escalacion escena escena->escalacionEscena(1, 2, 1); break; case 'b': escena->escalacionEscena(1, 0.5, 1); break; case '8': //Rotacion escena escena->rotacionEscena(2,0,1,0); break; case '9': escena->rotacionEscena(-2,0,1,0); break; case 't': //Encender/apagar luz ambiente global if(globalOn){ globalOn = false; glDisable(GL_LIGHT0); glDisable(GL_LIGHT1); glDisable(GL_LIGHT2); GLfloat amb[] = {0.0,0.0,0.0,1.0}; glLightModelfv(GL_LIGHT_MODEL_AMBIENT, amb); } else { globalOn = true; glEnable(GL_LIGHT0); glEnable(GL_LIGHT1); glEnable(GL_LIGHT2); GLfloat amb[] = {0.2,0.2,0.2,1.0}; glLightModelfv(GL_LIGHT_MODEL_AMBIENT, amb); } break; case 'a': //Escalar lámpara escena->getHijo(15)->getTAfin()->escalacion(1, 1.1, 1); escena->getHijo(15)->getTAfin()->traslacion(0, -1, 0); lampHeight *= 1.1; angleLamp = calculateLampAngle(0.5, lampHeight); glLightf(GL_LIGHT1, GL_SPOT_CUTOFF, angleLamp); break; case 'z': escena->getHijo(15)->getTAfin()->escalacion(1, 0.9, 1); escena->getHijo(15)->getTAfin()->traslacion(0, 1, 0); lampHeight *= 0.9; angleLamp = calculateLampAngle(0.5, lampHeight); glLightf(GL_LIGHT1, GL_SPOT_CUTOFF, angleLamp); break; case 'q': //Encender/apagar lámpara if(lamparaOn){ lamparaOn = false; glDisable(GL_LIGHT1); } else { lamparaOn = true; glEnable(GL_LIGHT1); } break; case 'w': // Activar/desactivar luz remota del este if(luzRemotaOn){ luzRemotaOn = false; glDisable(GL_LIGHT2); } else { luzRemotaOn = true; glEnable(GL_LIGHT2); } break; case '0': // Activar/desactivar niebla if(nieblaOn){ nieblaOn = false; glDisable(GL_FOG); } else { nieblaOn = true; glEnable(GL_FOG); } break; default: need_redisplay = false; break; } if (need_redisplay) glutPostRedisplay(); }
void choqueCoche(){ PV3D* pCoche = escena->coche->mt->getPos(); for (int i = 0; i < escena->numFarolas; i++){ Farola* f = escena->farolas[i]; PV3D* pFarola = f->mt->getPos(); if((abs(pCoche->getX()-pFarola->getX()) < 6) && (abs(pCoche->getZ()-pFarola->getZ()) < 3) && !f->caida){ f->mt->rota(90,0,0,1); f->caida = true; if(i == escena->numFarolas/2) glDisable(GL_LIGHT1); } } for (int i = 0; i < escena->numTrees; i++){ Tree* t = escena->trees[i]; PV3D* pTree = t->mt->getPos(); if((abs(pCoche->getX()-pTree->getX()) < 6) && (abs(pCoche->getZ()-pTree->getZ()) < 3) && !t->caido){ t->mt->rota(90,0,0,1); t->caido = true; } } // if(abs(pCoche->getX()) > escena->escenaSize/2 // || (abs(pCoche->getZ()) > escena->escenaSize/2)){ // escena->coche->mt->traslada(new PV3D(0,0,0,1)); // cam->setLookAt(new PV3D(5,5,5,1), escena->coche->mt->getPos()); // glutPostRedisplay(); // } }
PV3D* ParametricCurve::T(float t){ PV3D* ret; ret = Cdiff(t); ret->normalize(); return ret; }
PV3D* Malla::calculoNormalNewell(Cara* c){ GLdouble nx = 0.0; GLdouble ny = 0.0; GLdouble nz = 0.0; PV3D* verticeActual = NULL; PV3D* verticeSig = NULL; int nV = c->getNumVertices(); for(int i = 0; i < nV;i++){ verticeActual = vertices[c->getIndice(i)->get_indiceVertice()]; verticeSig = vertices[c->getIndice((i+1)%nV)->get_indiceVertice()]; nx += (verticeActual->getY()-verticeSig->getY())*(verticeActual->getZ()+verticeSig->getZ()); ny += (verticeActual->getZ()-verticeSig->getZ())*(verticeActual->getX()+verticeSig->getX()); nz += (verticeActual->getX()-verticeSig->getX())*(verticeActual->getY()+verticeSig->getY()); } PV3D* n = new PV3D(nx,ny,nz,0); n->normalizar(); return n; }
Tablero::Tablero(int largo, int alto, int ancho) { _largo = largo; _alto = alto; _ancho = ancho; _numCubos = _largo * _alto * _ancho; for (int i = 0; i < _numCubos; i++) { this->addObjeto(new Cubo()); hijos[i]->color->setColor(0.2, 0.2, 0.2); } //comienza pintando al principio de la carretara PV3D* p = new PV3D(_largo / 2, 0, 1, 1); int numCubo = 0; for (int x = 0; x < _largo; x++) { for (int y = 0; y < _alto; y++) { for (int z = 0; z < _ancho; z++) { hijos[numCubo]->mt->traslada(p); p->setZ(p->getZ()+1); numCubo++; } p->setZ(p->getZ()-_ancho); if(_alto > 1) p->setY(p->getY()+1); } if(_alto > 1) p->setY(p->getY()-_alto); p->setX(p->getX()-1); } }
void buildSceneObjects() { //objects mr = new MontanaRusa(1,15,90); mr1 = new MontanaRusa(0.95,15, 90); PV3D * p = mr->curva(0); PV3D * v = mr->vTangente(0); PV3D * n = mr->vNormal(0); // Camera parameters GLdouble eyeX = p->getX(), eyeY = p->getY(), eyeZ = p->getZ();//eyeX=100.0, eyeY=100.0, eyeZ=100.0; GLdouble lookX = eyeX + v->getX(), lookY = eyeY + v->getY(), lookZ = eyeZ + v->getZ(); GLdouble upX= n->getX(), upY = n->getY(), upZ = n->getZ();//0, upY=1, upZ=0; cam = new Camara(new PV3D(eyeX, eyeY, eyeZ, 1), new PV3D(lookX, lookY, lookZ, 1), new PV3D(upX, upY, upZ, 0));//lookAt & projection }
PV3D* Malla::vectorNormalNewell(Cara* c){ PV3D* n = new PV3D(); for(int i=0; i<c->getNumVertices(); i++){ PV3D* vertActual = vertice[c->getIndiceVerticeK(i)]; PV3D* vertSig = vertice[c->getIndiceVerticeK((i+1) % c->getNumVertices())]; n->setX(n->getX() + ((vertActual->getY() - vertSig->getY()) * (vertActual->getZ() + vertSig->getZ()))); n->setY(n->getY() + ((vertActual->getZ() - vertSig->getZ()) * (vertActual->getX() + vertSig->getX()))); n->setZ(n->getZ() + ((vertActual->getX() - vertSig->getX()) * (vertActual->getY() + vertSig->getY()))); } return n->normaliza(); }
PV3D* Malla::calculoVectorNormalPorNewell(Cara C){ PV3D* n = new PV3D(0, 0, 0, 0); for (int i = 0; i < C.getNumeroVertices(); i++){ PV3D* vertActual = vertice[C.getIndiceVertice(i)]; PV3D* vertSiguiente = vertice[C.getIndiceVertice((i + 1) % C.getNumeroVertices())]; n->setX(n->getX() + ((vertActual->getY() - vertSiguiente->getY())*(vertActual->getZ() + vertSiguiente->getZ()))); n->setY(n->getY() + ((vertActual->getZ() - vertSiguiente->getZ())*(vertActual->getX() + vertSiguiente->getX()))); // Z * X n->setZ(n->getZ() + ((vertActual->getX() - vertSiguiente->getX())*(vertActual->getY() + vertSiguiente->getY()))); // X * Y } return n->normaliza(); }
void MontanaRusa::crearMalla3(){ // |\/| // |/\| // INICIAR MALLA // Tama�os de los arrays numCaras = 4*(nQ - 1)*(nPuntosPerfil); // (nQ-1)= num de rodajas numNormales = numCaras; // una normal por cara numVertices = nQ*nPuntosPerfil + (nQ - 1)*(nPuntosPerfil); // Creaci�n de los arrays vertice = new PV3D*[numVertices]; normal = new PV3D*[numNormales]; cara = new Cara*[numCaras]; // CREAR VERTICES *************************************************************************************** // transformar: perfil => cortes // 1. vertices del poligono GLfloat t = 0; GLfloat inc = (2)*PI / (nQ - 1); for (int i = 0; i < nQ; i++){ // numero de cortes PV3D* n = vNormal(t); // t = i*inc PV3D* b = vBinormal(t); PV3D* tg = vTangente(t); for (int j = 0; j < nPuntosPerfil; j++){ // recorrer perfil i GLfloat x = n->getX()*perfil[j]->getX() + b->getX()*perfil[j]->getY() + tg->getX()*perfil[j]->getZ() + curva(t)->getX(); GLfloat y = n->getY()*perfil[j]->getX() + b->getY()*perfil[j]->getY() + tg->getY()*perfil[j]->getZ() + curva(t)->getY(); GLfloat z = n->getZ()*perfil[j]->getX() + b->getZ()*perfil[j]->getY() + tg->getZ()*perfil[j]->getZ() + curva(t)->getZ(); vertice[i*2*nPuntosPerfil + j] = new PV3D(x, y, z, 1); // vertice j del perfil i if(DEBUG) cout << "perfil " << i << " >> " << i * 2 * nPuntosPerfil + j << "\n"; } t += inc; } // 2.vertices puntos intermedios for (int i = 0; i < nQ - 1; i++){ for (int j = 0; j<nPuntosPerfil; j++) { // interm entre perfil i y i+1, int downL = i * 2 * nPuntosPerfil + j; int downR = (i + 1) * 2 * nPuntosPerfil + j; int upR = (i + 1) * 2 * nPuntosPerfil + (j + 1) % nPuntosPerfil; int upL = i * 2 * nPuntosPerfil + (j + 1) % nPuntosPerfil; int interm = i * 2 * nPuntosPerfil + nPuntosPerfil +j; PV3D** v = new PV3D*[4]; v[0] = vertice[downL]; // esquina inferior-izquierda de una cara v[1] = vertice[downR]; v[2] = vertice[upR]; v[3] = vertice[upL]; if (DEBUG) cout << "intermedio entre los perfiles " << i << " y " << i + 1 << " " << j << "\n"; // calcular intermedio[j] entre perfil i y i+1, PV3D* p = v[0]->puntoIntermN(v, 5);//puntoInterm4(v[1], v[2], v[3]); // guardar vertice[interm] = p; } // for } if (DEBUG) cout << "termina los vertices\n"; // CREAR CARAS Y NORMALES ********************************************************************************* int indiceCara = 0; for (int i = 0; i<nQ - 1; i++){ //unir el perfil i-�simo con el (i+1)-�simo con 4 triangulos if (DEBUG) cout << "dibuja triangulos entre perfiles" << i << " y " << i + 1 << "\n"; for (int j = 0; j<nPuntosPerfil; j++) { int downL = i * 2 * nPuntosPerfil + j; int downR = (i + 1) * 2 * nPuntosPerfil + j; int upR = (i + 1) * 2 * nPuntosPerfil + (j + 1) % nPuntosPerfil; int upL = i * 2 * nPuntosPerfil + (j + 1) % nPuntosPerfil; int interm = i * 2 * nPuntosPerfil + nPuntosPerfil+j; //crear triangulo 0 (^) VerticeNormal** vn_0 = new VerticeNormal*[3]; vn_0[0] = new VerticeNormal(upL, indiceCara); vn_0[1] = new VerticeNormal(interm, indiceCara); vn_0[2] = new VerticeNormal(upR, indiceCara); cara[indiceCara] = new Cara(3, vn_0); // cara PV3D* n_0 = calculoVectorNormalPorNewell(cara[indiceCara]); //Newell normal[indiceCara] = n_0; //normal indiceCara++; if (DEBUG) cout << " T-0\n"; //crear triangulo 1 (<) VerticeNormal** vn_1 = new VerticeNormal*[3]; vn_1[0] = new VerticeNormal(upL, indiceCara); vn_1[1] = new VerticeNormal(downL, indiceCara); vn_1[2] = new VerticeNormal(interm, indiceCara); cara[indiceCara] = new Cara(3, vn_1); PV3D* n_1 = calculoVectorNormalPorNewell(cara[indiceCara]); //Newell normal[indiceCara] = n_1; indiceCara++; if (DEBUG) cout << " T-1\n"; //crear triangulo 2 (v) VerticeNormal** vn_2 = new VerticeNormal*[3]; vn_2[0] = new VerticeNormal(downL, indiceCara); vn_2[1] = new VerticeNormal(downR, indiceCara); vn_2[2] = new VerticeNormal(interm, indiceCara); cara[indiceCara] = new Cara(3, vn_2); PV3D* n_2 = calculoVectorNormalPorNewell(cara[indiceCara]); //Newell normal[indiceCara] = n_2; indiceCara++; if (DEBUG) cout << " T-2\n"; //crear triangulo 3 (>) VerticeNormal** vn_3 = new VerticeNormal*[3]; vn_3[0] = new VerticeNormal(downR, indiceCara); vn_3[1] = new VerticeNormal(upR, indiceCara); vn_3[2] = new VerticeNormal(interm, indiceCara); cara[indiceCara] = new Cara(3, vn_3); PV3D* n_3 = calculoVectorNormalPorNewell(cara[indiceCara]); //Newell normal[indiceCara] = n_3; indiceCara++; if (DEBUG) cout << " T-3\n"; } //for } //for }
Matr Matr::matrizNBTC(float t){ //Calcular los valores c, c' y c'' PV3D aux = PV3D(); PV3D* c = aux.calculaValorFormula(t); PV3D* cc = aux.calculaValorPrimDerivada(t); PV3D* ccc = aux.calculaValorSegDerivada(t); //Calcular T, B y N PV3D* T = aux.calculaT(cc); PV3D* B = aux.calculaB(cc, ccc); PV3D* N = aux.calculaN(); //Recorro por columnas float data[alto][ancho]; data[0][0] = N->getX(); data[1][0] = N->getY(); data[2][0] = N->getZ(); data[3][0] = 0; data[0][1] = B->getX(); data[1][1] = B->getY(); data[2][1] = B->getZ(); data[3][1] = 0; data[0][2] = T->getX(); data[1][2] = T->getY(); data[2][2] = T->getZ(); data[3][2] = 0; data[0][3] = c->getX(); data[1][3] = c->getY(); data[2][3] = c->getZ(); data[3][3] = 1; return Matr(data); }
void key(unsigned char key, int x, int y){ bool need_redisplay = true; switch (key) { case 27: /* Escape key */ //continue_in_main_loop = false; // (**) //Freeglut's sentence for stopping glut's main loop (*) glutLeaveMainLoop (); break; // ---------------- // linea de debug::: cout<< angleX << " "<< angleY << " " <<angleZ << " "; case 't': escena->obRotate(5,0); break; case 'y': escena->obRotate(-5,0); break; // ---------------- case 'g': escena->obRotate(5,1); break; case 'h': escena->obRotate(-5,1); break; // ---------------- case 'b': escena->obRotate(5,-1); break; case ',': escena->obRotate(-5,-1); break; // ---------------- // ------ Roll case 'u': acumRoll += 0.09; camera.roll(acumRoll); break; case 'i': acumRoll += -0.09; camera.roll(acumRoll); break; // ------ Yaw case 'j': acumYaw += 0.01; acumRoll = 0; acumPitch = 0; camera.yaw(acumYaw); break; case 'k': acumYaw += -0.01; acumRoll = 0; acumPitch = 0; camera.yaw(acumYaw); break; // ------ Pitch case 'n': acumPitch += 0.01; acumRoll = 0; acumYaw = 0; camera.pitch(acumPitch); break; case 'm': acumPitch += -0.01; acumRoll = 0; acumYaw = 0; camera.pitch(acumPitch); break; // ------ Recorrido X case 'e': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.recorridoEje(10.0,0.0,0.0); break; case 'r': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.recorridoEje(-10.0,0.0,0.0); break; // ------ Recorrido Y case 'd': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.recorridoEje(0.0,10.0,0.0); break; case 'f': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.recorridoEje(0.0,-10.0,0.0); break; // ------ Recorrido Z case 'c': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.recorridoEje(0.0,0.0,10.0); break; case 'v': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.recorridoEje(0.0,0.0,-10.0); break; // ------ Desplazar X case 'q': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.desplazar(2.0,0.0,0.0); break; case 'w': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.desplazar(-2.0,0.0,0.0); break; // ------ Desplazar Y case 'a': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.desplazar(0.0,2.0,0.0); break; case 's': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.desplazar(0.0,-2.0,0.0); break; // ------ Desplazar Z case 'z': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.desplazar(0.0,0.0,2.0); break; case 'x': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.desplazar(0.0,0.0,-2.0); break; // ------ Ortogonal case 'o': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.ortogonal(xLeft,xRight,yBot,yTop,N,F); break; // ------ Perspectiva case 'p': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.perspectiva(xLeft,xRight,yBot,yTop,N,F); break; // ------ Oblicua case 'l': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.oblicua(aux.clone(),xLeft,xRight,yBot,yTop,N,F); break; // ------ Gira X case '1': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.giraX(0.1); break; // ------ Gira Y case '2': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.giraY(0.1); break; // ------ Gira Z case '3': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.giraZ(0.1); break; // ------ Vista Lateral case '4': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.lateral(); break; // ------ Vista Frontal case '5': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.frontal(); break; // ------ Vista Cenital case '6': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.cenital(); break; // ------ Vista Esquina case '7': acumRoll = 0; acumPitch = 0; acumYaw = 0; camera.esquina(); break; default: need_redisplay = false; cout<<key<<endl; break; } if (need_redisplay) glutPostRedisplay(); }
void modifCam() { //GLdouble eyeX = 100.0, eyeY = 100.0, eyeZ = 100.0; //GLdouble lookX = 0.0, lookY = 0.0, lookZ = 0.0; //GLdouble upX = 0, upY = 1, upZ = 0; PV3D * p = mr->curva(t); PV3D * v = mr->vTangente(t); PV3D * n = mr->vNormal(t); // Camera parameters GLdouble eyeX = p->getX(), eyeY = p->getY(), eyeZ = p->getZ();//eyeX=100.0, eyeY=100.0, eyeZ=100.0; GLdouble lookX = eyeX + v->getX(), lookY = eyeY + v->getY(), lookZ = eyeZ + v->getZ(); GLdouble upX = n->getX(), upY = n->getY(), upZ = n->getZ();//0, upY = 1, upZ = 0; cout << "Camara ---------------------------------------------" << t << endl; cout << "\teye: " << eyeX << " " << eyeY << " " << eyeZ << endl; cam->setEyeLookUp(new PV3D(eyeX, eyeY, eyeZ, 1), new PV3D(lookX, lookY, lookZ, 1), new PV3D(upX, upY, upZ, 0)); }
void MontanaRusa::crearMalla4(){ //INICIAR MALLA //Tama�os de los arrays numVertices = nQ*nPuntosPerfil; numCaras = (nQ - 1)*(nPuntosPerfil); // (nQ-1)= num de rodajas numNormales = numCaras; //una normal por cara //Creaci�n de los arrays vertice = new PV3D*[numVertices]; normal = new PV3D*[numNormales]; cara = new Cara*[numCaras]; //CREAR VERTICES //transformar: perfil => cortes GLfloat t = 0; GLfloat inc = (2)*PI / (nQ - 1); for (int i = 0; i < nQ; i++){//numero de cortes PV3D* n = vNormal(i*inc); //t = i*inc PV3D* b = vBinormal(i*inc); PV3D* tg = vTangente(i*inc); for (int j = 0; j < nPuntosPerfil; j++){//recorrer perfil i GLfloat x = n->getX()*perfil[j]->getX() + b->getX()*perfil[j]->getY() + tg->getX()*perfil[j]->getZ() + curva(t)->getX(); GLfloat y = n->getY()*perfil[j]->getX() + b->getY()*perfil[j]->getY() + tg->getY()*perfil[j]->getZ() + curva(t)->getY(); GLfloat z = n->getZ()*perfil[j]->getX() + b->getZ()*perfil[j]->getY() + tg->getZ()*perfil[j]->getZ() + curva(t)->getZ(); vertice[i* nPuntosPerfil + j] = new PV3D(x, y, z, 1);//vertice j del perfil i } t += inc; } //CREAR CARAS Y NORMALES int indiceCara = 0; for (int i = 0; i<nQ - 1; i++){ //unir el perfil i-�simo con el (i+1)%n-�simo for (int j = 0; j<nPuntosPerfil; j++) { //esquina inferior-izquierda de una cara int indice = i*nPuntosPerfil + j; //vertice j del perfil i VerticeNormal** vn = new VerticeNormal*[4]; vn[0] = new VerticeNormal(indice, indiceCara); vn[1] = new VerticeNormal((indice + nPuntosPerfil) % numVertices, indiceCara); vn[2] = new VerticeNormal((indice + 1 + nPuntosPerfil) % numVertices, indiceCara); vn[3] = new VerticeNormal(indice + 1, indiceCara); cara[indiceCara] = new Cara(4, vn); PV3D* n = calculoVectorNormalPorNewell(cara[indiceCara]); //Newell normal[indiceCara] = n; indiceCara++; } //for } //for }
void MontanaRusa::dibujaCoche(){ GLfloat movimiento = coche->getMovimiento(); PV3D* T = primeraDerivada(movimiento); T->normaliza(); PV3D* B = primeraDerivada(movimiento)->productoVectorial(segundaDerivada(movimiento)); B->normaliza(); PV3D* N = B->productoVectorial(T); PV3D* C = funcion(movimiento); GLfloat m[] = { N->getX(), N->getY(), N->getZ(), N->isPoint(), B->getX(), B->getY(), B->getZ(), B->isPoint(), T->getX(), T->getY(), T->getZ(), T->isPoint(), C->getX(), C->getY(), C->getZ(), C->isPoint()}; glMatrixMode(GL_MODELVIEW); glPushMatrix(); glMultMatrixf(m); coche->dibuja(); glPopMatrix(); }