sábado, 3 de noviembre de 2007

Tarea 11 (TEORIA)

Métodos de animación:

  • Forward Kinematics (Cinemática Directa)
Se le llama así al método de animación en tres dimensiones que anima modelos a partir de que las posiciones de partes particulares del modelo en un momento especificado son calculadas desde la posición y la orientación del objeto, junto con cualquier información sobre las articulaciones de un modelo con tal atributo.

Por ejemplo, si el objeto a ser animado es un brazo con un hombro que debe permanecer en una posición fija, la localización de la punta del pulgar sería calculada desde los ángulos de las articulaciones del hombro, codo, muñeca, pulgar y de los nudillos. Tres de dichas articulaciones (el hombro, la muñeca y la base del pulgar) tienen más de un grado de libertad y deben de ser tomados en cuenta. Si el modelo fuera una figura humana entera, entonces la localización del hombro también tendría que ser calculada desde otras propiedades del modelo.

  • Motion Capture (Captura de Movimientos)
Técnica para grabar digitalmente movimientos, que inició como una herramienta de análisis fotogramético en investigaciones de biomecánicas en los 1970s y 1980s y se expandió a la educación, entrenamiento de deportes y, recientemente, a la animación por computadora para el cine y los videojuegos, al madurar la tecnología.

Consiste básicamente en un actor que utiliza marcadores cerca de cada articulación para identificar el movimiento de las posiciones o los ángulos entre marcas. Las marcas acústicas, inerciales, LED, magnéticas o de reflexión son rastreadas, óptimamente al menos con un índice de al menos el doble del movimiento deseado, a posiciones submilimétricas. Un programa de captura de movimiento graba las posiciones, los ángulos, las velocidades, aceleraciones e impulsos, proveyendo así una muy acertada aproximación digital del movimiento.
  • Inverse Kinematics (Cinemática Inversa)

Consiste básicamente en determinar los parámetros de un objeto articulado y flexible (una cadena cinemática) con tal de lograr una posición deseada. La cinemática inversa también es relevante para la programación de videojuegos y la animación 3D, donde un uso común es asegurarse de que los personajes del juego se conecten al mundo físicamente, tal como lo que es aterrizar los pies firmemente sobre terreno, alinear las manos con perillas, etc.

Se define una figura articulada como un conjunto de segmentos rígidos conectados por articulaciones. El variar los ángulos de las articulaciones provee un número infinito de configuraciones. La solución al problema de animación por cinemática directa, dados estos ángulos, es la pose de la figura. La solución más complicada al problema de la cinemática inversa es hallar los ángulos de articulación dada la configuración deseada de una figura. En los casos generales, no hay una solución analítica para el problema de cinemática inversa. Sin embargo, la cinemática inversa puede ser solucionada a partir de técnicas de programación no lineales. Ciertas cadenas cinemáticas especiales – aquellas con una muñeca esférica – permiten una separación cinemática.

  • KEY FRAMES
Se definen así a los dibujos que son esenciales para definir puntos de inicio y de fin de cualquier transición que se considere suave. Se les llama “frames” (marcos) porque su posición en el tiempo se mide en marcos en un fragmento de filme. Una secuencia de key frames define cuál movimiento verá el espectador, mientras que la posición de los key frames en el filme, video o animación definen el tiempo del movimiento.

Como sólo dos o tres key frames sobre la extensión de un segundo no crea la ilusión de movimiento, los frames restantes son llenados con más dibujos, llamados “inbetweens” (intermedios).

Referencia:
http://es.wikipedia.org/wiki/Animaci%C3%B3n_por_computadora
http://en.wikipedia.org/wiki/Key_frame

viernes, 26 de octubre de 2007

Reporte Practica 7 (LABORATORIO)

¿Es posible aplicar una textura transparente , cómo?
- Se puede lograr utilizando el canala alpha en las texturas. Una iomagen normal de computadora es construida con pixeles. Cada pixel tiene un valor de colorque usualmentente es descrito por tres componentes, rojo,axul y verde. Algunso sistemas también soportan un valor alfa. El valor alfa describe cuánto del fondo debe ser mezclado (blended) con el valor del pixel actual. Describe que tan transparente es el pixel. Un pixel puede ir desde compeltamente opaco hasta completamente transparente


2.-Bajo qué parámetros la textura aplicada prevalece sobre las características de color y material de la superfcie a la cual se aplica, es decir, no se modifica

Cuando aplicamos una textura debemos especificar como queremos que se mezcle con el color del objeto.
OpenGL permite elegir entre 4 métodos, que tienen como objetivo determinar el valor RGBA final de cada pixel a visualizar a partir del color de la superficie del objeto a texturizar y del color de la textura:

- Replace (Sustitución)
- Decal (Sustitución con transparencia)
- Modulate (Modulación)
- Blend (Mezcla)

•Replace (Sustitución): En este modo el color utilizado
para el objeto es el de la textura.

•Decal: En este modo se diferencian dos casos.
Si trabajamos con formato de textura RGB el color
utilizado para el objeto es el de la textura.
En cambio, con formato de textura RGBA, el color a
utilizar es una mezcla del color de la superficie y el de la
textura, predominando más uno y otro dependiendo del
valor alpha.

•Modulate(Modulación): Permite ir escalando el color final
entre el color original de la superficie y el negro
dependiendo del grado de luminosidad de la textura (1
para color de la superficie; 0 para negro).

Blend (Mezcla): Se utiliza para mezclar los valores del
color y de transparencia de la superficie con los valores de
color y transparencia de la textura.
Cc indica el valor de las componentes R, G, B, y A
asignado con GL_TEXTURE_ENV_COLOR.


¿Qué alternativas existen a al aplicación de texturas bitmap para hacer de manera más realista las superficies? Describa al menos 5 métodos.


