Anuncios Google

Tutoriales de programación 3D para NDS: 1- Introducción al 3D

Buenos días, después de mi último fracaso (si, el pokemon), decidí aprender a programar 3D para PC, usando las librerías multiplataforma OpenGL y GLU, en C++.

Tras meses de esfuerzo propio, ya sé todo lo necesario para programar, incluso hice varios juegos, un Pong y otro de navecitas en 3D por el momento.

Y he vuelto para programar para NDS, empezando con estos tutoriales, para, sobre todo, aprender por mi parte y por los que estáis leyendo. Dejemos ya de hablar de mí y empecemos con el asunto.

Primero, unas advertencias

1- Estos tutoriales son para programar en 3D, es decir, no son recomendados para los que acaban de empezar

2- En estos tutoriales asumo que teneis instalado el devkitpro (www.devkitpro.org) y que tenéis un nivel medio de C/C++

3- Cualquier duda, pregunta o sugerencia, que la postee el este tema, no respondo MPs

4- 

Licencia de Creative Commons
Estos tutoriales 3D para NDS están licenciados en Creative Commons Reconocimiento-NoComercial-CompartirIgual 3.0 Unported License.


 

1- Especificaciones sobre el Hardware 3D de la NDS

Lo primero que hay que saber para programar 3D es la pantalla principal es la única que puede usar 3D (puede ser la superior o la inferior).

La NDS está limitada a 6500 vértices (más o menos)  por frame, procuremos no pasarnos del límite ^^

Si usas 3D en una pantalla no significa que no puedas usar 2D en ella misma, puesto que la capa 0 es la única que usa 3D, podéis usar las capas 1, 2, y 3 para 2D, además de un modo ortográfico para ponerlo encima del 3D.

Vamos a usar un sistema de coordenadas diferente que en 2D, eso es, las coordenadas XYZ, en 2D la X era el valor horizontal e Y el valor vertical, bueno pues en 3D es lo mismo solo que la Z se refiere a la profundidad, es decir, el volumen de las cosas.

 

2- Especificaciones sobre el OpenGL de la NDS

El OpenGL de la NDS no es el mismo que se usa en PC, y tampoco usan todas las funciones, o tienen algunas específicas, como glPolyFmt(), o no pueden usar el algunos buffers, o estan limitados a 4 luces, asi que cuidado, no es lo mismo.

Para iniciar el 3D hay que hacer una serie de cosas:

1- Configurar el VIDEO para que soporte 3D

2- Iniciar el OpenGL

3- Iniciar las matrices (usaremos la de modelacion, proyeccion y texturas)

4- Configurar la capa 0 para el 3D (si usar o no el antialias, color de fondo etc)

 

Después llegamos al bucle principal del juego, el while(1), donde se dibujará todo el 3D

Para empezar a dibujar en 3D hay que hacer lo siguiente:

1- Seleccionar la matriz de modelacion y borrarla.

2- Posicionar la cámara (donde mira el usuario en el espacio)

3- Lectura de teclado y tactil

 

Dentro dibujaremos lo que sea, luego para mostrar la escena 3D se hace esto:

1- Mandamos la escena 3D al VBlank para que la mande a la pantalla

2- Ejecutar el VBlank para mostrar el 3D

 

Dicho esto, la estructura de un programa en 3D es la siguiente:

 

// Includes librerias
#include <nds.h>
 
// Funcion Main
int main(){
 
   // Iniciar 3D
 
   // Bucle principal
   while(1){
        // Empieza a dibujar
 
        // Dibuja el 3D
 
        // Actualiza la pantalla y llama al VBlank
   }
 
   // Fin del programa
   return 0;
}

 

Bien, leeros bien y entended todo, porque ahora vamos a hacer nuestro primer programa en 3D

 

3- Iniciando el OpenGL

 

Ahora vamos a aprender cómo inicializar el 3D en la DS, esto tiene una serie de pasos a seguir:

 

3.1- Iniciar el video 3D

 

Tenemos que decirle al Hardware que vamos a usar 3D, para ello hacemos lo siguiente:

// INICIAMOS VIDEO 3D
 
// La pantalla que accede al 3D es la superior
lcdMainOnTop();
 
// Dile a la DS que usaremos 3D y que lo haga en la capa 0
REG_DISPCNT = (MODE_0_3D | DISPLAY_BG0_ACTIVE);
 
// Inicia los buffers
glInit();
 
// Inicia la pantalla 3D
glViewport(0, 255, 0, 191);

Fácil no? Lo que hacemos primero es seleccionar la pantalla principal, es decir, la superior o la inferior, luego, iniciamos dicha pantalla y la capa 0 para dibujar, y de paso iniciamos los buffers del OpenGL

 

3.2- Iniciar matrices del OpenGL

Luego iniciamos las 3 matrices que usaremos, la de modelado (donde dibujamos), la de proyección (perspectiva y cámara) y la de textura (donde estás las texturas), el código que usaremos será este:

 

// Inicia proyeccion (perspectiva y camara)
	glMatrixMode(GL_PROJECTION);   // Selecciona la matriz
	glLoadIdentity();              // Borrala por completo
 
	// Pon la perspectiva y camara
	gluPerspective(70.0, (float) 256.0/192.0, 0.5, 40.0);  // Perspectiva: Aspecto, inicio, final
	gluLookAt(0.0, 0.0, 1.0,    // Posicion de la camara
			  0.0, 0.0, 0.0,    // Donde mira (ojo de la camara
			  0.0, 1.0, 0.0);   // Rotacion XYZ de la camara
 
	// Inicia la matriz de textura (las coordenadas de textura) (en proximos tutoriales os hablare de esto)
	glMatrixMode(GL_TEXTURE);
	glLoadIdentity();
 
	// Inicia la matriz de modelado (donde dibujamos el 3D)
	glMatrixMode(GL_MODELVIEW);
	glLoadIdentity();

 

Primero seleccionamos la matriz, la borramos, y finalmente, la configuramos para que haga lo que queremos.

 

3.3- Configurar la capa 0 donde dibujamos

El último paso para dibujar 3D es configurar el fondo, es decir, el color que quieres, la profundidad máxima, si usas Antialias (mejorar gráficos) etc. Lo del Antialias lo veremos en el próximo tutorial.

Bien, este es el código...

// Atributos de los poligonos (os hablare de esto mas adelante
	glPolyFmt(POLY_ALPHA(31) | POLY_CULL_NONE);  // Los poligonos son opacos y se dibujan todas las caras
 
	// Configura el fondo 0
	glClearColor(0, 0, 0, 0);   // Valores RGBA15 del color de fondo (negro)
	glClearDepth(GL_MAX_DEPTH); // Profundidad maxima

 

Bueno si has llegado hasta aquí y no tienes ninguna duda, felicidades, has aprendido  a iniciar 3D, y procedemos ahora a dibujar en el bucle principal

 

4- Empezar a dibujar

Bien, ahora empezamos a dibujar, es más facil que iniciarlo, el código es el siguiente...

// Borra la matriz de modelado
	glMatrixMode(GL_MODELVIEW);
	glLoadIdentity();
 
	// Reposiciona la camara
	gluLookAt(0.0, 0.0, 1.0,    // Posicion de la camara
			  0.0, 0.0, 0.0,    // Donde mira (ojo de la camara
			  0.0, 1.0, 0.0);   // Rotacion XYZ

 

Como vimos en la parte 2 (especificaciones de OpenGL), primero eliminamos lo que hayamos dibujado antes con glLoadIdentity(); y reposicionamos la cámara, con sólo esto ya estamos listos.

 

5- Dibujando 3D

Ahora que has llegado hasta aquí, vamos a dibujar lo que queremos, pero sólo pueden ser Triángulos o Cuadrados (aunque haya algunas optativas como los TriangleStrip y demás)

 

Lo primero que hacemos para dibujar una figura 3D es decir qué dibujamos, todo con esta función:

glBegin(GLenum modo);
    modo ->
              GL_TRIANGLES - Dibuja triangulos
              GL_QUADS - Dibuja cuadrados
              GL_TRIANGLE_STRIP - Dibuja triangulos consecutivos
              GL_QUAD_STRIP - Lo mismo pero con cuadrados

Después definimos los vértices (coordenadas XYZ) para colocar el objeto, una vez decimos dónde están los vértices la figura se dibuja sola, todo con esta función

glVertex3f(float x, float y, float z);
      x- Valor X del vertice
      y- Valor Y
      z - Valor Z

 

También podemos añadirle colores a los vértices, con esta función

glColor3b(u8 r, u8 g, u8 b);
   r- Valor R del color de vertice
   g - Valor G
   b- Valor B

 

Recordad siempre que definimos el color antes que el vértice afectado.

Y para terminar, un ejemplo de cómo dibujar un triángulo 3D

