Motor juegos C++, openGL y codeblocks

Iniciado por Desiresportal, 25 Febrero 2015, 17:01 PM

0 Miembros y 1 Visitante están viendo este tema.

Desiresportal

Muy buenas!:

He estado buscando y no encuentro lo que yo busco.

Tengo cierta experiencia programando juegos en Blender. Mientras aprendía a programar para Blender en python, toque Python (lo que viene siendo el programa en consola) y PyGame. Despues aprendí a programar en PHP y javascript en un curso. Despues pude aplicar lo aprendido de javascript para aprender Canvas. (para quien no sepa: lo que aprendí de canvas es mostrar imagenes. Lo demas realmente no es mas que javascript puro y duro.) Y ahora estoy a tope con C++.

Estoy viendo cosillas. Mirando por un lado y por otro. Aún no consigo nada realmente extraordinario o medianamente bueno como para estar orgulloso, y ya estoy buscando como hacer un juego.

El caso es: En los juegos que he echo en javascript funcionan de la siguiente forma:

Una funcion run() llama a Act(), Paint() y run() (si se llama a sí misma). Esta ultima pasados 0.017s.

Al llamarse a si misma en ese intervalo de tiempo se obtiene el bucle que engloba al juego.

Despues en Act() se hacen los calculos con las teclas que se pulsan y se dejan de pulsar.
Y por ultimo Paint() muestra el estado actual de los calculos de forma visual al jugador (dibujando el cubito en player.x=25 o player.x=500).

Busco hacer juegos a base de puro codigo. Nada de usar motores externos que despues dan errores que no tienen nada que ver con mi codigo. (Eso mismo me paso con Blender y por eso lo dejé de lado.)

Lo que quiero saber es: ¿Hay algo como el run() que acabo de explicar? ¿Se puede hacer en C++ que una funcion se llame a sí misma al cabo de X segundos o milisegundos sin que en ningún momento el programa quede como "no responde"? ¿Como lo hago exactamente? (se coger las teclas pulsadas y el ratón con OpenGL [mas o menos...])

(lo ideal como respuesta es: sentencia(parametros), forma de uso de la sentencia, librería necesaria para usarla y tipos de los parametros [int, double, char, string, boolean, matriz, tupla].)

Datos extra por si falta informacion:
- Utilizo Codeblocks 13.12.
- Sigo los tutoriales de minidosis.org.
- Tengo windows 7 64 bits.
- Estoy enfocado a usar OpenGL. (Por cabezonería. No pienso en hacer juegos DirectX.)
- Ya tengo todo lo necesario para correr OpenGL. (he echo pruebas)

Ejemplos de juegos que he echo en javascript: http://desiresportal.esy.es/juegos/

eferion

Cita de: Desiresportal en 25 Febrero 2015, 17:01 PM
Y ahora estoy a tope con C++.

Si pretendes dominar C++, más vale que le dediques varios añitos... no es algo que se pueda controlar al 100% con un par de añitos de experiencia ;)

Cita de: Desiresportal en 25 Febrero 2015, 17:01 PM
Una funcion run() llama a Act(), Paint() y run() (si se llama a sí misma). Esta ultima pasados 0.017s.

Eso se llama recursividad... si intentas hacer eso en un juego programado en código nativo, el juego va a morir en un par de segundos porque te has quedado sin pila. Lo más normal es que la función "run" tenga un bucle que ejecute "Act()", "Paint()", y añada una pausa del tiempo que sea necesario... sin recursividad.

Cita de: Desiresportal en 25 Febrero 2015, 17:01 PM
Busco hacer juegos a base de puro codigo. Nada de usar motores externos que despues dan errores que no tienen nada que ver con mi codigo. (Eso mismo me paso con Blender y por eso lo dejé de lado.)

Para diseñar ese juego vas a hacer uso de la librería estándar... que aunque funciona estupendamente no está exenta de algún que otro bug.

Además también te vas a tener que apoyar en el sistema operativo... que también suelen ser famosos por tener bugs.

Moraleja: No tengas tanto miedo a usar librerías externas. Una cosa es que quieras aprender y por eso decides reinventar la rueda, pero a la hora de la verdad hay que ser práctico.

Cita de: Desiresportal en 25 Febrero 2015, 17:01 PM
Lo que quiero saber es: ¿Hay algo como el run() que acabo de explicar? ¿Se puede hacer en C++ que una funcion se llame a sí misma al cabo de X segundos o milisegundos sin que en ningún momento el programa quede como "no responde"? ¿Como lo hago exactamente? (se coger las teclas pulsadas y el ratón con OpenGL [mas o menos...])

* En C++ no hay nada expecífico como el run() que acabas de comentar
* En C++ se puede programar la recursividad sin ningún problema... eso si, si no le pones límite, tu programa no saldrá bien parado
* Ejemplo de recursividad:

Código (cpp) [Seleccionar]
void func( )
{
 printf( "1" );
 func( ); // Se llama a sí misma
}

int main( )
{
 func( );
}


Cita de: Desiresportal en 25 Febrero 2015, 17:01 PM
(lo ideal como respuesta es: sentencia(parametros), forma de uso de la sentencia, librería necesaria para usarla y tipos de los parametros [int, double, char, string, boolean, matriz, tupla].)

Esta información podría ser útil si utilizases una librería externa para el motor gráfico, como no es así te lo tienes que currar todo tu.

Cita de: Desiresportal en 25 Febrero 2015, 17:01 PM
- Utilizo Codeblocks 13.12.

El IDE que uses no es relevante. Eso únicamente te afecta a tí, asi que lo mejor es elegir uno con el que te sientas cómodo.

Cita de: Desiresportal en 25 Febrero 2015, 17:01 PM
- Estoy enfocado a usar OpenGL. (Por cabezonería. No pienso en hacer juegos DirectX.)

