Simulador de vuelo para navegador. Se vuela sobre Paraguay —el relieve es real, el paisaje lo pintamos nosotros— y se aterriza donde se pueda.
Estado: esqueleto funcional. Modelo de vuelo, terreno procedural, HUD y controles operativos. Sin arte final, sin audio, sin multijugador. Lo que falta está en los issues.
Producto de Oksigenia SL, publicado bajo la marca Granja Óga. Gratis para siempre para la educación paraguaya — ver LICENSE-CONTENIDO.md.
Porque una niña dijo que quería ser piloto "con las gafas de sol", y porque no había ningún simulador que la dejara reconocer su país desde el aire.
Esa niña tiene cuatro años y medio, y eso no es una anécdota: es la restricción de diseño más dura del proyecto. La jugadora más joven todavía no sabe leer. Nada de lo esencial puede depender de un texto.
El objetivo no es la fidelidad de un simulador de entrenamiento. Es que volar se sienta bien, que el paisaje se reconozca, y que un chico de ocho años pueda despegar en el primer intento sin leer un manual —y que uno de cuatro pueda hacerlo sin leer nada en absoluto.
npm install
npm run devAbre http://localhost:5173. No hace falta nada más: el escenario inicial se genera por código, sin descargar datos.
| Comando | Qué hace |
|---|---|
npm run dev |
Servidor de desarrollo con recarga en caliente |
npm run build |
Compila a dist/ (estático, se sirve con nginx) |
npm run typecheck |
Comprueba tipos sin compilar |
npm test |
Tests del modelo de vuelo |
npm run terreno |
Convierte teselas NASADEM a mapas de altura |
npm run acceso |
Mide WCAG 2.2 AA: contraste, foco, teclado y movimiento |
npm run sin-red |
Compila, corta la conexión y comprueba que se vuela igual |
npm run rendimiento |
Mide el coste por fotograma con la CPU estrangulada |
A partir de la segunda visita, el juego funciona sin internet: un service worker guarda el armazón —HTML, código y estilos, 1,1 MB— y, según se usan, los mundos que se visitan. El escenario en el que se voló ayer está disponible hoy aunque no haya red, que es la diferencia entre una promesa educativa y un folleto. Se puede instalar en el escritorio de una tablet como una aplicación más.
Lo que no se guarda es lo de fuera de casa: las teselas de Google y el METAR en directo. Sin ellas el juego cae al mundo dibujado y al tiempo de casa, que es exactamente para lo que están esos dos caminos.
Comprobado con npm run sin-red, que apaga el servidor de verdad y vuelve a
entrar.
Todas las teclas se pueden cambiar desde la pantalla de mandos, y esa pantalla dice la verdad sobre lo que hace cada una. Esta tabla, hasta hace poco, no: prometía botones táctiles de cámara y de reinicio que no existían y una pantalla de ajustes que sigue sin existir (#149).
| Acción | Teclado | Táctil |
|---|---|---|
| Cabeceo / alabeo | Flechas o W A S D |
Palanca izquierda |
| Timón | Q / E |
Los dos pedales |
| Motor | + / − o X / Z |
Palanca derecha |
| Frenos | B o Espacio |
La mano roja del HUD |
| Cámara | C |
Botón, arriba a la izquierda |
| Pausa | Esc |
Botón, arriba a la izquierda |
| Reiniciar vuelo | R |
Desde el menú de pausa |
| Volver al hangar | — | Botón, y desde el menú de pausa |
| Nivel de dificultad | M |
— |
| Idioma | L |
— |
| Sonido | V |
Botón en pantalla |
| Cambiar de avión | P |
— |
| Misión | N |
— |
| Mandos, mapa, tiempo, créditos, cuaderno | K, F1 |
Botones de la barra |
También funciona con mando (Xbox / PlayStation) por la Gamepad API.
.
├── src/
│ ├── flight/ Modelo de vuelo, aeronaves, controles
│ │ ├── fdm.ts FDM propio de coeficientes (el corazón)
│ │ ├── model.ts Interfaz FlightModel — el punto de enchufe
│ │ ├── aircraft.ts Fichas técnicas de cada aeronave
│ │ └── input.ts Teclado, táctil y mando
│ ├── world/ Terreno, cielo, escenarios
│ ├── ui/ HUD, menús, créditos
│ ├── i18n/ es-PY y guaraní (gug)
│ └── game.ts Bucle de juego y ensamblaje
├── scripts/ Pipeline de terreno (NASADEM → mapa de altura)
├── docs/adr/ Decisiones de arquitectura y su porqué
└── public/assets/ Assets estáticos
FDM propio, escrito en TypeScript, de coeficientes aerodinámicos: calcula sustentación, resistencia, fuerza lateral y los tres momentos a partir del ángulo de ataque, el derrape y las velocidades angulares, e integra las ecuaciones de Euler del sólido rígido. Entra en pérdida de verdad.
| Guyrami | Tukã | Taguato | Taguato Ruvicha | |
|---|---|---|---|---|
| Edad orientativa | 4-6 | 7-9 | 10-13 | 14+ |
| Modelo de vuelo | sencillo | coeficientes | coeficientes | coeficientes |
| Pérdida | no existe | protegida | sí | sí |
| Alas | se enderezan solas | se enderezan solas | las nivelás vos | las nivelás vos |
| Instrumentos | ninguno | pictóricos | numéricos | seis analógicos |
| Unidades | km/h y metros | km/h y metros | km/h y metros | nudos y pies |
Lo que cambia entre peldaños no es el mundo ni el avión: es cuánta física
se le confía al jugador. Se cambia de nivel con M, incluso en el aire.
El primer peldaño usa otro modelo de vuelo, no el mismo con más ayudas
(src/flight/arcade.ts). Pelear con un modelo realista para que se comporte
de forma sencilla es luchar contra la física que uno mismo eligió: el fugoide
existe porque un avión intercambia altura por velocidad, y la manera de no
tenerlo no es amortiguarlo, es no tenerlo. Los otros tres peldaños comparten
el modelo de coeficientes y se distinguen por qué capas de ayuda llevan
(src/flight/assists.ts).
Está detrás de la interfaz FlightModel a propósito:
se le puede enchufar JSBSim
compilado a WebAssembly como implementación alternativa sin tocar el resto
del juego. El porqué —y las implicaciones de licencia LGPL, que son las que
nos hicieron no usarlo de entrada— está en
docs/adr/0002-modelo-de-vuelo-propio.md.
El relieve sale de NASADEM (NASA, dominio público, ~30 m de resolución).
scripts/hgt-a-heightmap.mjs convierte las teselas .hgt a mapas de altura
PNG de 16 bits que el juego carga como escenario.
El color no sale de imaginería satelital: se pinta por altitud, pendiente y bioma con shaders propios. Sale más bonito, no cuesta nada al mes y no nos ata a ningún proveedor.
Tres idiomas, que se pasan con L: español paraguayo (es-PY),
guaraní (gug) e inglés (en). Como en el resto de productos de
Granja Óga se aplica el test Ña Emy: si una abuela paraguaya no puede usar
la pantalla, la pantalla no está terminada.
Los rótulos de los instrumentos —IAS, ALT, HDG, V/S, THR— no se traducen en ningún idioma. Son los mismos en cualquier cabina del mundo, y aprenderlos es parte de lo que el juego enseña sin proponérselo. Debajo de cada uno va la palabra corriente en pequeño, que es la muleta de quien está aprendiendo a leer y que con el tiempo se deja de mirar.
Las unidades siguen al modo de vuelo: Arcade muestra km/h y metros, Piloto muestra nudos y pies. Quien decide que quiere volar en serio se encuentra con las unidades de verdad en el mismo gesto.
- Código — Apache-2.0. Úsalo, véndelo, no nos preguntes.
- Contenido y marcas — propietario, © Oksigenia SL.
- Toda la educación paraguaya — gratis, permanente, sin trámites. Detalles.
Procedencia y licencia de cada dependencia y cada dato: CREDITOS.md.
Gratis para siempre para toda la educación paraguaya. Eso está firmado en LICENSE-CONTENIDO.md y no depende de que haya dinero: mientras Óga Veve exista, a un colegio no se le cobra.
Lo que no está firmado es que vaya a existir siempre. Esto lo mantiene una empresa pequeña, no tiene ingresos y puede dar pérdidas y cerrarse. Conviene decirlo aquí y no en la letra pequeña, porque quien monte una clase encima de esto tiene derecho a saberlo: el código es Apache-2.0 y los datos son de OpenStreetMap y de dominio público, así que si un día esto se apaga, cualquiera puede volver a encenderlo.
Si quieres que dure, Liberapay y PayPal. Lo que llegue va a lo que de verdad cuesta dinero: las teselas del mundo real, que se pagan por vuelo.
Issues y pull requests, bienvenidos. Antes de mandar código, lee docs/adr/ para no chocar con una decisión ya tomada, y AGENTS.md si trabajas con herramientas de asistencia.
Al contribuir aceptas que tu aportación se publique bajo Apache-2.0.