Mipmaps: Se guardan distintas versiones de la misma
textura, con diferentes resoluciones. Mejora el rendimiento al
utilizar versiones de menor resolución de la textura a medida
que nos alejamos. Solucionan problemas de minimización.
Tiene un consumo mayor de memoria.

Mapeo sobre el objeto:
Consiste en aplicar la textura directamente sobre el objeto.
Es el ideal para suelos, paredes y demás superficies lisas.
No suelen obtener resultados apropiados para superficies que
no sean planas.
•Mapeo en dos partes:
Para solventar los problemas que presenta el sistema anterior
se mapea primero la textura como si fuese una superficie 3D
(S-mapping), ya sea plana, cilíndrica, cúbica o esférica para
posteriormente aplicar ésta sobre la propia superficie
tridimensional (O-mapping).

Bump Mapping:La geometría del objeto no es afectada, solo se modifican sus normales para simular depresiones y picos en su superficie.
Utiliza un espacio 2D de textura, que contiene vectores normales en lugar de color.
Al mapear esta textura sobre una superficie, el vector normal de ésta se modifica según el valor encontrado en la textura.

Proyective Mapping: Consiste en la proyección de una textura en la escena como si
saliera desde un proyector de video.


referencia:
http://www.cimec.org.ar/twiki/pub/Cimec/ComputacionGrafica/texturas.ppt.pdf

lunes, 22 de octubre de 2007

Previo 8 (LABORATORIO)

1.-¿Qué es una curva/superficie paramétrica?

- Se dice que una curva es paramétrica si se puede expresar en base a una variable que varia en
un rango determinado, generalmente [ 0..n].

Las curvas paramétricas pueden ser expresadas como:


Los componentes de la curva se pueden representar como un vector

matricialmente podemos representa a una curva como:



Una superficie paramétrica es la imagen de una función o transformación r definida en una región R de un plano uv y que tiene valores en el espacio xyz. La imagen bajo r en cada punto (u,v) en R es el punto del espacio xyz con vector de posición.

r(u,v)= x(u,v), y(u,v), z(u,v)

2.-Describa lso resultados aparentes y diferencias entre las familias de curvas:

-Bézier
-Spline
-B-Spline
-β-Spline
-NURBS

-Bézier
Propuestas por Pierre Bezier (Ingeniero Fránces de Reanult)
- Utilizada para el diseño de carrocería de automóviles.
- A diferencia de Hermite que utiliza explícitamente la derivada el primer y último punto, las curvas de Bezier necesitan como restricciones cuatro puntos que son los puntos de control, que define la geometría de la curva.
- Es de fácil implementación y fácil manipulación.
- La curva interpola el primer y último punto, pero aproxima el resto de puntos.
- Los valores de las primeras derivadas paramétricas de una curva de Bezier en los extremos se
pueden calcular a partir de las coordenadas de los puntos de control como:



B-Spline: Las B-splines que se analizarán consisten en segmentos de curva cuyos coeficientes polinomiales dependen de ciertos puntos de control, lo que originará un control local. Así, mover un punto de control afectará solamente a una pequeña parte de la curva.
Las B–splines no interpola ninguno de sus puntos de control.
αB (t) = GB x MB x T



spline: un spline es una curva definida a trozos mediante polinomios. En los problemas de interpolación, se utiliza a menudo la interpolación mediante splines porque da lugar a resultados similares requiriendo solamente el uso de polinomios de bajo grado a la vez que se evitan las oscilaciones, que en la mayoría de las aplicaciones resultan indeseables, que aparecen al interpolar mediante polinomios de grado elevado. Para el ajuste de curvas, los splines se utilizan para aproximar formas complicadas. La simplicidad de la representación y la facilidad de cómputo de los splines los hacen populares para la representación de curvas en informática, particularmente en el terreno de los gráficos por ordenador.

Beta-spline A diferencia de los splines, los beta–splines poseen dos parámetros adicionales denominados bias y tensión, denotados por beta1 y beta2 respectivamente. Estos parámetros afectan de forma global a todos los segmentos (no proporcionan control local) y permiten controlar la uniformidad del spline. En general, proporcionan mayor control sobre la curva, pero se trata de un control global. Los beta-Splines poseen continuidad geométrica G2 y paramétrica C0. Si beta1 = 1, entonces la continuidad paramétrica es C1. Si incrementamos el parámetro de bias beta1 en valores mayores que 1 el spline estará más influenciado por el vector tangente a los puntos. Incrementar el parámetro de tensión beta2 hace que el spline tienda a estirarse hasta parecerse a la linea que une los puntos de control del mismo.

NURBS. Acrónimo inglés de la expresión Non Uniform Rational B-Splines. Modelo matemático muy utilizado en los gráficos por ordenador para generar y representar curvas y superficies.

Las NURBS, B-splines racionales no uniformes, son representaciones matemáticas de geometría en 3D capaces de describir cualquier forma con precisión, desde simples líneas en 2D, círculos, arcos o curvas, hasta los más complejos sólidos o superficies orgánicas de forma libre en 3D. Gracias a su flexibilidad y precisión, se pueden utilizar modelos NURBS en cualquier proceso, desde la ilustración y animación hasta la fabricación.