Pues fíjate que DirectX obtiene mejores rendimientos y es más portable (dentro de las diferentes versiones de Windows y de tarjetas gráficas) que OpenGL, aun así tienes tus motivos y es una opción perfectamente válida.

PD.: no me apetece iniciar un debate sobre qué es mejor OpenGL o DirectX.

En Resumen. En C++ puedes hacer lo que te propongas, pero al ser un lenguaje de más bajo nivel que javascript, vas a tener que estar más atento a lo que haces... aquí no hay barreras y es muy fácil salirse del camino... eso sí, la satisfacción de hacer un programa completo compensa :)

Un saludo.

Desiresportal

¿Y no hay algo como el "window.setTimeout(run(), 17);" de javascript pero para C++?

Ademas en javascript la "rellamada" de run() se hace antes de Act() y Paint() para que se hagan 60fps lo mas reales posibles. Sino tardaría 17 milisegundos despues de calcularlo y dibujarlo todo.

Mejor se hace antes y si ha dado tiempo a calcularlo todo y dibujarlo todo para cuando han pasado esos 17 milisegundos, bien. Sino, a por el siguiente frame.

Seyro97

C++ es un lenguaje que es secuencial a primera vista, es decir, que las cosas se van haciendo en el orden que vas escribiendo. En el caso de javascript, es cierto que tenemos la función 'setTimeout', pero C++ no usa ese método.

En C++, para que algo se repita indefinidamente (hasta que se cierra el juego, o así) tienes, como ya se ha mencionado, la recursividad.

Un ejemplo:

Código (cpp) [Seleccionar]
void run() {
   Act();
   Paint();
   
   run();
}


Analicemos:
Una vez se ejecuta por primera vez esa función 'run', se va a ejecutar Act(), posteriormente se va a ejecutar la función 'Paint' y por último se va a ejecutar la función 'run', y comencamos de nuevo el ciclo.

Si lo que quieres es pausar la función 'run' un tiempo determinado, harías lo siguiente:

Código (cpp) [Seleccionar]
#include <thread>
#include <chrono>

void run() {
   Act();
   Paint();

   std::this_thread::sleep_for(std::chrono::milliseconds(17));
   run();
}


Lo que hace 'std::this_thread::sleep_for(std::chrono::milliseconds(17));' es pausar el programa entero 17 milisegundos

Este es un ejemplo algo tosco, por lo que habría que añadirle mas cosas para que vaya mejor. Suerte
Carlos Peláez González. visita http://www.taringa.net/EnjoyC para muchos tutoriales!

iUDEX

Bueno, no creo que ayude mucho, y dices que no quieres DirectX, pero puedes probar el motor Unity 5, en donde usas el sistema de scripting para codificar el juego. Puede ser javascript, o si quieres interactuar mucho más, C#. Boo no es muy tomado en cuenta.

La función que "engloba" el juego (ejemplo):

Código (javascript) [Seleccionar]
function Update () { // Función reservada que se ejecuta por cada frame
// Función
}


Para Act() tienes un script prefabricado en la librería.
Para Paint() tienes los famosos "GUITextures".

Y acerca del tiempo, no es neceario, ya que la función Update se ejecuta continuamente. De todas maneras puedes usar Corountines o simples yield WaitForSeconds(tiempo);.

Puedes revisar la documentación, si ya dominas javascript entonces no se te dificultará tanto.
Namasté, criatura.

Desiresportal

Lo cierto es que al final me decanté por utilizar la funcion "display" para hacer ambos procesos. Primero "act" y despues "paint". Y utilizo la funcion "idle" de OpenGL para que se produzca la animacion cuando el usuario no pulsa nada.

Doy por cerrado el tema. Y gracias por la ayuda.

class_OpenGL

Código (javascript) [Seleccionar]
window.setTimeout(run(), 17);

No sé mucho de javascript, pero creo que sé para qué sirve "window.setTimeout(run(), 17);" Sirve para que la función run() se ejecute cada 17 milisegundos, ¿no?. Si es el caso, en C++ no existe algo para hacer eso. Esa instrucción sirve para la sincronización vertical, es decir, para que el juego vaya a 60 FPS. Para activar la sincronización vertival en tu aplicación de C++, en Windows, se hace así:

Código (cpp) [Seleccionar]
wglSwapIntervalEXT(1);

Lo que hace la función es darle tiempo a la gráfica y al monitor a mostrar un fotograma.

El código general quedaría así:

Código (cpp) [Seleccionar]
// Inicialización de OpenGL
...
wglSwapIntervalEXT(1);
...

// Función del bucle del juego (ejecutar cuando todo se haya inicializado
void run() {
   while(evento_cerrar_ventana == false) {
      // Escribir todo lo que se hará en cada fotograma, como pintar, reproducir sonidos...
   }
}


_______________________________________________

Dejando el tema este tema, te recomiendo encarecidamente que uses unas librerías externas (tranquilo, no te quitan el trabajo gráfico, solo te FACILITA la vida) que son GLFW y GLEW (ambas gratuitas). La librería GLFW te permite crear un sistema de ventanas con pocas líneas, y es compatible tanto con Windows, Linux y Mac OSX (me parece), y GLEW te carga las extensiones de OpenGL (las necesitarás para trabajar con el OpenGL 3.3 en adelante). De verdad, es aburridísimo cargar las funciones nuevas de OpenGL y además no es multiplataforma... mejor usa GLEW y GLFW.

Te recomiendo una página, que aunque esté en inglés, es muy buena explicando lo referente a gráficos, y trabaja en C++. http://learnopengl.com/

Programador aficionado. Me quiero centrar en programar videojuegos. La API que uso para crearlos es OpenGL