// Empieza a dibujar el triangulo
	glBegin(GL_TRIANGLE);   // Si ponemos glBegin(GL_QUAD) dibujaremos un cuadrado
 
		// Define el color del vertice
		glColor3b(255, 0, 0);  // Rojo
 
		// Define el vertice
		glVertex3f(-1.0, -1.0, 0.0);
 
		// Lo mismo (color, vertice, color, vertice)
		glColor3f(0, 0, 255);
		glVertex3f(1.0, -1.0, 0.0);
 
		glColor3b(0, 255, 0);
		glVertex3f(0.0, 1.0, 0.0);

Primero decimos qué dibujamos (triangulos o cuadrados), decimos el color del vertice y su posicion, con 3 de ellos formamos un triángulo.

 

6- Mostrando la escena 3D

Esta es la última parte del tutorial, que es cómo mandar ese triángulo que dibujamos antes a la pantalla principal, este es el código:

// Manda la escena 3D al VBlank
	glFlush(0);
 
	// Espera al VBlank (refresco de pantalla)
	swiWaitForVBlank();

Primero mandamos el 3D al VBlank y el VBlank lo procesa y lo manda a la pantalla, esta es la parte más fácil del tutorial.

 

Nuestro primer programa 3D para NDS

 

Por último, voy a dar un código para que veáis cómo vamos a programar aquí, es muy simple, sólo un triángulo rotando en la pantalla superior y texto en 2D en la inferior, aquí va...

/*
 * TUTORIAL OPENGL PARA NDS
 * POR ANDRESMARGAR (INDEXALPHA9)
 * DE NDS SCENEBETA.COM
 * -------------------------------
 * ESTE TUTORIAL ES HECHO SIN ANIMO 
 * DE LUCRO, CON INTENCION DE APRENDER
 * POR PARTE DEL LECTOR Y MIA
 * -------------------------------
 * (2012-2013) Andresmargar
 */
 
// Incluir librerias NDS
#include <nds.h>           // Libreria NDS principal
#include <filesystem.h>    // Manejo del sistema de archivos
#include <stdio.h>         // Funciones de entrada y salida
#include <stdlib.h>        // Libreria STD
#include <unistd.h>        // Funcion chdir();
 
// Funciones
void Iniciar3D(void);     // Iniciar el 3D
void Empieza3D(void);     // Empezar a dibujar 3D
void Actualiza3D(void);   // Actualiza la pantalla
void Dibujar3D(void);     // Dibuja la escena 3D
 
// Variables
float rotacion_triangulo = 0.0;  // Rotacion del triangulo que dibujaremos
 
// Funcion Main(int argc, char **argv);
// Bloque principal de la aplicacion
int main(int argc, char **argv) {
 
	// Inicia el 3D superior
	Iniciar3D();
 
	// En la pantalla inferior, consola de texto
	consoleDemoInit();
	iprintf("\n Tutoriales 3D para NDS\n By Andresmargar\n\n Practica 0- Basicas del 3D\n");
 
	// Bucle principal del juego
	while(1){
		Empieza3D();   // Empieza a dibujar 3D
		Dibujar3D();   // Dibuja la escena 3D
		Actualiza3D(); // Actualiza la pantalla 3D
	}
 
	// Fin del programa, liberar memoria
	return 0;
}
 
/************* FUNCIONES *****************/
 
// Inicia el 3D
void Iniciar3D(void){
 
	/** 1- INICIAR VIDEO 3D  **/
 
	// La pantalla 3D será la superior, si pones lcdMainOnBottom() será la inferior
	lcdMainOnTop();
 
	// Inicia el video 3D y muestra la capa 0 para dibujar
	REG_DISPCNT = (MODE_0_3D | DISPLAY_BG0_ACTIVE);
 
	// Inicia el OpenGL de la NDS
	glInit();
 
	// El 3D ocupa toda la pantalla (256x192)
	glViewport(0, 0, 255, 191);
 
	/** 2- INICIAR MATRICES DEL 3D **/
 
	// Inicia proyeccion (perspectiva y camara)
	glMatrixMode(GL_PROJECTION);   // Selecciona la matriz
	glLoadIdentity();              // Borrala por completo
 
	// Pon la perspectiva y camara
	// La DS no tiene unidad de coma flotante, mas adelante os dire lo que podemos usar en su lugar
	gluPerspective(70.0, (float) 256.0/192.0, 0.5, 40.0);  // Perspectiva: Aspecto, inicio, final
	gluLookAt(0.0, 0.0, 1.0,    // Posicion de la camara
			  0.0, 0.0, 0.0,    // Donde mira (ojo de la camara
			  0.0, 1.0, 0.0);   // Rotacion XYZ de la camara
 
	// Inicia la matriz de textura (las coordenadas de textura) (en proximos tutoriales os hablare de esto)
	glMatrixMode(GL_TEXTURE);
	glLoadIdentity();
 
	// Inicia la matriz de modelado (donde dibujamos el 3D)
	glMatrixMode(GL_MODELVIEW);
	glLoadIdentity();
 
	/** 3- CONFIGURAR FONDO 3D **/
 
	// Atributos de los poligonos (os hablare de esto mas adelante
	glPolyFmt(POLY_ALPHA(31) | POLY_CULL_NONE);  // Los poligonos son opacos y se dibujan todas las caras
 
	// Configura el fondo 0
	glClearColor(0, 0, 0, 0);   // Valores RGBA15 del color de fondo (negro)
	glClearDepth(GL_MAX_DEPTH); // Profundidad maxima
}
 
