#ifndef NOAUDIO
#include <SDL/SDL_mixer.h>

int audio;
bool mplaying = false;

void musicFinished() { mplaying = false;}

void initAudio() {
  if(audio == 0) {  
    if(Mix_OpenAudio(MIX_DEFAULT_FREQUENCY, MIX_DEFAULT_FORMAT, 2, 4096) != 0)  {
      fprintf(stderr, "Unable to initialize audio: %s\n", Mix_GetError());
      audio = 1;
      }
    else audio = 2;
    Mix_AllocateChannels(16);
    Mix_HookMusicFinished(musicFinished);
    }
  }

void closeAudio() {
  if(audio == 2) Mix_CloseAudio();
  audio = 0;
  }

void Sound::play(int vol) {
  Mix_VolumeChunk(chunk, vol);
  Mix_PlayChannel(-1, chunk, 0);
  }

Sound::~Sound() {
  Mix_FreeChunk(chunk); 
  }

void Music::play() {
  if(mplaying) Mix_HaltMusic();
  if(Mix_PlayMusic(chunk, 0) >= 0) mplaying = true;
  }

Music::~Music() {
  Mix_FreeMusic(chunk); 
  }

#ifdef USELUA
int lh_loadsound(lua_State *L) {
  checkArg(L, 1, "loadsound");
  initAudio();
  if(audio == 1) return retInt(L, 0);
  Mix_Chunk *chk = Mix_LoadWAV(luaStr(1));
  if(!chk) return retInt(L, 0);
  Sound *snd = new Sound();
  snd->chunk = chk;
  return retObject(L, snd);
  }

int lh_loadmusic(lua_State *L) {
  checkArg(L, 1, "loadmusic");
  initAudio();
  if(audio == 1) return retInt(L, 0);
  Mix_Music *chk = Mix_LoadMUS(luaStr(1));
  if(!chk) return retInt(L, 0);
  Music *snd = new Music();
  snd->chunk = chk;
  return retObject(L, snd);
  }

int lh_playsound(lua_State *L) {
  checkArg(L, 2, "playsound");
  if(audio == 1 || luaInt(1) == 0) return 0;
  Sound *s = luaO(1, Sound);
  s->play(luaInt(2));
  return 0;
  }

int lh_musicvolume(lua_State *L) {
  checkArg(L, 1, "musicvolume");
  if(audio == 1) return 0;
  int vol = luaInt(1);
  Mix_VolumeMusic(vol);
  return 0;
  }

int lh_musichalt(lua_State *L) {
  Mix_HaltMusic();
  mplaying = false;
  return 0;
  }

int lh_playmusic(lua_State *L) {
  checkArg(L, 1, "playmusic");
  if(audio == 1 || luaInt(1) == 0) return 0;
  Music *m = luaO(1, Music);
  m->play();
  return 0;
  }

int lh_musicon(lua_State *L) {
  return retBool(L, mplaying);
  }
#endif

#else
void closeAudio() {}
#endif
