return NULL; /* cannot find image file */
}
+char *getCustomSoundFilename(char *basename)
+{
+ static char *filename = NULL;
+
+ if (filename != NULL)
+ free(filename);
+
+ /* 1st try: look for special artwork in current level series directory */
+ filename = getPath3(getCurrentLevelDir(), SOUNDS_DIRECTORY, basename);
+ if (fileExists(filename))
+ return filename;
+
+ /* 2nd try: look for special artwork in private artwork directory */
+ filename = getPath2(getUserSoundsDir(), basename);
+ if (fileExists(filename))
+ return filename;
+
+ /* 3rd try: look for special artwork in configured artwork directory */
+ filename = getPath2(getSetupArtworkDir(artwork.snd_current), basename);
+ if (fileExists(filename))
+ return filename;
+
+ /* 4th try: look for default artwork in new default artwork directory */
+ filename = getPath2(getDefaultSoundsDir(SOUNDS_SUBDIR), basename);
+ if (fileExists(filename))
+ return filename;
+
+ /* 5th try: look for default artwork in old default artwork directory */
+ filename = getPath2(options.sounds_directory, basename);
+ if (fileExists(filename))
+ return filename;
+
+ return NULL; /* cannot find image file */
+}
+
void InitTapeDirectory(char *level_subdir)
{
createDirectory(getUserDataDir(), "user data", PERMS_PRIVATE);
#include "system.h"
#include "sound.h"
#include "misc.h"
+#include "setup.h"
static int num_sounds = 0, num_music = 0;
}
#define CHUNK_ID_LEN 4 /* IFF style chunk id length */
-#define WAV_HEADER_SIZE 20 /* size of WAV file header */
+#define WAV_HEADER_SIZE 16 /* size of WAV file header */
static boolean LoadSoundExt(char *sound_name, boolean is_music)
{
char *filename;
#if !defined(TARGET_SDL) && !defined(PLATFORM_MSDOS)
byte sound_header_buffer[WAV_HEADER_SIZE];
- char chunk[CHUNK_ID_LEN + 1];
- int chunk_size, dummy;
+ char chunk_name[CHUNK_ID_LEN + 1];
+ int chunk_size;
FILE *file;
int i;
#endif
Sound = checked_realloc(Sound, num_sounds * sizeof(struct SampleInfo));
snd_info = &Sound[num_sounds - 1];
+ snd_info->data_len = 0;
+ snd_info->data_ptr = NULL;
+#if 0
snd_info->name = sound_name;
+#endif
- filename = getPath2((is_music ? options.music_directory :
- options.sounds_directory), snd_info->name);
+ if (is_music)
+ filename = getPath2(options.music_directory, sound_name);
+ else
+ filename = getStringCopy(sound_name);
#if defined(TARGET_SDL)
if ((snd_info->mix_chunk = Mix_LoadWAV(filename)) == NULL)
{
- Error(ERR_WARN, "cannot read sound file '%s' -- no sounds", filename);
+ Error(ERR_WARN, "cannot read sound file '%s'", filename);
free(filename);
return FALSE;
}
if ((file = fopen(filename, MODE_READ)) == NULL)
{
- Error(ERR_WARN, "cannot open sound file '%s' -- no sounds", filename);
+ Error(ERR_WARN, "cannot open sound file '%s'", filename);
free(filename);
return FALSE;
}
- /* read chunk "RIFF" */
- getFileChunk(file, chunk, &chunk_size, BYTE_ORDER_LITTLE_ENDIAN);
- if (strcmp(chunk, "RIFF") != 0)
+ /* read chunk id "RIFF" */
+ getFileChunk(file, chunk_name, &chunk_size, BYTE_ORDER_LITTLE_ENDIAN);
+ if (strcmp(chunk_name, "RIFF") != 0)
{
Error(ERR_WARN, "missing 'RIFF' chunk of sound file '%s'", filename);
fclose(file);
return FALSE;
}
- /* read chunk "WAVE" */
- getFileChunk(file, chunk, &dummy, BYTE_ORDER_LITTLE_ENDIAN);
- if (strcmp(chunk, "WAVE") != 0)
+ /* read "RIFF" type id "WAVE" */
+ getFileChunk(file, chunk_name, NULL, BYTE_ORDER_LITTLE_ENDIAN);
+ if (strcmp(chunk_name, "WAVE") != 0)
{
- Error(ERR_WARN, "missing 'WAVE' chunk of sound file '%s'", filename);
+ Error(ERR_WARN, "missing 'WAVE' type ID of sound file '%s'", filename);
fclose(file);
free(filename);
return FALSE;
}
- /* read header information */
- for (i=0; i<WAV_HEADER_SIZE; i++)
- sound_header_buffer[i] = fgetc(file);
-
- /* read chunk "data" */
- getFileChunk(file, chunk, &chunk_size, BYTE_ORDER_LITTLE_ENDIAN);
- if (strcmp(chunk, "data") != 0)
+ while (getFileChunk(file, chunk_name, &chunk_size, BYTE_ORDER_LITTLE_ENDIAN))
{
- Error(ERR_WARN, "missing 'data' chunk of sound file '%s'", filename);
- fclose(file);
- free(filename);
- return FALSE;
+#if 0
+ printf("DEBUG: file '%s', chunk id '%s', chunk size '%d' [%d]\n",
+ filename, chunk_name, chunk_size, feof(file));
+#endif
+
+ if (strcmp(chunk_name, "fmt ") == 0)
+ {
+ /* read header information */
+ for (i=0; i < MIN(chunk_size, WAV_HEADER_SIZE); i++)
+ sound_header_buffer[i] = fgetc(file);
+
+ if (chunk_size > WAV_HEADER_SIZE)
+ ReadUnusedBytesFromFile(file, chunk_size - WAV_HEADER_SIZE);
+ }
+ else if (strcmp(chunk_name, "data") == 0)
+ {
+ snd_info->data_len = chunk_size;
+ snd_info->data_ptr = checked_malloc(snd_info->data_len);
+
+ /* read sound data */
+ if (fread(snd_info->data_ptr, 1, snd_info->data_len, file) !=
+ snd_info->data_len)
+ {
+ Error(ERR_WARN,"cannot read 'data' chunk of sound file '%s'",filename);
+ fclose(file);
+ free(filename);
+ return FALSE;
+ }
+
+ /* check for odd number of sample bytes (data chunk is word aligned) */
+ if ((chunk_size % 2) == 1)
+ ReadUnusedBytesFromFile(file, 1);
+ }
+ else /* unknown chunk -- ignore */
+ ReadUnusedBytesFromFile(file, chunk_size);
}
- snd_info->data_len = chunk_size;
- snd_info->data_ptr = checked_malloc(snd_info->data_len);
+ fclose(file);
- /* read sound data */
- if (fread(snd_info->data_ptr, 1, snd_info->data_len, file) !=
- snd_info->data_len)
+ if (snd_info->data_ptr == NULL)
{
- Error(ERR_WARN, "cannot read sound file '%s' -- no sounds", filename);
- fclose(file);
+ Error(ERR_WARN, "missing 'data' chunk of sound file '%s'", filename);
free(filename);
return FALSE;
}
- fclose(file);
-
for (i=0; i<snd_info->data_len; i++)
snd_info->data_ptr[i] = snd_info->data_ptr[i] ^ 0x80;
snd_info->sample_ptr = load_sample(filename);
if (!snd_info->sample_ptr)
{
- Error(ERR_WARN, "cannot read sound file '%s' -- no sounds", filename);
+ Error(ERR_WARN, "cannot read sound file '%s'", filename);
return FALSE;
}
return LoadSoundExt(sound_name, FALSE);
}
+boolean LoadCustomSound(char *basename)
+{
+ char *filename = getCustomSoundFilename(basename);
+
+ if (filename == NULL)
+ {
+ Error(ERR_WARN, "cannot find sound file '%s' -- no sounds", filename);
+ return FALSE;
+ }
+
+ return LoadSound(filename);
+}
+
boolean LoadMod(char *mod_name)
{
#if defined(TARGET_SDL)