// Empieza a dibujar 3D
void Empieza3D(void){
 
	// Borra la matriz de modelado
	glMatrixMode(GL_MODELVIEW);
	glLoadIdentity();
 
	// Reposiciona la camara
	gluLookAt(0.0, 0.0, 1.0,    // Posicion de la camara
			  0.0, 0.0, 0.0,    // Donde mira (ojo de la camara
			  0.0, 1.0, 0.0);   // Rotacion XYZ
 
	// Atributos de los poligonos otra vez
	glPolyFmt(POLY_ALPHA(31) | POLY_CULL_NONE);
}
 
// Actualiza el 3D
void Actualiza3D(void){
 
	// Manda la escena 3D al VBlank
	glFlush(0);
 
	// Espera al VBlank (refresco de pantalla)
	swiWaitForVBlank();
}
 
// Dibuja la escena 3D
void Dibujar3D(void){
 
	// Dibuja un triangulo de prueba
 
	// Rota el triangulo en Z
	glRotateZ(++rotacion_triangulo);
	if(rotacion_triangulo == 360) rotacion_triangulo = 0;
 
	// Empieza a dibujar el triangulo
	glBegin(GL_TRIANGLE);   // Si ponemos glBegin(GL_QUAD) dibujaremos un cuadrado
 
		// Define el color del vertice
		glColor3b(255, 0, 0);  // Rojo
 
		// Define el vertice
		glVertex3f(-1.0, -1.0, 0.0);
 
		// Lo mismo (color, vertice, color, vertice)
		glColor3f(0, 0, 255);
		glVertex3f(1.0, -1.0, 0.0);
 
		glColor3b(0, 255, 0);
		glVertex3f(0.0, 1.0, 0.0);
 
	//glEnd(); // Esto en NDS no hace nada...
}

 

Si queréis podéis descargar la plantilla para programar cualquier cosa en 3D para NDS, es ésta:

http://www.mediafire.com/?50pdb1w6y03ybsv

 

Si lo compiláis el resultado será este:

 

Dentro vienen las carpetas del proyecto, un emulador y un compilador automatizado (recordad tener devkitpro instalado para compilarlo)

 

Bueno, este es el fin de este primer tutorial, siento que haya sido taan largo pero es todo lo básico para dibujar 3D, las dudas en los comentarios, por favor.

 

El próximo tutorial dibujaremos nuestras primeros figuras, como Cubos y Priámides, y aprenderemos a usar el Antialias (mejorar gráficos).

 

Espero que os haya gustado, y hasta entonces, saludos!


~Actualmente estudiando Ingeniería de las Tecnologías de la Telecomunicación en la Escuela de Ingenieros~


Anuncios Google

Opciones de visualización de comentarios

Seleccione la forma que prefiera para mostrar los comentarios y haga clic en «Guardar las opciones» para activar los cambios.

Muy bueno el tutorial

Muy bueno el tutorial, me será util.

 

Saludos!

Mis felicitaciones, sin duda

Mis felicitaciones, sin duda uno de los mejores tutoriales que he visto en scenebeta Guiño

Imagen de Andresmargar

^^

Muchas gracias xerpi :)

Felicitaciones, que buen

Felicitaciones, que buen tutor, justo estaba pensando en ver algo de 3D y leo tu correo.

 

Imagen de Andresmargar

Gracias :D

Muchas gracias, me animas a seguir con los tutoriales :)

Opciones de visualización de comentarios

Seleccione la forma que prefiera para mostrar los comentarios y haga clic en «Guardar las opciones» para activar los cambios.