La geometría NURBS tiene cinco cualidades esenciales que la convierten en la opción ideal para el modelado asistido por ordenador (grado,puntos de control,nodos, nodos y puntos de control, regla del cálculo.


3.-¿Qué familias de curvas/superficies paramétricas están implementadas en opengl? ¿cómo escribimos código que las defina?

Nurbs

void dibujanurbs()
{
int i,j;
float ctrlptos[4][4][3],knots[8]={0,0,0,0,1,1,1,1};
GLUnurbsObj *pnurb=NULL; // Declaración de la variable de objeto NURB
/* Rellenado de unos puntos de control simples*/
for(i=0;i<4;i++)
for(j=0;j<4;j++)
{ ctrlptos[i][j][0]=i;ctrlptos[i][j][1]=j;ctrlptos[i][j][2]=0;}
for(i=0;i<4;i++)ctrlptos[2][i][2]=1;
/* Creacion del Objeto NURB */
pnurb=gluNewNurbsRenderer();
glEnable(GL_AUTO_NORMAL);
//glShadeModel(GL_SMOOTH);
/* Cambio de las propiedaddes del objeto, en este caso la toleracia de error se pone en 20 pixel, esto implica mas o menos poligonización en la visualización*/
gluNurbsProperty(pnurb,GLU_SAMPLING_TOLERANCE, 20.0);
/* Establecemos que quermos ver la NURB en modo alambre*/
gluNurbsProperty(pnurb, GLU_DISPLAY_MODE,GLU_OUTLINE_POLYGON);
/* Iniciamos el dibujado de la superficie NURB*/
gluBeginSurface(pnurb);
/*Damos los valores de descripcion de la NURB, en este caso 8 knots y grado de los polinomios4*/ gluNurbsSurface(pnurb,8,knots,8,knots,4*3,3,&ctrlptos,4,4,GL_MAP2_VERTEX_3);
gluEndSurface(pnurb);
/* Eliminamos el objeto nurb que creamos*/
gluDeleteNurbsRenderer(pnurb);
}


Bezier:
void dibujar_curvas_bezier()
{
int i,j;
/** Definicion del Mapeo */
glMap1f(GL_MAP1_VERTEX_3,0.0,1.0,3, n_pc_c_bezier, &pc_c_bezier[i]);
/*Habilitacion del mapeo a vertices 3D */
glEnable(GL_MAP1_VERTEX_3);
/* Especificación del numero de evaluaciones del mapeo (100 en los valores 0 y 1 del parámetro*/
glMapGrid1d(100,0,1.0);
/*Dibujado de los puntos de la curva de bezier */
glEvalMesh1(GL_LINE,0,100);
/*Tambien se podria hacer asi
glBegin(GL_LINE_STRIP);
for(j=0; j < 100;j++)
glEvalCoord1f(j/100.0);
glEnd(); */
/* Dibujado de la polilinea de control*/
glBegin(GL_LINE_STRIP);
for(j=0;j
glVertex3fv(pc_c_bezier[j]);
glEnd();
/* Dibujado de los puntos de control */
glPointSize(5.0);
glBegin(GL_POINTS);
for(j=0;j
glVertex3fv(pc_c_bezier[j]);
glEnd();
}

viernes, 19 de octubre de 2007

Tarea 8 (TEORIA)

. Algoritmo DDA (Digital Differential Analyzer)

Es un algoritmo que se basa en el cálculo y la evaluación de un DeltaX ( X) y un DeltaY( Y). Por medio de las siguientes ecuaciones:

DeltaX = DeltaY / m DeltaY = m * DeltaX

Se efectúa un muestreo de la línea en intervalos unitarios en una coordenada y se determinan los valores enteros correspondientes más próximos a la trayectoria de la línea para la siguiente coordenada.

Se aceptan como datos de entradas las dos posiciones de los pixeles correspondientes a los extremos de la línea P1(Xinicial,Yinicial) y P2(Xfinal,Yfinal). Las diferencias horizontal y vertical entre las posiciones de los extremos dados, se asignan a las varialbles DeltaX y DeltaY respectivamente. La diferencia con la mayor magnitud determina el valor del parámetro Pasos. Se procede a determinar la compensación necesaria(incremento), para generar la posición del pixel siguiente a lo largo de la trayectoria de la línea. Luego, se ilumina la posición en la pantalla. y se repite este proceso cíclico Pasos Veces, hasta obtener la línea deseada.

Leer Coordenadas P1(Xinicial, Yinicial)

Leer Coordenadas P2(Xfinal,Yfinal)

Asignar a DeltaX la diferencia de Xfinal - Xinicial

Asignar a DeltaY la diferencia de Yfinal - Yinicial

Si ABS( DeltaX) > ABS(DeltaY)

Asignar a Pasos el ABS(DeltaX)

De lo contrario

Asignar a Pasos el ABS(DeltaY)

Asignar a Xincremento el resultado de DeltaX / Pasos

Asignar a Yincremento el resultado de DeltaY / Pasos

Asignar a X el valor de Xinicial

Asignar a Y el valor de Yinicial

Iluminar pixel en coordenada X,Y

Desde k=1 hasta Pasos

Asignar a X la suma de X + Xincremento

Asignar a Y la suma de Y + Yincremento

Iluminar pixel en Coodenada X,Y

Fin de Algoritmo(DDA)

Algoritmo de Bresenham


Considerado uno de los algoritmos más efectivos para el trazo de líneas mediante rastreo. Emplea cálculos incrementales con valores enteros. La forma de determinar el siguiente pixel a iluminar en la generación de una línea, se describe a continuación: Se parte de un punto inicial P1(Xinicial, Yinicial). Luego se desplaza una columna (incrementando la posición en X)

y se traza el pixel cuyo valor de Y de la línea de rastreo se aproxima más a la trayectoria de la línea.

Se capturan los dos extremos de la línea P1(Xinicial,Yinicial) y P2(Xfinal,Yfinal), se ilumina el primer pixel correspondiente al extremo izquierdo de la línea(P1). Luego se calculan los parámetros que permitien decidir cuál será el proximo pixel a iluminar (DeltaX, DeltaY y ConstanteP). Dependiendo del valor que tome el Parámetro ConstanteP se evalúa y determina la coordenada a iluminar que puede ser: (X+1,Y) para ConstanteP <>, en caso contrario se ilumina (X+1,Y+1). El proceso anterior debe repetirse 4DeltaX veces.

Leer Coordenadas P1(Xinicial, Yinicial)

Leer Coordenadas P2(Xfinal, Yfinal)

Asignar a DeltaX el ABS( Xfinal - Xinicial)

Asignar a DeltaY el ABS( Yfinal -Yinicial)

Asignar a ConstanteP el resultado de 2*DeltaY - DeltaX

i Xinicial > Xfinal

Asignar Xfinal a X

Asignar Yfinal a Y

Asignar Xinicial a Ultimo

De lo contrario

Asignar Xinicial a X

Asignar Yinicial a Y

Asignar a Xfinal a Ultimo

Iluminar pixel en coordenada X,Y

Hacer mientras X

Asignar X + 1 a X

Si ConstanteP < style="">

Asignar ConstanteP + 2 *DeltaY a ConstanteP

De lo contrario

Asignar Y+1 a Y

Asignar a ConstanteP el resultado de ConstanteP+2 *(DeltaY-DeltaX)

Iluminar pixel en coordenada X,Y

Fin de Algoritmo (Bresenham)



  • REFERENCIA:
HTTP://agr115ues.iespana.es/guialineasrectas.doc

viernes, 12 de octubre de 2007

Reporte Practica 6 (LABORATORIO)

1.- Escriba un programa que lea un archivo de texto plano (.txt) y lo transforme a caracteres dibujados (stroke) y dibuje dicho texto en pantalla. -El texto se debe mostrar con un efecto de deslizamiento (scroll) de abajo hacia arriba (Estilo entrada de Star Wars). Usar el callback glutIdleFunc, glutSwapBuffers y el parámetro GLUT_DOUBLE. Explique cómo y dónde se usan estas funciones y constante.

glutIdleFunc se utiliza en el main, recibe como parámetro la función display (), lo que nos indica que cada vez que haya inactividad se estará llamando a la función display. Esto nos sirve para que el scroll del texto sea constante y no tener que accionarlo con algún evento en particular

GLUT_DOUBLE es un parametro que recibe el glutInitDisplayMode. Nos sirve apra tener un buffer doble quepermite que se actualicen más rápido lso frames que se mostrarán en pantalla

glutSwapBuffers se utiliza al final de la función display (), es necesario poner esta sentencia ya que estamos usando buffer doble.

código

#include
#include


char cadena[250];

char c;
int posicion;
float y;



void output3(float x, float y, char *text) //funcion para dibujar el texto
{
char *p;

glPushMatrix();
glTranslatef(x, y, 0);
glScalef(0.001, 0.004, 0.004);
for (p = text; *p; p++)
glutStrokeCharacter(GLUT_STROKE_ROMAN, *p);
glPopMatrix();
}




void display()
{

glClear(GL_COLOR_BUFFER_BIT);
glColor3f(0.0, 0.0, 1.0);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluPerspective(35.0, 1.0, 0.2, 150.0); //perspectiva



glPushMatrix();

glTranslatef(1, 0, -4);
glRotatef(-60, 1, 0, 0);
glTranslatef(0,y,0); //y es el desplazamiento

//se dibuja al texto alamacenado en el archivo
output3(-2.5, -0.6, cadena);

glPopMatrix();


glFlush();
glutSwapBuffers();

y=y+0.003; //se incrementa el desplazamiento, para dar el efecto de que se aleja el texto


}



void reshape(int w, int h)
{

glViewport(0, 0, w, h);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glScalef(1,-1,1);

glMatrixMode(GL_MODELVIEW);

}



void init() //cada vez que se inicia el programa se lee el archivo de texto
{

FILE *archivo=fopen("archivo.txt", "rw");


while((c=getc(archivo))!=EOF) //todo lo que lee lo gaurda en "cadena"
{
cadena[posicion]=c;
posicion++;
}

fclose(archivo);
}



int main(int argc, char **argv)
{

int i, msg_submenu, color_submenu;

glutInit(&argc, argv);

glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB);
glutInitWindowSize(800, 600);
glutInitWindowPosition (50, 100);
init();
glutCreateWindow("Reporte 6 Ximena");
glClearColor(0.0, 0.0, 0.0, 1.0);
glutIdleFunc(display);
glutDisplayFunc(display);
glutReshapeFunc(reshape);



glutMainLoop();

return 0;
}


martes, 2 de octubre de 2007

Previo 7 (LABORATORIO)

1.¿Que es "shading" (sombreado) en términos de computación gráfica

En computación grafica "Shading" se refiere al proceso de alterar el color basado en el angulo y la distancia en que una fuente de luz reside en un objeto, creando un efecto realista.

2.Qué es y cómo se declara y usa en OpenGL/GLUT y cuales son los atributos/caracteristicas que se pueden declarar
para manejo de:

-Un puente de luz
-Un material
-Una textura

LUZ: Para la iluminación de una escena se debe seguir lo siguiente: - Definir los vectores normales para todos los vértices de los objetos - Colocar las fuentes de luz - Elegir el tipo de luz - Escoger el tipo de material de cada objeto Primero se ejecutara el comando glEnable( GL_LIGHTING ), con esto se activan los cálculos de iluminación necesarios.
En la definición estándar hay 8 fuentes de luz desde LIGHT0 a LIGHT7. En OpenGL se pueden definir tres formas de luz distintas, estas son: AMBIENTE, DIFUSA y ESPECULAR AMBIENTE.- la luz llega de todas las direcciones de forma distribuida y es reflejada de igual forma por los polígonos de la escena. DIFUSA.- la luz llega de una fuente puntual en particular y toca la superficie con una intensidad que depende de la cara hacia la cual llega la luz, este tipo de iluminación es la que mejor define el contorno en los objetos 3D ESPECULAR.- es la luz emitida desde el objeto de forma distribuida en todas direcciones. La luz tiene las propiedades de color, posición y dirección. El color que las luces tendrán esta determinado por las tres componentes de color que maneja OpenGL, rojo, verde y azul.
El comando utilizado para especificar todas las propiedades de la luz es glLiht(), este comando tiene tres argumentos para identificar la luz que se está utilizando, la propiedad y el valor deseado para la propiedad. Después de definir las características de las luces se encienden con el comando glEnable(nombre de la fuente de luz a activar). También existe una función para desactivar la iluminación, que es glDisable y desactiva la luz especificada. Las características de la luz por default para glLight son: GL_AMBIENT, GL_DIFFUSE, GL_SPECULAR, GL_POSITION, GL_SPOT_DIRECTION, GL_SPOT_EXPONENT, GL_SPOT_CUTOFF, GL_CONSTANT_ATTENUATION, GL_LINEAR_ATTENUATION, GL_QUADRATIC_ATTENUATION. GL_DIFFUSE Y GL_ESPECULAR sólo se usan con la primera fuente de luz. GL_AMBIENT: Define los valores de la luz ambiental. Valor RGBA, su valor por defecto es (0.0,0.0,0.0,1.0) GL_DIFFUSE: Define los valores de la luz difusa. Valor RGBA. su valor por defecto es (1.0,1.0,1.0,1.0) GL_SPECULAR: Define los valores de la luz especular. Valor RGBA. Su valor por defecto es (1.0,1.0,1.0,1.0) GL_POSITION: Posición de la luz, en coordenadas { x, y, z, w }, su valor por defecto es (0.0,0.0,1.0,0.0) GL_SPOT_DIRECTION: Vector de dirección de la luz, en coordenadas { x, y, z }, su valor por defecto es (0.0,0.0,-1.0) GL_SPOT_EXPONENT: Representa la concentración de la intensidad de la luz. Valor escalar, por defecto 0. GL_SPOT_CUTOFF: Ángulo del cono de luz. Valor escalar, por defecto 180. GL_CONSTANT_ATTENUATION: Atenuación constante a aplicar a la luz según la distancia. Valor escalar, por defecto 1 GL_LINEAR_ATTENUATION: Atenuación lineal a aplicar a la luz según la distancia. Valor escalar, por defecto 0GL_QUADRATIC_ATTENUATION: Atenuación cuadrática a aplicar a la luz según la distancia. Valor escalar, por defecto 0

MAteriales:
Dependiendo de las propiedades de los materiales la luz tiene un efecto distinto sobre ellos Estas propiedades se definen con glMaterial: void glMaterial(GLenum cara, GLenum nombre, TYPOparam); El argumento cara, determina la cara del objeto en la que aplicamos las propiedades, tiene los siguientes valores: GL_FRONT,GL_BACK,GL_FRONT_AND_BACK. El siguiente indica la propiedad que va utilizarse para dicha cara, puede ser: GL_AMBIENT, GL_DIFFUSE, GL_AMBIENT_AND_DIFFUSE, GL_SPECULAR, GL_SHININESS, GL_EMISSION, GL_COLOR_INDEXES.
El ultimo parámetro especifica un puntero al valor o valores que el parámetro nombre tomara. · GL_AMBIENT .- color ambiente del material, sus valores por defecto son (0.2, 0.2, 0.2, 1.0). · GL_DIFFUSE .- color difuso del material, sus valores por defecto son (0.8, 0.8, 0.8, 1.0). · GL_AMBIENT_AND_DIFFUSE .- color ambiente y difuso del material · GL_SHININESS.- exponente especular, su valor por defecto es 0. · GL_EMISSION.- el color de emisión del material, sus valores por defecto son (0.0, 0.0, 0.0, 1.0). · GL_COLOR_INDEXES.- índice de color ambiente, difuso y especular, sus valores por defecto son (0, 1, 1).Es importante aclarar que el efecto óptico desarrollado por la luz sobre el material depende en gran forma de las características del mismo. Se complementan mutuamente dando así el efecto deseado.

Texturas:
2.¿Qué es y cómo se declara y usa en OpenGL/GLUT
El proceso de cargar la textura en memoria, no es propio de OpenGL. Se tiene que realizar una funcion externa. Existen algunas limitaciones que la librería impone. Las dimensiones de todas las texturas que carguentienen que ser potencias de 2, como por ejemplo 64x64, 128x64, etc. Se tiene que tener en cuenta que si sedebe estar dibujando en RGB, sin color indexado, o bien cargando texturas en formato RGB.
Si se carga una imagen GIF, que tiene color indexado, se tiene que programar una función extra para convertirla a RGB.. Sea cuál sea el método, al final se tendrá un puntero a un segmento de memoria que contiene la imagen: unsigned char *textura; Es importante también guardar las propiedades de la textura, en concreto sus dimensiones de ancho y alto, así como su profundidad en bits. Si estamos trabajando en RGB, la profundidad será 24bits. Los pasos a seguir son: ·

Determinamos el tamaño ·
Calculamos la memoria que será necesaria ·
Reservamos memoria ·
Generación de archivo TGA el cual viene en formato RGB.

Si no está en este formato se deberá realizar la conversión. Una vez tenemos la imagen cargada en memoria, los pasos a seguir son: · Generar la referencia para la textura. [glGenTextures (1, &textura);] Con el GLuint textura referenciaremos a "esa textura". Si se quiere tener más, se debe crear un array de GLuint. El 1 significa que sólo generamos una textura. · Referenciamos esa textura: [glBindTexture (GL_TEXTURE_2D, textura);].

Esta función dice que ahora en adelante, todas las operaciones que afecten al manejo de texturas se aplicarán sobre esa textura. En este caso es una etextura 2D · Especificamos los filtros para esa textura: o glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,GL_LINEAR_MIPMAP_NEAREST); · OpenGL puede aplicar filtros a las texturas para mejorar su visualización. La primer línea especifica el filtro a utilizar en caso de que las textura se vea más grande de lo que en realidad es (Aumento). La segunda, especifica el filtro para el caso de que la textura se vea más pequeña de lo que en realidad es. Aquí utilizamos un filtro LINEAR para el 1er caso y del segundo hablaremos más adelante.
Otro valor que podríamos haber utilizado es el GL_NEAREST, que es un filtro peor pero más rápido · Creamos la textura por medio de MIPMAPS para mejor rendimiento, en vez de filtrar las textura dinámicamente, al crear un mipmap, creamos varias texturas de diferentes tamaños (del original hacia más pequeño). OpenGL, decidirá en función de lo lejano que esté el objeto con esa textura, de qué mipmap utilizar.

Por ultimo, sólo hace falta habilitar el empleo de texturas con:
glEnable(GL_TEXTURE_2D);
En la función init_gl. TRANSFORMACIÓN DE LA TEXTURA Para la generación de la imagen TGA en memoria. El TGA debe cumplir las siguientes características:

· Ser de 24 bits
· Canal ALPHA. (32 bits) y SIN COMPRIMIR
· El tamaño debe ser cuadrado (x=y) y 32x32 o 64x64 o 128x128 o 256x256

Si se cumple todo lo anterior, devuelve un puntero a la imagen y el tamaño de la imagen MAPEO DE TEXTURAS PARA TEXTURAS 1D •Para definir la textura: • void glTexImage1D (GLenum objetivo, GLint nivel, • GLint componentes, GLsizei ancho, GLint borde, GLenum formato, GLenum tipo, const GLvoid *pixels) •donde: –objetivo vale siempre GL_TEXTURE_1D –nivel indica el nivel de detalle (0 para texturas individuales) –componentes vale 1 (modo índice), 3 (RGB) ó 4 (RGBA) –ancho indica el ancho en pixel del mapa de textura (debe ser potencia de 2) –borde indica el número de pixels que forman el borde de la textura (0, 1 ó 2) –formato indica el formato de los pixels: GL_RED, GL_RGB, GL_LUMINANCE –tipo indica el tipo de dato de los pixels: GL_UNSIGNED_INT, GL_FLOAT –pixels es un puntero a los pixels de la textura MAPEO PARA TEXTURAS 2D •Para definir la textura:
• void glTexImage2D (GLenum objetivo, GLint nivel,
• GLint componentes, GLsizei ancho, GLsizei alto,
• GLint borde, GLenum formato, GLenum tipo,
• const GLvoid *pixels) •donde: –objetivo vale siempre GL_TEXTURE_2D –nivel indica el nivel de detalle (0 para texturas individuales) –componentes vale 1 (modo índice o luminancia), 3 (RGB) ó 4 (RGBA) –ancho indica el ancho en pixels del mapa de textura (debe ser potencia de 2) –alto indica el alto en pixels del mapa de textura (debe ser potencia de 2) –borde indica el número de pixels que forman el borde de la textura (0, 1 ó 2) –formato indica el formato de los pixels: GL_RED, GL_RGB, GL_LUMINANCE –tipo indica el tipo de dato de los pixels: GL_UNSIGNED_INT, GL_FLOAT –pixels es un puntero a los pixels de la textura MAPEO DE TEXTURAS EN UNA SUPERFICIE •Al mapear la imagen de textura sobre una superficie, los texels no se van a corresponder exactamente con los pixels Magnificación : Si la superficie es mayor que la textura, cada pixel se corresponderá con un trozo pequeño de texel Minificación : Si la superficie es menor que la textura, cada pixel se corresponderá con una conjunto de texels contiguos
• Modos de mapeo
•Para establecer el modo de mapeo:
• glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GLint valor)
• donde valor puede tomar 3 valores: –GL_DECAL: el valor del texel se copia directamente al pixel –GL_MODULATE: el valor del texel se escala por el color del objeto –GL_BLEND: el valor del texel se usa para interpolar entre el color del objeto y un color constante definido para la textura, mediante la función
• glTexEnvfv(GL_TEXTURE_ENV,GL_TEXTURE_ENV_COLOR,GLfloat color[4]) MODOS DE APLICACIÓN DE TEXTURAS GL TEXTURE WRAP S Establece el parámetro wrap para la coordenada de textura s a GL_CLAMP, GL_CLAMP_TO_EDGE, o GL_REPEAT. GL_CLAMP causa que las coordenadas s estén limitadas al rango [0,1] y es útil para prevenir artefactos de envoltura (compresión?) cuando se mapea una única imagen en un objeto.
GL_CLAMP_TO_EDGE causa que las coordenadas s se limiten al rango [1/2n, 1-(1/2n)i], donde n es el tamaño de la textura en la dirección del límite. GL_REPEAT causa que la parte entera de s se ignore; el GL utiliza solo la parte fraccionaria, creando por lo tanto un patrón repetitivo. Los elementos de textura de borde son accesados solo si la envoltura se establece a GL_CLAMP. Inicialmente, GL_TEXTURE­_WRAP_S se establece a GL_REPEAT. GL TEXTURE WRAP T Establece el parámetro wrap para la coordenada de textura t a GL_CLAMP, GL_CLAMP_TO_EDGE, o GL_REPEAT (véase arriba). Inicialmente, GL_TEXTURE_WRAP_T se establece a GL_REPEAT.

