Mostrando entradas con la etiqueta corona. Mostrar todas las entradas
Mostrando entradas con la etiqueta corona. Mostrar todas las entradas

domingo, 29 de abril de 2012

Arnow2D: Capturas de pantalla y uso de teclado


Artículo perteneciente a la sección de motores gráficos



Hola a todos...

Este capitulo se basa en explicar como hacer una captura de pantalla desde nuestro motor gráfico , así como usar el teclado con GLFW para activar dicha captura.

La captura de pantalla la realizaremos pidiendole a OpenGL que nos dé el buffer donde se pinta la pantalla y cargandolo mediante corona como si fuera una textura, para despues , mediante esta libreria grabarlo en un fichero.

La lectura de teclado se hace directamente mediante GLFW con la función: glfwGetKey

Así pues, vamos a mirar el código:


char data[1024*1024*4];

void A2D_Capture(char  *file)
{
int i;
corona::Image* imagen=NULL;

glReadPixels(0,0,1024,768, GL_RGBA , GL_BYTE, data);

for(i = 3 ; i<1024*768*4; i+=4)
data[i] = 255;

imagen = corona::CreateImage(1024,768,corona::PF_R8G8B8A8,data);
imagen = corona::FlipImage(imagen,corona::CA_X);
corona::SaveImage(file,corona::FF_AUTODETECT,imagen);
delete(imagen);
}

Como podeis observar: glReadPIxels nos devuelve en el vector data, toda la información correspondiente a la pantalla.

Este código:

for(i = 3 ; i<1024*768*4; i+=4)
data[i] = 255;

Es un apaño para que la imagen resultante me salga más luminosa (es el parametro de alpha).No se por que la imagen me salia todo oscurecida...si alguien tiene propuestas para hacerlo mejor que me lo diga.

Con este código invertimos la imagen en el eje x (el formato de imagen no es el mismo)
imagen = corona::FlipImage(imagen,corona::CA_X);

Y finalmente con este código grabamos el archivo en cuestión:
corona::SaveImage(file,corona::FF_AUTODETECT,imagen);


Finalmente solo nos queda hacer la llamada a esta función cuando el usuario le de a la tecla F12:

void Draw(void)
{
A2D_Draw(0,0,graf[0]);
A2D_Draw(500,0,graf[1]);
A2D_Draw(0,300,graf[2]);
A2D_Draw(500,300,graf[3]);

if ( glfwGetKey(GLFW_KEY_F12) )
{
A2D_Capture("A2DShot.png");
}
}

Y con esto os dejo hasta el siguiente capitulo...

Espero que os haya gustado y hagáis aprendido.

Nos vemos

LordPakusBlog

miércoles, 8 de junio de 2011

GameEngine: Capitulo 6 . Texture Manager

Hola a todos,

Bienvenidos a una nueva entrega sobre como hacer tu propio game engine desde 0.

En este capítulo explicaremos la implementación del texture manager. A grandes rasgos es lo mismo que el soundmanager pero para texturas. Es decir, cargaremos las texturas mediante un archivo de loading y accederemos a ellas mediante tags.

La carga de texturas (por ahora) la implementaremos con SOIL (quien quiera hacerlo con otra libreria y pasarmelo , yo se lo publico). La libreria SOIL es una manera muy potente de cargar texturas para su uso en 2D/3D . Os la podeis bajar de aquí 

Como unir SOIL al proyecto.
Una vez tengáis instalada la librería (mirad por Internet, no os lo voy ha hacer yo todo :D ) tendremos que linkarla al proyecto. Como ya hicimos en algún capítulo anterior:
1.propiedades de proyecto > C/C++ > Directorios de inclusión adicionales > “la ruta donde tengais instalados los .h de SOIL”
2. propiedades de proyecto > Vinculador>.Entrada > Dependencias adicionales : SOIL.lib

Con esto os deberia de funcionar todo. Si teneis problemas poned un comentario en este post y lo miraremos.

Como implementar el TextureManager
El texture manager se compone de un .h y un .cpp c on una estructura interna muy parecida al Sound Manager , así como de cambios en el GraphicsManager (inicialización , carga, descarga ,etc..) y en el Graphics3DManager (texturizaremos el cubo que teniamos hasta ahora con un gráfico de madera)

