SDL en C bajo GNU/Linux 010 – Modulo sonando de fondo


  
En el anterior articulo se ha explicado por encima como se puede hacer para reproducir módulos musicales pero no llegamos a ver un ejemplo adaptado en condiciones para usarlo con SDL en C. El ejemplo era funcional pero sin ventanita y sin control para poder cerrar.
  
En este caso he adaptado el ejemplo que ofrece libxmp para usarlo junto a sdl. Digamos que este ejemplo va mucho más en la línea del resto de artículos aunque creo que es necesario mirar ese articulo anterior si se quiere saber de que estamos hablando.
  
Veamos un vídeo de ejemplo de como se escucha y ve el código de este articulo:
  
https://mierda.tv/descargas/modulo_sonando.avi
  
Aquí puede bajarse el zip con el código y el makefile listo para hacer make y make run: playmod2.zip
  
El zip lleva varios módulos para use y disfrute. El código simplemente crea una ventana y espera a que la cierres para finalizar (pero mientras suena la música). No he metido nada en la ventana para no añadir código que pueda inducir a error o resultar más molesto ir al grano.
  
Veamos el código:
  

#include <SDL.h>
#include <xmp.h>
#include <stdbool.h>

int sonando;
char * modulo = "res/modulo2.it";

static void rellenarAudio(void *udata, Uint8 *stream, int len)
{
  if (xmp_play_buffer((xmp_context)udata, stream, len, 0) < 0){ sonando = 0; }
}


static int sdl_init(xmp_context ctx) {
  if (SDL_Init(SDL_INIT_AUDIO) < 0) { printf("No se ha podido inicializar: %s\n", SDL_GetError()); return 1; }
  SDL_AudioSpec a;
  a.freq = 44100;
  a.format = AUDIO_S16;
  a.channels = 2;
  a.samples = 2048;
  a.callback = rellenarAudio;
  a.userdata = ctx;
  if (SDL_OpenAudio(&a, NULL) < 0) { printf("No se ha podido inicializar el dispositivo de audio: %s\n", SDL_GetError());	return 1; }
  return 0;
}

int main(int argc, char **argv) {
  SDL_Event evento;
  bool quit = false;
  SDL_Window * ventana;
  SDL_Init(SDL_INIT_VIDEO);
  ventana = SDL_CreateWindow("Modulo sonando de fondo",SDL_WINDOWPOS_UNDEFINED,SDL_WINDOWPOS_UNDEFINED,320,240,SDL_WINDOW_OPENGL);
  if (ventana == NULL) { printf("No se pudo crear la ventana: %s\n", SDL_GetError());	return 1; }

  xmp_context ctx;
  ctx = xmp_create_context();
  sdl_init(ctx);
  xmp_load_module(ctx, modulo);
  xmp_start_player(ctx, 44100, 0);
  sonando = 1;
  SDL_PauseAudio(0);

  while (!quit) {
    SDL_WaitEvent(&evento);
    switch (evento.type) {
    case SDL_QUIT:
      xmp_end_player(ctx);
      xmp_free_context(ctx);
      SDL_CloseAudio();
      quit = true;
      break;
    }
  }
}

  
Podemos ver que se han declarado 2 funciones antes del main y que cargamos en modulo = “res/modulo2.it” (el modulo2.it que está en el directorio res).
  
Lo mismo si lo escuchas te suena el tema :).
  
Cuando el evento de cerrar se active se descargará el modulo y se cerrará la ventana. También es bueno comentar que se ha usado la función: SDL_AudioSpec
  
Y bueno. Supongo que con esto ya se tiene un ejemplo de como cargar un modulo de sonido y hacer que suene en nuestro programa.
  
En este ejemplo se carga al inicio y no se para hasta que cerramos la ventana. Pero nada nos impide como vimos en el ejemplo del teclado hacer que se inicie en otro momento o que se inicie usando una tecla y que se pare pulsando otra.
  
Digamos que como en los módulos podemos cargar un solo sample o un solo instrumento y hacer que suene como queramos podríamos crear una combinación de sonidos que suenen cuando pulsamos una tecla u otra y crearnos una caja de ritmos o simplemente para un programa de radio tener sonidos de aplausos, risas enlatadas, …
  
Saludos cordiales.

2 comentarios sobre “SDL en C bajo GNU/Linux 010 – Modulo sonando de fondo

  1. ya con el anterior, se esta poniendo denso el curso! otros mas asi y me pongo a aprender en serio

  2. :). Algunos más tienen que llegar. Al menos algunos ejemplos de uso de tipografias, efectos como text zoom, plasma, raster bar, …

    Pero supongo que no pasará esto de 20 posts.

    Saludos cordiales.

Deja un comentario

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *