SDK Multiplataforma en C logo

SDK Multiplataforma en C

Crear nueva aplicación

❮ Anterior
Siguiente ❯

Me considero una persona técnica que eligió un gran proyecto y una excelente manera para llevarlo a cabo. Linus Torvalds.


En Inicio rápido y Generar binarios NAppGUI hemos visto como obtener el SDK, así como compilar y ejecutar las aplicaciones de ejemplo. También, en ¡Hola Mundo!, aprendimos la estructura básica de una aplicación basada en NAppGUI. Ha llegado el momento de crear nuestras propias aplicaciones, aprovechando los scripts CMake incluidos en la carpeta /prj de la distribución.

Si tu objetivo es utilizar NAppGUI como librería externa en tus proyectos, puedes saltar este capítulo.

1. Aplicaciones de escritorio

Para crear una nueva aplicación de escritorio, abre el archivo /src/CMakeLists.txt y añade la siguiente línea después de # Your projects here!:

src/CMakeLists.txt
 
# Your projects here!
desktopApp("MyNewApp" "myapp" "osapp" NRC_EMBEDDED)

Acto seguido, vuelve a generar la solución con CMake y ábrela con el IDE correspondiente:

 
cmake -S ./src -B ./build
cmake --open ./build
El comando cmake --open solo funciona con los generadores de Visual Studio y Xcode. En Linux tendrás que abrirlo manualmente con el editor que prefieras.

En caso de que la solución ya estuviese abierta, es posible que el IDE te avise que han habido cambios, por ejemplo Visual Studio (Figura 1).

Warning de Visual Studio tras añadir un nuevo proyecto.
Figura 1: Aviso de Visual Studio de que debe recargar la solución.

Verás que CMake ha creado un nuevo proyecto llamado MyNewApp dentro de la solución (Figura 2).

Captura del Explorador de Solución de Visual Studio donde aparece el nuevo proyecto.
Figura 2: Proyecto MyNewApp recién añadido a la solución.

Si compilas y ejecutas MyNewApp, te darás cuenta de que no es otra cosa que el Hello, World! (Figura 3), ya que esta es la plantilla predeterminada para cada nueva aplicación de escritorio. También se ha asignado un Icono de aplicación por defecto, pero lo podremos personalizar posteriormente.

Aplicación NAppGUI Hello World.
Figura 3: Resultado de compilar y ejecutar MyNewApp.

Viendo en detalle la sintaxis del comando desktopApp que acabamos de añadir al CMakeLists.txt, tenemos:

 
desktopApp("MyNewApp" "myapp" "osapp" NRC_EMBEDDED)

desktopApp(appName path depends nrcMode)
  • appName: El nombre de la aplicación.
  • path: Ruta relativa a /src donde se ubicará el proyecto (en este caso nappgui_src/src/myapp). Se admite cualquier profundidad de ruta. Por ejemplo, "games/myapp" creará el proyecto en nappgui_src/src/games/myapp y "demo/games/myapp" en nappgui_src/src/demo/games/myapp.
  • depends: Librerías de las que depende la aplicación. Como mínimo tendrás que incluir osapp ya que estamos ante una aplicación de escritorio. Si la aplicación necesitara dependencias adicionales, como librerías creadas por ti mismo, las escribiremos a continuación separadas por punto y coma (pe. "osapp;physics;render"). En Crear nueva librería tienes un ejemplo de aplicaciones con dependencias. Importante: Solo necesitas indicar las dependencias de primer nivel. CMake añadirá recursivamente las dependencias de las dependencias.
  • nrcMode: Cómo se administrarán los recursos de la aplicación. Por el momento, indicamos NRC_EMBEDDED. Profundizaremos en ellos en el capítulo Recursos.
Puedes crear tantas aplicaciones dentro de la misma solución como quieras. Solo debes que repetir el proceso, añadiendo nuevos desktopApp() al script CMakeLists.txt.

2. Añadir archivos

Volviendo al proyecto MyNewApp, vemos que por defecto solo se crea un archivo de código fuente (mynewapp.c) que contiene toda la aplicación. Es muy probable que quieras dividir el código entre diferentes archivos. Crea un par de nuevos archivos myfunc.c y myfunc.h dentro de nappgui_src/src/myapp desde el IDE o directamente desde el explorador. Ábrelos y añade estas líneas:

myfunc.h
1
2
3
4
5
// Example of new header

#include "core.hxx"

real32_t myadd_func(real32_t a, real32_t b);
myfunc.c
1
2
3
4
5
6
7
8
// Example of new c file

#include "myfunc.h"

real32_t myadd_func(real32_t a, real32_t b)
{
    return a + b;
}

Abre mynewapp.c y edita la función i_OnButton.

mynewapp.c
1
2
3
4
5
6
7
8
9
...
static void i_OnButton(App *app, Event *e)
{
    real32_t res = myadd_func(56.4f, 23.3f);
    textview_printf(app->text, "Button click (%d-%.2f)\n", app->clicks, res);
    app->clicks += 1;
    unref(e);
}
...