El código es el siguiente:
TextureManager.h:
/**************************************************************************************************/
// Código creado por F.Bordas (LordPakus) como ejemplo de creación de un game engine
// para el blog LordPakus (http://lordpakus.blogspot.com/).
// Prohibida la distribución fuera de este blog sin el permiso expreso del autor
/**************************************************************************************************/

/**************************************************************************************************/
// TextureManager.h : Código del gestor de texturas del game engine
// El código del cargador de texturas se obtiene de http://www.lonesock.net/soil.html
/**************************************************************************************************/

#ifndef __TextureManager__
#define __TextureManager__

#include "MyGL.h"
#include "FileManager.h" //Sirve para cargar el archivo de loading de texturas

#define MAX_ELEMENTS_LOADED 256 //por ahora hardcodeado, lo arreglaremos en algún momento.


class TextureManager
{
private:
// Constructor y destructor de la clase
static TextureManager instance;
TextureManager();
~TextureManager();

public:
static TextureManager& singleton();

public:
//Funcion para inicializar el motor de sonido
void Init(int* argc, char* argv[]);

//Funcion para desinicializar el motor de sonido
void DeInit();

public:
int LoadTexture( char cad[] );
void Texture(char id[]);

private:
FileManager filemanager;

char loaded[MAX_ELEMENTS_LOADED][256]; //Matriz donde guardamos los identificadores de textura y sus indices.

};


#endif // __FileManager__


TextureManager.cpp:
/**************************************************************************************************/
// Código creado por F.Bordas (LordPakus) como ejemplo de creación de un game engine
// para el blog LordPakus (http://lordpakus.blogspot.com/).
// Prohibida la distribución fuera de este blog sin el permiso expreso del autor
/**************************************************************************************************/

/**************************************************************************************************/
// TextureManager.cpp : Código del gestor de texturas del game engine
// El código del cargador de texturas se obtiene de http://www.lonesock.net/soil.html
/**************************************************************************************************/
#include "TextureManager.h"
#include "MyGL.h"

#include <SOIL/SOIL.h> //Libreria usada para cargar texturas

#include <iostream> //Usada para imprimir por consola

using namespace std;

//Instancia única del sound manager
TextureManager TextureManager::instance;

TextureManager::TextureManager()
{
}

TextureManager::~TextureManager()
{
}

//Devolvemos el puntero al singleton
TextureManager& TextureManager::singleton()
{
return instance;
}

//Sounds functions
void TextureManager::Init(int* argc, char* argv[])
{
char cad[256]; //Cadena donde guardaremos cada linea que leamos
char id[256]; //Cadena donde guardaremos el identificador de cada recurso
char ruta[256]; //Cadena donde guardaremos la ruta de cada recurso
int num_id; //número que nos asigna la función de carga del recurso.... un -1 significa que no lo ha podido cargar

cout << "Inicializamos el texture manager\n";

//alutInit(argc, argv) ;

filemanager.Init("Data\\LoadTexture.txt");


//Todo este código tendrá que ir al filemanager, pero por el momento lo dejamos aquí
//Leemos cada linea del archivo
while( filemanager.GetLine(cad) )
{
for( int i = 0 ; i < strlen(cad); ++i)
{
if ( cad[i] == '=' )
{
cad[i]='\0';
sprintf(id,"%s",cad);
sprintf(ruta,"%s",&cad[i+1]);
i = 257;
}
}

num_id = LoadTexture(ruta); //Cargamos el recurso
cout << "Intentamos cargar textura con ruta:" << ruta << "\n";

if (num_id == -1) //Si el recurso no se ha podido cargar, vamos a cargar el siguiente recurso
continue;

cout << "textura cargada con identificadores:" << id << " " << num_id << "\n";

sprintf( loaded[ num_id ] ,"%s" , id ); //Nos guardamos la referencia al recurso
}
}

void TextureManager::DeInit()
{
cout << "Desinicializamos el texture manager\n";
filemanager.DeInit();
}


//Carga el sonido cad y devuelve su posición en la que se ha guardado
int TextureManager::LoadTexture( char cad[] )
{
//TODO : Evaluar los casos en los que el archivo no se puede cargar y devolver un -1 en consecuencia
return ( SOIL_load_OGL_texture(
cad,
SOIL_LOAD_AUTO,
SOIL_CREATE_NEW_ID,
SOIL_FLAG_MIPMAPS | SOIL_FLAG_INVERT_Y | SOIL_FLAG_NTSC_SAFE_RGB | SOIL_FLAG_COMPRESS_TO_DXT)
);
}