3.- -Dibuje un cubo y asigne caracteristicas de material que lo hagan verse
como de madera.
-Aplique una textura de madera al cubo(bitmap).
-Aplique como textura su fotografia.
El cambio de modo se hará con click del mouse.

código:

#include
#include
#include "bitmap.h"


static int spinx = 0;
static int spiny = 0;
static int p1 = 1;
static int p2 = 1;
static int ry,rx,rz;
BITMAPINFO *TexInfo; /* Texture bitmap information */
GLubyte *TexBits; /* Texture bitmap pixel bits */


void init(void)
{
glClearColor (0.0, 0.0, 0.0, 0.0);
glShadeModel (GL_SMOOTH);
glEnable(GL_LIGHTING);
glEnable(GL_LIGHT0);
glEnable(GL_LIGHT1);
glEnable(GL_DEPTH_TEST);
}

void display(void)
{
/*Matrices para la luz*/
GLfloat position[] = { 0.0, 0.0, 2.5, 0.0 };
GLfloat position2[] = { 0.0, 3.0, 3.0, 0.0 };
GLfloat light_ambient[]={0.4, 0.4, 0.4, 1.0};
GLfloat light_diffuse[]={0.4, 0.4, 0.4, 1.0};
GLfloat light_specular[]={0.8, 0.8, 0.8, 1.0};
/*Matrices para materiales*/
GLfloat no_mat[] = {0.0,0.0,0.0,1.0};
GLfloat mat_ambient[] = {0.7,0.7,0.7,1.0};
GLfloat mat_ambient_color[] = {0.8,0.8,0.2,1.0};
GLfloat mat_diffuse[] = {0.1,0.5,0.8,1.0};
GLfloat mat_specular[] = {1.0,1.0,1.0,1.0};
GLfloat no_shininess[] = {0.0};
GLfloat low_shininess[] = {5.0};
GLfloat high_shininess[] = {100.0};
GLfloat mat_emission[] = {0.3,0.2,0.2,1.0};

GLfloat mat_amb_diff[] = {0.1, 0.5, 0.8, 1.0};
GLfloat mat_amb_diff2[] = {1.0, 0.1, 0.1, 1.0};
GLfloat mat_emission1[] = {0.3,0.8,0.2,1.0};



glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glPushMatrix ();
//gluLookAt (6.0, 6.0, 8.0, 2.0, 3.0, 0.0, 0.0, 1.0, 0.0);
gluLookAt (-7.0, 7.0, 7.0, 2.0, 0.0, 0.0, 0.0, 1.0, 0.0);

/*luz 0*/
glPushMatrix ();
glRotated ((GLdouble) spinx, 1.0, 0.0, 0.0);
glRotated ((GLdouble) spiny, 0.0, 1.0, 0.0);
glLightfv (GL_LIGHT0, GL_POSITION, position);


glTranslated (0.0, 0.0,2.5 );
glDisable (GL_LIGHTING);
glColor3f (1.0, 1.0, 1.0);
//glutWireCube (0.1);
glEnable (GL_LIGHTING);
glPopMatrix ();
/*fin luz 0*/

/*luz 1*/
glPushMatrix ();
glLightfv (GL_LIGHT1, GL_POSITION, position2);
glLightfv (GL_LIGHT1, GL_AMBIENT, light_ambient);//GL_DIFFUSE
glLightfv (GL_LIGHT1, GL_DIFFUSE, light_diffuse);
glLightfv (GL_LIGHT1, GL_SPECULAR, light_specular);

glTranslated (0.0,2.5,2.5);
glDisable (GL_LIGHTING);
glColor3f (1.0, 1.0, 1.0);
//glutWireCube (0.1);
glEnable (GL_LIGHTING);
glPopMatrix ();
/*fin luz 1*/

/*cubo materiales*/



/*fin cubo de materiales*/

//Despliegue del cubo con imagenes

glPushMatrix();

glTranslated (-2.0, 3.5,3.5 );
glRotatef(rx,1.0,0.0,0.0);
glRotatef(ry,0.0,1.0,0.0);
glRotatef(rz,0.0,0.0,1.0);
glColor3f(1.0, 1.0, 1.0);

//se activa el mapeado de texturas
glEnable(GL_TEXTURE_2D);
//Despliegue de primer textura
TexBits = LoadDIBitmap("Ximena.bmp", &TexInfo);
glTexImage2D(GL_TEXTURE_2D, 0, 3, TexInfo->bmiHeader.biWidth,
TexInfo->bmiHeader.biHeight, 0, GL_RGB,
GL_UNSIGNED_BYTE, TexBits);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
//Fin despliegue primer textura
glBegin(GL_QUADS);
glNormal3f(0.0,0.0,1.0);
glTexCoord2f(1.0,1.0); glVertex3f(0.5,0.5,0.5);
glTexCoord2f(0.0,1.0); glVertex3f(-0.5,0.5,0.5);
glTexCoord2f(0.0,0.0); glVertex3f(-0.5,-0.5,0.5);
glTexCoord2f(1.0,0.0); glVertex3f(0.5,-0.5,0.5);
glEnd();
glDisable(GL_TEXTURE_2D);
glEnable(GL_TEXTURE_2D);
//Despliegue de segunda textura
TexBits = LoadDIBitmap("Ximena.bmp", &TexInfo);
glTexImage2D(GL_TEXTURE_2D, 0, 3, TexInfo->bmiHeader.biWidth,
TexInfo->bmiHeader.biHeight, 0, GL_RGB,
GL_UNSIGNED_BYTE, TexBits);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
//Fin despliegue segunda textura
glBegin(GL_QUADS);
glNormal3f(0.0,0.0,-1.0);
glTexCoord2f(1.0,1.0); glVertex3f(-0.5,0.5,-0.5);
glTexCoord2f(0.0,1.0); glVertex3f( 0.5,0.5,-0.5);
glTexCoord2f(0.0,0.0); glVertex3f(0.5,-0.5,-0.5);
glTexCoord2f(1.0,0.0); glVertex3f(-0.5,-0.5,-0.5);
glEnd();
glDisable(GL_TEXTURE_2D);
glEnable(GL_TEXTURE_2D);
//Despliegue de tercera textura
TexBits = LoadDIBitmap("Ximena.bmp", &TexInfo);
glTexImage2D(GL_TEXTURE_2D, 0, 3, TexInfo->bmiHeader.biWidth,
TexInfo->bmiHeader.biHeight, 0, GL_RGB,
GL_UNSIGNED_BYTE, TexBits);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
//Fin despliegue tercera textura
glBegin(GL_QUADS);
glNormal3f(-1.0,0.0,0.0);
glTexCoord2f(1.0,1.0); glVertex3f(-0.5,0.5,0.5);
glTexCoord2f(0.0,1.0); glVertex3f(-0.5,0.5,-0.5);
glTexCoord2f(0.0,0.0); glVertex3f(-0.5,-0.5,-0.5);
glTexCoord2f(1.0,0.0); glVertex3f(-0.5,-0.5,0.5);
glEnd();
glDisable(GL_TEXTURE_2D);
glEnable(GL_TEXTURE_2D);
//Despliegue de cuarta textura
TexBits = LoadDIBitmap("Ximena.bmp", &TexInfo);
glTexImage2D(GL_TEXTURE_2D, 0, 3, TexInfo->bmiHeader.biWidth,
TexInfo->bmiHeader.biHeight, 0, GL_RGB,
GL_UNSIGNED_BYTE, TexBits);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
//Fin despliegue cuarta textura
glBegin(GL_QUADS);
glNormal3f(1.0,0.0,0.0);
glTexCoord2f(0.0,1.0); glVertex3f(0.5,0.5,0.5);
glTexCoord2f(0.0,0.0); glVertex3f(0.5,-0.5,0.5);
glTexCoord2f(1.0,0.0); glVertex3f( 0.5,-0.5,-0.5);
glTexCoord2f(1.0,1.0); glVertex3f(0.5,0.5,-0.5);
glEnd();
glDisable(GL_TEXTURE_2D);
glEnable(GL_TEXTURE_2D);
//Despliegue de quinta textura
TexBits = LoadDIBitmap("Ximena.bmp", &TexInfo);
glTexImage2D(GL_TEXTURE_2D, 0, 3, TexInfo->bmiHeader.biWidth,
TexInfo->bmiHeader.biHeight, 0, GL_RGB,
GL_UNSIGNED_BYTE, TexBits);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
//Fin despliegue quinta textura
glBegin(GL_QUADS);
glNormal3f(0.0,1.0,0.0);
glTexCoord2f(0.0,1.0); glVertex3f(-0.5,0.5,-0.5);
glTexCoord2f(0.0,0.0); glVertex3f(-0.5,0.5,0.5);
glTexCoord2f(1.0,0.0); glVertex3f(0.5,0.5,0.5);
glTexCoord2f(1.0,1.0); glVertex3f( 0.5,0.5,-0.5);
glEnd();
glDisable(GL_TEXTURE_2D);
glEnable(GL_TEXTURE_2D);
//Despliegue de sexta textura
TexBits = LoadDIBitmap("Ximena.bmp", &TexInfo);
glTexImage2D(GL_TEXTURE_2D, 0, 3, TexInfo->bmiHeader.biWidth,
TexInfo->bmiHeader.biHeight, 0, GL_RGB,
GL_UNSIGNED_BYTE, TexBits);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
//Fin despliegue sexta textura
glBegin(GL_QUADS);
glNormal3f(0.0,-1.0,0.0);
glTexCoord2f(0.0,0.0); glVertex3f(0.5,-0.5,-0.5);
glTexCoord2f(1.0,0.0); glVertex3f(-0.5,-0.5,-0.5);
glTexCoord2f(1.0,1.0); glVertex3f(-0.5,-0.5,0.5);
glTexCoord2f(0.0,1.0); glVertex3f(0.5,-0.5,0.5);
glEnd();
glDisable(GL_TEXTURE_2D);
glutSwapBuffers() ;
glPopMatrix();
//Fin del despliegue del cubo con imagenes

glPopMatrix ();
glFlush ();
}

