Buenos dias gente, recurro a ustedes por un problema que estoy teniendo con
OpenGL es bastante raro e inusual el problema y ya he probado buscando
informacion en otros lados y probando diferentes alternativas sin llegar a
una explicacion de por que esta sucediendo. La cuestion es la siguiente,
explico a grandes rasgos que quiero realizar y expongo luego el codigo que
realiza lo que estoy haciendo para que puedan tener una idea mas clara a fin
de darme opiniones o detectar cosas que por encima no he obviado.

La idea es encapsualr en clases C++ widgets que se pueden dibujar con
OpenGL, para eso tengo una clase GLWidget con un metodo draw que invoca a 3
metodos virtuales preDraw, drawWidget y postDraw y ademas tiene metodos
protegidos para manejar eventos SDL, como

handleMouseButtonDownEvent(SDL_MouseButtonEvent& event),
handleMouseButtonUpEvent*SDL_MouseButtonEvent& event),

Admeas guardo en una clase estatica o global el estado de presion de las
teclas para que luego desde cada widget qeu desee verifico si una tecla esta
presionada o no ya sea al actualizar la escena. y asi con varios tipos de
ventos mas, ademas cada widget tiene un metodo virtual llamado update que se
ejecuta antes de renderizarse o dibujarse para hacer el "update" de la
escena.

Por otro lado yo tengo una clase Estatica a la Gtkmm Main que lleva una
cuenta de widgets 2d y widgets 3d registrados y se pone en un loop
procesando los eventos de mouse y teclado, para luego notificarselos a cada
widget registrado y por ultimo hace un renderizado de la escena, es decir
itera por todos los widgets 3d llamando a su update y a su draw y luego a
los widgets 2d llamando a su update y luego a su draw...

Hasta ahi todo bien, yo puedo dibujar labels, botones deterctar clickes en
botones, pero el tema sucede es que tengo un widget que dibuja una esfera
texturizada y en su metodo update hago algo asi como lo siguiente:

void GLSphereWidget::update() {
    int newTime = SDL_GetTicks();
    double deltaTime = (newTime - lastTime) / 1000.0;
    lastTime = newTime;

    double distancePrime = 0.0, alphaPrime = 0.0, betaPrime = 0.0;

    if (GLKeyManager::isKeyPressed(SDLK_LEFT)) {
        alphaPrime -= 0.5;
    }
    if (GLKeyManager::isKeyPressed(SDLK_RIGHT)) {
        alphaPrime += 0.5;
    }
    if (GLKeyManager::isKeyPressed(SDLK_DOWN)) {
        betaPrime -= 0.5;
    }
    if (GLKeyManager::isKeyPressed(SDLK_UP)) {
        betaPrime += 0.5;
    }
    if (GLKeyManager::isKeyPressed(SDLK_PAGEDOWN)) {
        distancePrime += 2.5;
    }
    if (GLKeyManager::isKeyPressed(SDLK_PAGEUP)) {
        distancePrime -= 2.5;
    }

    this->alpha += deltaTime * alphaPrime;
    this->beta += deltaTime * betaPrime;
    this->distance += deltaTime * distancePrime;

    this->alpha = (this->alpha > 2 * PI) ? this->alpha - 2 * PI :
this->alpha;
    this->alpha = (this->alpha < -2 * PI) ? this->alpha +  2 * PI :
this->alpha;
    this->beta = (this->beta > 1.0) ? 1.0 : this->beta;
    this->beta = (this->beta < -1.0) ? -1.0 : this->beta;
    this->distance = (this->distance > 2.0) ? 2.0 : this->distance;
    this->distance = (this->distance < -2.0) ? -2.0: this->distance;
}

Para actualizar el modelo, este metodo se invoca antes de dibujar, he
debuggeado y efectivamente ahi se llama.

Y tengo el siguiente codigo de dibujado del widget:

void GLSphereWidget::drawWidget() {
    glMatrixMode(GL_PROJECTION);
    // Guardo en el stack la matriz.
    glPushMatrix();
    // Cargo la identidad.
    glLoadIdentity();
    // Translado coordenadas del origen
    glTranslatef(0.0f, 0.0f, 0.0f);
    // Defino campo de vision.
    gluPerspective(60.0, 1.33, 0.1, 100.0);
    // Cargo la matriz de proyeccion.
    glMatrixMode(GL_MODELVIEW);
    // Guardo la matriz en el stack.
    glPushMatrix();
    // Cargo la identidad
    glLoadIdentity();

//  std::cerr << (this->distance * cos(this->alpha) * cos(this->beta)) << "
" << (this->distance * sin(this->alpha) * cos(this->beta)) << " " <<
(this->distance * sin(this->beta)) << std::endl;
    gluLookAt(
        this->distance * cos(this->alpha) * cos(this->beta),
        this->distance * sin(this->alpha) * cos(this->beta),
        this->distance * sin(this->beta),
        0.0, 0.0, 0.0,
        0.0, 0.0, 1.0);

    // Habilito la textura
    glBindTexture( GL_TEXTURE_2D, texture );
    glEnable(GL_TEXTURE_2D);

    glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP);
    glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP);
    glEnable(GL_TEXTURE_GEN_S);
    glEnable(GL_TEXTURE_GEN_T);
    // Dibujo esfera
    gluSphere(sphere, radius, 20, 20);
    // Deshabilito la textura
    glDisable(GL_TEXTURE_GEN_S);
    glDisable(GL_TEXTURE_GEN_T);
    glDisable(GL_TEXTURE_2D);
    // Cargo matriz.
    glPopMatrix();
    // Cargo matriz.
    glPopMatrix();
}

El tema sucede que las teclas efectivamente se detectan como pulsadas en el
update, pero solo funciona el acercamiento a la esfera el resto los ignora,
o sea sea cual sea la tecla que apriete, ya sea SDLK_LEFT, SDKL_RIGHT
SDLK_UP SDLK_DOWN las detecta como pulsadas, entra a los if
correspondientes, modifica los valores de alphaPrime, betaPrime y
distancePrime, y luego modifica acorde a alpha, beta y distance, pero la
esfera no se dibuja diferente, solo funciona el acercamiento, ya probe de
todas formas cambiando valores, harcodeando valores en los IF del update,
todo lo que se les ocurra, ademas de miles de lineas de couts y cerrs en
esos pujntos para ver que efectivamente los valores se estan modificando,
pero por alguna razon, al moemnto de dibujarla tambien imprimo los valores
alpha, beta, distance, y son los correctos pero la esfera no cambia al
dibujarse...

El codigo de dibujdo y de update funciona por separado, fueron probados como
funciones C en un ejemplo OpenGL que hice y tengo a mano asi que imagino que
ese no debe ser el problema.

Si alguien tiene alguna idea o sugerencia de por que se puede dar esto o si
necesitan mas codigo para analizar el problema no tengo inconvenientes en
subirlo.

Desde ya muchas gracias
Pablo Viva

-- 
Si yo tengo una manzana y tú tienes una manzana, luego de intercambiarlas
ambos tenemos una manzana. Si yo tengo una idea y tú tienes una idea, luego
de intercambiarlas ambos tenemos dos ideas.

Apoyando a la comunidad Open Source.

Facebook prifile:
http://www.facebook.com/profile.php?id=1244601012
Orkut prifile:
http://www.orkut.com/Profile.aspx?uid=12594853021246287134
_______________________________________________
Lista de correo Programacion.
[email protected]
http://listas.fi.uba.ar/mailman/listinfo/programacion

Responder a