//Función usada para seleccionar una textura en especial
void TextureManager::Texture(char id[])
{
int i; //Iterador
for ( i = 0 ; i < MAX_ELEMENTS_LOADED ; ++i ) //Para cada elemento cargado
{
if( !strcmp(loaded[i],id) ) //Hemos encontrado la cadena que nos interesa
{
continue;
}
}

if ( i == MAX_ELEMENTS_LOADED)
return;

//Texturizamos
glBindTexture(GL_TEXTURE_2D, i);
glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT );
glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT );

}

GraphicsManager.cpp:
/**************************************************************************************************/
// Código creado por F.Bordas (LordPakus) como ejemplo de creación de un game engine
// para el blog LordPakus (http://lordpakus.blogspot.com/).
// Prohibida la distribución fuera de este blog sin el permiso expreso del autor
/**************************************************************************************************/

/**************************************************************************************************/
// GraphicsManager.cpp : Código del motor gráfico.
/**************************************************************************************************/

#include "GraphicsManager.h"
#include "MyGL.h"

#include "Graphics3DManager.h" //Parte de 3D del motor gráfico
#include "TextureManager.h" //Inclusión del motor de texturas

#include <iostream> //Usada para imprimir por consola

using namespace std;

//Instancia única del graphics manager
GraphicsManager GraphicsManager::instance;

//Constructor
GraphicsManager::GraphicsManager()
{
}

//Destructor
GraphicsManager::~GraphicsManager()
{
}

//Devolvemos el puntero al singleton
GraphicsManager& GraphicsManager::singleton()
{
return instance;
}

//Funcion para inicializar el motor gráfico
void GraphicsManager::Init(int* argc, char* argv[])
{
cout << "Inicializamos el Graphics Manager\n";
//Creamos la ventana principal del programa utilizando la libreria GLUT
glutInit(argc, argv);
glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE | GLUT_DEPTH);
glutInitWindowPosition(0, 0);
glutInitWindowSize(640, 480);
int mainWindow = glutCreateWindow("Lord Pakus Engine!!!"); //Viva la originalidad!!! :)
glutSetWindow(mainWindow);

//Asignamos todas las funciones gráficas de callback del glut
//a las funciones que definiremos posteriormente
glutDisplayFunc(Render);
// glutReshapeFunc(Reshape); //Por ahora la dejamos comentada por que no nos hace falta

TextureManager::singleton().Init(argc,argv); //Inicializamos las texturas
Graphics3DManager::singleton().Init(argc,argv); //Inicializamos la parte de 3D
}

//Funcion para desinicializar el bucle principal
void GraphicsManager::DeInit()
{
TextureManager::singleton().DeInit(); //Desinicializamos la parte de texturas
Graphics3DManager::singleton().DeInit(); //Desinicializamos la parte de 3D

cout << "Desinicializamos el Graphics Manager\n";
}

//CALLBACKS DE GLUT, por ahora

//Funcion que se ejecuta automaticamente desde glut (por ahora)
void GraphicsManager::Render()
{
//Pintado de la parte de 3D
Graphics3DManager::singleton().Render();

//IMPORTANTE: Función encargada de realizar el double-buffering
glutSwapBuffers();
}

//Funcion que se ejecuta automaticamente desde glut (por ahora). Por el momento la dejamos comentada por que no nos hace falta
//void GraphicsManager::Reshape()
//{
// //AQUI IRÁ NUESTRA FUNCIÓN DE REESCALADO. Por ahora vacia
//}


Graphics3DManager: Se aplica solo este cambio dentro de la función de pintado.
glEnable(GL_TEXTURE_2D);
glColor3f(1.0f,1.0f,1.0f); //Limpiamos el buffer de color
TextureManager::singleton().Texture("wood"); //Usamos la textura