void reshape (int w, int h)
{
glViewport (0, 0, (GLsizei) w, (GLsizei) h);
glMatrixMode (GL_PROJECTION);
glLoadIdentity();
gluPerspective(40.0, (GLfloat) w/(GLfloat) h, 1.0, 20.0);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
}

/* ARGSUSED2 */
void mouse(int button, int state, int x, int y)
{
switch (button) {
case GLUT_LEFT_BUTTON:
if (state == GLUT_DOWN) {
if (p1 == 1)
{
glDisable(GL_LIGHT0);
p1 = 0;
glutPostRedisplay();
}
else
{
glEnable(GL_LIGHT0);
p1 = 1;
glutPostRedisplay();
}
}
break;
case GLUT_RIGHT_BUTTON:
if (state == GLUT_DOWN) {
if (p1 == 1)
{
glDisable(GL_LIGHT1);
p1 = 0;
glutPostRedisplay();
}
else
{
glEnable(GL_LIGHT1);
p1 = 1;
glutPostRedisplay();
}
}
break;
default:
break;
}
}
void special(int key, int x, int y)
{
switch (key)
{
case GLUT_KEY_RIGHT:
spiny = (spiny + 3) % 360;
glutPostRedisplay();
break;
case GLUT_KEY_LEFT:
spiny = (spiny - 3) % 360;
glutPostRedisplay();
break;
case GLUT_KEY_UP:
spinx = (spinx - 3) % 360;
glutPostRedisplay();
break;
case GLUT_KEY_DOWN:
spinx = (spinx + 3) % 360;
glutPostRedisplay();
break;
default:
break;
}
}
void keyboard(unsigned char key, int x, int y)
{
switch (key) {
case 27:
exit(0);
break;
case 'a':
ry = (ry + 3)%360;
glutPostRedisplay();
break;
case 's':
rx = (rx + 3)%360;
glutPostRedisplay();
break;
case 'd':
rz = (rz + 3)%360;
glutPostRedisplay();
break;
case 'p':
spinx = 0;
spiny = 0;
rx = 0;
rz = 0;
ry = 0;
glEnable(GL_LIGHT0);
glEnable(GL_LIGHT1);
glutPostRedisplay();
break;

}
}

int main(int argc, char** argv)
{
glutInit(&argc, argv);
glutInitDisplayMode (GLUT_SINGLE | GLUT_RGB | GLUT_DEPTH);
glutInitWindowSize (600, 600);
glutInitWindowPosition (200, 100);
glutCreateWindow ("CuBo" );
init ();
glutDisplayFunc(display);
glutReshapeFunc(reshape);
glutMouseFunc(mouse);
glutKeyboardFunc(keyboard);
glutSpecialFunc(special);
glutMainLoop();
return 0;
}