Vuelve a re-generar la solución con cmake -S ./src -B ./build. El IDE, Visual Studio en este caso, nos vuelve a informar que han habido cambios en el proyecto MyNewApp (Figura 4). Simplemente presiona [Reload All].

Advertencia que muestra Visual Studio, al detectar que se han añadido nuevos archivos.
Figura 4: Visual Studio advierte sobre nuevos archivos. Pulsa [Reload All].

Vuelve a compilar y ejecutar MyNewApp para ver los cambios que acabas de realizar. Puedes crear tantos archivos y subcarpetas dentro del directorio src/myapp como necesites para organizar mejor tu código. Recuerda siempre ejecutar cmake -S ./src -B ./build cada vez que añadas o elimines archivos del proyecto. CMake actualizará la solución "clonando" la estructura de directorios dentro del proyecto (MyNewApp en este caso).

Llegados a este punto te recomendamos que dediques algo de tiempo a investigar, compilar y probar los ejemplos de las carpetas demo y howto.

3. Aplicaciones por línea de comandos

De forma similar a las aplicaciones de escritorio vistas anteriormente, podrás crear aplicaciones de consola. Abre /src/CMakeLists.txt y añade esta línea después de # Your projects here!:

src/CMakeLists.txt
 
# Your projects here!
commandApp("myutil" "utils/myutil" "core" NRC_NONE)

Al regenerar la solución con cmake -S ./src -B ./build, Visual Studio te alertará que debes recargar la solución, de la misma forma que ocurrió con nuestra aplicación anterior. Se habrá creado un nuevo proyecto en nappgui_src/src/utils/myutil, pero esta vez si lo compilas y ejecutas no aparecerá ninguna ventana. Tan solo verás un mensaje en la consola de Visual Studio:

1
Hello world!

Si abres myutil.c encontrarás el código que ha generado la salida anterior:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
/* NAppGUI Console Application */

#include "coreall.h"

int main(int argc, char *argv[])
{
    unref(argc);
    unref(argv);
    core_start();
    bstd_printf("Hello world!\n");
    core_finish();
    return 0;
}

Que es la típica plantilla de un programa en C, a la que se le ha incluido el soporte de la librería core. A partir de aquí, ya podemos modificar el código y compilar. CMake ya lo configuró todo por nosotros. Volvamos al src/CMakeLists.txt para repasar la línea anterior:

src/CMakeLists.txt
 
commandApp("myutil" "utils/myutil" "core" NRC_NONE)

commandApp(appName path depends nrcMode)
  • appName: El nombre de la aplicación.
  • path: Ruta relativa a /src donde se ubicará el proyecto (en este caso nappgui_src/src/utils/myutil).
  • depends: Dependencias. Una aplicación de línea de comandos no requiere ninguna dependencia "mínima", como ocurría con las aplicaciones de escritorio. Recomendamos incluir una dependencia con Core ("core") ya que contiene gran variedad de funciones que nos pueden facilitar la tarea. No obstante, puedes establecer Osbs ("osbs") o incluso Sewer ("sewer") como requisitos mínimos.
  • nrcMode: NRC_NONE, NRC_EMBEDDED o NRC_PACKED. Distribución de recursos.

Ni que decir tiene que podemos añadir nuevos archivos y subcarpetas al proyecto de forma similar a como lo hicimos en aplicaciones de escritorio.


4. Estándar C/C++

NAppGUI se ha creado, en su práctica totalidad, en lenguaje C90, añadiendo los enteros de tipo fijo uint32_t, int16_t, ... (<stdint.h>) de C99. Para ciertas partes del proyecto se ha utilizado C++98, pero siempre encapsulado bajo una interfaz en C90. Por lo tanto, se puede crear una aplicación o librería utilizando únicamente C90, lo que proporciona gran portabilidad entre plataformas y compiladores.

Por lo general, los compiladores permiten comprobar que el código se ajuste a ciertos estándares de C/C++, emitiendo advertencias o errores cuando no sea así. Por defecto, cada nuevo proyecto creado con desktopApp() o commandApp() establecerá C90 y C++98 como estándares. De esta forma, serán compatibles con toda la lista de Compiladores e IDEs soportados por NAppGUI.

No obstante, es posible que quieras utilizar un estándar más moderno para tus nuevos proyectos. En este caso, deberás indicarlo al final de los comandos desktopApp o commandApp:

 
desktopApp("MyNewApp" "myapp" "osapp" NRC_EMBEDDED "C17;C++17")

En este caso indicaremos que la aplicación MyNewApp utilizará los estándares C17 y C++17 en lugar de C90 y C++98, que son los valores por defecto.

  • Para el compilador de C, las opciones serán: C90, C99, C11, C17 y C23.
  • Para el compilador de C++, las opciones serán: C++98, C++11, C++14, C++17, C++20 y C++23.
Si el compilador no soporta la versión del lenguaje indicada, se establecerá la mayor soportada. Es responsabilidad del programador utilizar los compiladores apropiados al estándar elegido.
❮ Anterior
Siguiente ❯