glBegin(GL_QUADS); // Start Drawing The Cube
//glColor3f(0.0f,1.0f,0.0f); // Set The Color To Green
glTexCoord2f( 0.0f, 0.0f); glVertex3f( 1.0f, 1.0f,-1.0f); // Top Right Of The Quad (Top)
glTexCoord2f( 0.0f, 1.0f); glVertex3f(-1.0f, 1.0f,-1.0f); // Top Left Of The Quad (Top)
glTexCoord2f( 1.0f, 1.0f); glVertex3f(-1.0f, 1.0f, 1.0f); // Bottom Left Of The Quad (Top)
glTexCoord2f( 1.0f, 0.0f); glVertex3f( 1.0f, 1.0f, 1.0f); // Bottom Right Of The Quad (Top)
//glColor3f(1.0f,0.5f,0.0f); // Set The Color To Orange
glTexCoord2f( 0.0f, 0.0f); glVertex3f( 1.0f,-1.0f, 1.0f); // Top Right Of The Quad (Bottom)
glTexCoord2f( 0.0f, 1.0f); glVertex3f(-1.0f,-1.0f, 1.0f); // Top Left Of The Quad (Bottom)
glTexCoord2f( 1.0f, 1.0f); glVertex3f(-1.0f,-1.0f,-1.0f); // Bottom Left Of The Quad (Bottom)
glTexCoord2f( 1.0f, 0.0f); glVertex3f( 1.0f,-1.0f,-1.0f); // Bottom Right Of The Quad (Bottom)
//glColor3f(1.0f,0.0f,0.0f); // Set The Color To Red
glTexCoord2f( 0.0f, 0.0f); glVertex3f( 1.0f, 1.0f, 1.0f); // Top Right Of The Quad (Front)
glTexCoord2f( 0.0f, 1.0f); glVertex3f(-1.0f, 1.0f, 1.0f); // Top Left Of The Quad (Front)
glTexCoord2f( 1.0f, 1.0f); glVertex3f(-1.0f,-1.0f, 1.0f); // Bottom Left Of The Quad (Front)
glTexCoord2f( 1.0f, 0.0f); glVertex3f( 1.0f,-1.0f, 1.0f); // Bottom Right Of The Quad (Front)

//glColor3f(1.0f,1.0f,0.0f); // Set The Color To Yellow
glTexCoord2f( 0.0f, 0.0f); glVertex3f( 1.0f,-1.0f,-1.0f); // Bottom Left Of The Quad (Back)
glTexCoord2f( 0.0f, 1.0f); glVertex3f(-1.0f,-1.0f,-1.0f); // Bottom Right Of The Quad (Back)
glTexCoord2f( 1.0f, 1.0f); glVertex3f(-1.0f, 1.0f,-1.0f); // Top Right Of The Quad (Back)
glTexCoord2f( 1.0f, 0.0f); glVertex3f( 1.0f, 1.0f,-1.0f); // Top Left Of The Quad (Back)

//glColor3f(0.0f,0.0f,1.0f); // Set The Color To Blue
glTexCoord2f( 0.0f, 0.0f); glVertex3f(-1.0f, 1.0f, 1.0f); // Top Right Of The Quad (Left)
glTexCoord2f( 0.0f, 1.0f); glVertex3f(-1.0f, 1.0f,-1.0f); // Top Left Of The Quad (Left)
glTexCoord2f( 1.0f, 1.0f); glVertex3f(-1.0f,-1.0f,-1.0f); // Bottom Left Of The Quad (Left)
glTexCoord2f( 1.0f, 0.0f); glVertex3f(-1.0f,-1.0f, 1.0f); // Bottom Right Of The Quad (Left)

//glColor3f(1.0f,0.0f,1.0f); // Set The Color To Violet
glTexCoord2f( 0.0f, 0.0f); glVertex3f( 1.0f, 1.0f,-1.0f); // Top Right Of The Quad (Right)
glTexCoord2f( 0.0f, 1.0f); glVertex3f( 1.0f, 1.0f, 1.0f); // Top Left Of The Quad (Right)
glTexCoord2f( 1.0f, 1.0f); glVertex3f( 1.0f,-1.0f, 1.0f); // Bottom Left Of The Quad (Right)
glTexCoord2f( 1.0f, 0.0f); glVertex3f( 1.0f,-1.0f,-1.0f); // Bottom Right Of The Quad (Right)
glEnd(); // Done Drawing The Quad
glDisable(GL_TEXTURE_2D);



Espero que os haya gustado. Aunque este capitulo os parezca una tonteria es el que nos servirá de base para absolutamente todo el módulo de Graphics2DManager y lo usaremos con cierta recurrencia para múltiples utilidades (graficos 2D, fuentes bitmapeadas , HUD , texturización de modelos 3D ,etc...)

Probad que os funcione y si veis que os falla, lo miramo.

LordPakusBlog
Nos vemosss

Entradas populares