/*************************************************************************** **************************************************************************** **************************************************************************** * * FunktrackerGOLD - By Jason Nunn * Copyright (C) 1996,1998 Jason Nunn * * FunktrackerGOLD now comes under the GNU General Public License. Please * read the COPYING notice in this distribution. * * ================================================================ * File Finder routines * **************************************************************************** **************************************************************************** ****************************************************************************/ #include #include #include #include #include #include #include "funktracker_defs.h" #include "dsp_mixxer.h" #include "funktracker.h" #include "funkload.h" #include "funkgold_misc.h" #include "funkgold_sm.h" #include "funkgold_pe.h" #include "funkgold.h" typedef struct _tdir_entry { char *filename; mode_t mode; } tdir_entry; tdir_entry *dir_entry_table; int no_dir_entries; int filefind_maxd; int file_type; #define FILE_TYPE_SONG 0 #define FILE_TYPE_SAM 1 int resample_indice = 10000000; unsigned char *file_pos_real; unsigned char *file_pos_hl; unsigned char *file_pos_hl_old; /*************************************************************************** * ***************************************************************************/ void print_resample_factor(void) { char tmpstr[20]; sprintf(tmpstr,"%f",resample_factor); clear_area(8,38,8,60); move(8,38); addstr(tmpstr); move(8,38 + 12); sprintf(tmpstr,"(x%d)",resample_indice); addstr(tmpstr); } void get_resample_params(void) { register int resam_option = 1; set_colour_hl(COL_BOX); clear_area(6,18,10,62); set_colour(COL_TEXT); clear_area(7,19,9,61); move(8,20); addstr("Resample factor: "); print_resample_factor(); while(resam_option) { ch = getch(); switch(ch) { case FC_ENTER: resam_option = 0; break; case FC_ARROW_UP: resample_factor -= 0.00000001 * resample_indice; if(resample_factor < 0.2) resample_factor = 0.2; print_resample_factor(); break; case FC_ARROW_DN: resample_factor += 0.00000001 * resample_indice; if(resample_factor > 5) resample_factor = 5; print_resample_factor(); break; case FC_ARROW_LEFT: if(resample_indice > 10) resample_indice /= 10; print_resample_factor(); break; case FC_ARROW_RIGHT: if(resample_indice < 10000000) resample_indice *= 10; print_resample_factor(); break; } } } /*************************************************************************** * ***************************************************************************/ int compar(const void *file1,const void *file2) { return strcmp( (*(tdir_entry *)file1).filename, (*(tdir_entry *)file2).filename); } int filter_by_ext(char *str,char *ext) { register int p; p = strlen(str) - strlen(ext); if(p) if(!strcmp(str + p,ext)) return 1; return 0; } int wildcard(tdir_entry *entry) { if(entry->mode & S_IFDIR) return 1; if(entry->mode & S_IFREG) if(entry->filename[0] == '.') return 0; if(file_type == FILE_TYPE_SONG) { if(filter_by_ext(entry->filename,".Funk")) return 1; if(filter_by_ext(entry->filename,".fnk")) return 1; if(filter_by_ext(entry->filename,".mod")) return 1; } else { if(filter_by_ext(entry->filename,".wav")) return 1; if(filter_by_ext(entry->filename,".snd")) return 1; if(filter_by_ext(entry->filename,".raw")) return 1; } return 0; } /*************************************************************************** * ***************************************************************************/ void *add_slash(char *dirname) { char *adjst_path; adjst_path = malloc(strlen(dirname) + 2); if(adjst_path != NULL) { strcpy(adjst_path,dirname); if(!((strlen(dirname) == 1) && (dirname[0] == '/'))) strcat(adjst_path,"/"); } return adjst_path; } int load_directory(char *dirname,tdir_entry *table,int dis) { DIR *dp; struct dirent *dir_entry; struct stat statbuf; register int entry_no = 0; char *fullpath_str; char *adjst_path; if(dis) { attron(A_REVERSE); move(3,0); addstr("Please Wait... "); update_screen(); } adjst_path = add_slash(dirname); if(adjst_path == NULL) return -1; if((dp = opendir(dirname)) == NULL) return -1; while(((dir_entry = readdir(dp)) != NULL) && (entry_no < MAX_DIR_ENTRIES)) { fullpath_str = malloc(strlen(dir_entry->d_name) + strlen(adjst_path) + 1); if(fullpath_str != NULL) { strcpy(fullpath_str,adjst_path); strcat(fullpath_str,dir_entry->d_name); if(lstat(fullpath_str,&statbuf) != -1) { (table + entry_no)->filename = malloc(strlen(dir_entry->d_name) + 1); if((table + entry_no)->filename != NULL) { strcpy((table + entry_no)->filename,dir_entry->d_name); (table + entry_no)->mode = statbuf.st_mode; if(wildcard(table + entry_no)) entry_no++; } } free(fullpath_str); } } closedir(dp); free(adjst_path); qsort(table,entry_no,sizeof(tdir_entry),compar); return entry_no; } void unload_directory(tdir_entry *table) { int x; for(x = 0;x < no_dir_entries;x++) { free(table[x].filename); table[x].filename = NULL; } } /*************************************************************************** * miwi 27/05/96 ***************************************************************************/ void filefind_dis_bg(void) { register int y; register amaxy = maxy - 4; display_topbar(); set_colour_hl(COL_BOX); for(y = 0;y < (maxy - 8);y++) { move(y + 5,0); addch(' '); move(y + 5,56); addch(' '); } clear_area(4,0,4,56); clear_area(amaxy,0,amaxy,56); set_colour(COL_TITLE); move(1,0); if(file_type == FILE_TYPE_SONG) addstr("Song Loader (*.Funk, *.fnk, *.mod"); else { addstr("Sample Loader ("); if(funk_info.sample_precision == 8) addstr("8 bit"); else addstr("16 bit"); addstr(" *.snd, *.raw, *.wav"); } addstr(" files)"); move(4,59); addstr("Hit enter to load"); move(5,59); addstr("file."); move(7,59); addstr("Hit 'R' to rename"); move(8,59); addstr("file."); if(file_type == FILE_TYPE_SAM) { move(10,59); addstr("Use the usual note"); move(11,59); addstr("keys to listen to"); move(12,59); addstr("the sample before"); move(13,59); addstr("loading it."); } } /*************************************************************************** * ***************************************************************************/ void filefind_disline(unsigned char pos_hl) { register int x,ad = 55; char tmpstr[55]; move(pos_hl + 5,1); if(pos_hl < filefind_maxd) { strncpy(tmpstr,(dir_entry_table + *file_pos_real + pos_hl)->filename,55); addstr(tmpstr); ad -= strlen(tmpstr); if((dir_entry_table + *file_pos_real + pos_hl)->mode & S_IFDIR) { addch('/'); ad--; } } for(x = 0;x < ad;x++) addch(' '); } void filefind_dis_path(char *directory) { attroff(A_REVERSE); move(3,0); clear_area(3,0,3,79); move(3,0); addnstr(directory,80); } /*miwi 27/05/96*/ void filefind_dis_all(void) { unsigned char pos_hl; attroff(A_REVERSE); for(pos_hl = 0;pos_hl < (maxy - 9);pos_hl++) filefind_disline(pos_hl); attron(A_REVERSE); filefind_disline(*file_pos_hl); *file_pos_hl_old = *file_pos_hl; } void filefind_move_hl(void) { attroff(A_REVERSE); filefind_disline(*file_pos_hl_old); attron(A_REVERSE); filefind_disline(*file_pos_hl); *file_pos_hl_old = *file_pos_hl; } /*************************************************************************** * ***************************************************************************/ void file_cursor_up(void) { if(*file_pos_hl > 0) { (*file_pos_hl)--; filefind_move_hl(); filefind_disline(*file_pos_hl); update_screen(); } else { if(*file_pos_real > 0) (*file_pos_real)--; filefind_dis_all(); update_screen(); } } /*miwi 27/05/96*/ void file_cursor_down(void) { if(*file_pos_hl < (filefind_maxd - 1)) { (*file_pos_hl)++; filefind_move_hl(); filefind_disline(*file_pos_hl); update_screen(); } else { if(no_dir_entries > filefind_maxd) { if(*file_pos_real < (no_dir_entries - (maxy - 9))) (*file_pos_real)++; filefind_dis_all(); update_screen(); } } } /*************************************************************************** * miwi 27/05/96 ***************************************************************************/ int get_file_name( char *directory, unsigned char *fpos_real, unsigned char *fpos_hl, unsigned char *fpos_hl_old, char *filename) { register char option = 0; char *adjst_path = NULL,*adjst2_path = NULL; char new_name[56]; register int nv; register int amaxy = maxy - 9; dir_entry_table = malloc(MAX_DIR_ENTRIES * sizeof(tdir_entry)); if(dir_entry_table == NULL) return -1; file_pos_real = fpos_real; file_pos_hl = fpos_hl; file_pos_hl_old = fpos_hl_old; if(chdir(directory) == -1) return -1; if((no_dir_entries = load_directory(".",dir_entry_table,0)) != -1) { filefind_maxd = no_dir_entries; if(filefind_maxd > amaxy) filefind_maxd = amaxy; filefind_dis_bg(); set_colour(COL_TEXT); filefind_dis_all(); filefind_dis_path(directory); update_screen(); while(option == 0) { ch = getch(); switch(ch) { case FC_SCREEN_ESCAPE: option = -1; break; case FC_ARROW_UP: file_cursor_up(); break; case FC_ARROW_DN: file_cursor_down(); break; case FC_DIR_RENAME: get_string(5 + *file_pos_hl,1,new_name,55); if(rename((dir_entry_table + *file_pos_real + *file_pos_hl)->filename, new_name) != -1) { unload_directory(dir_entry_table); if((no_dir_entries = load_directory(".",dir_entry_table,1)) != -1) { filefind_maxd = no_dir_entries; if(filefind_maxd > amaxy) filefind_maxd = amaxy; } } filefind_dis_all(); filefind_dis_path(directory); update_screen(); break; case FC_ENTER: if((dir_entry_table + *file_pos_real + *file_pos_hl)->mode & S_IFDIR) { adjst_path = add_slash(directory); if(adjst_path != NULL) { adjst2_path = malloc( strlen(adjst_path) + strlen((dir_entry_table + *file_pos_real + *file_pos_hl)->filename) + 1); if(adjst2_path != NULL) { strcpy(adjst2_path,adjst_path); free(adjst_path); strcat( adjst2_path, (dir_entry_table + *file_pos_real + *file_pos_hl)->filename); if(chdir(adjst2_path) != -1) { getcwd(directory,1024); unload_directory(dir_entry_table); if((no_dir_entries = load_directory(".",dir_entry_table,1)) != -1) { *file_pos_real = 0; *file_pos_hl = 0; *file_pos_hl_old = 0; filefind_maxd = no_dir_entries; if(filefind_maxd > amaxy) filefind_maxd = amaxy; filefind_dis_all(); filefind_dis_path(directory); update_screen(); } else ferr_message("Can't open directory."); } free(adjst2_path); } } } else { if(file_type == FILE_TYPE_SAM) get_resample_params(); strcpy(filename,(dir_entry_table + *file_pos_real + *file_pos_hl)->filename); option = 1; } break; } if((file_type == FILE_TYPE_SAM) && ((nv = mus_kb_input()) != -1)) { register int period = nv + (pe_octave_no * 12); tfunk_sb tmp_funk_sb; #pragma pack(1) void *tmp_funk_sam_ptrs; #pragma pack() memcpy(&tmp_funk_sb, &funk_hr_ptr->funk_sb[sm_pos_real + sm_pos_hl],sizeof(tfunk_sb)); tmp_funk_sam_ptrs = funk_sam_ptrs[sm_pos_real + sm_pos_hl]; load_sample(sm_pos_real + sm_pos_hl, (dir_entry_table + *file_pos_real + *file_pos_hl)->filename,1); if(ferr_val != FERR_OK) ferr_message(ferr_messages[ferr_val]); play_slot(period); free(funk_sam_ptrs[sm_pos_real + sm_pos_hl]); memcpy(&funk_hr_ptr->funk_sb[sm_pos_real + sm_pos_hl], &tmp_funk_sb,sizeof(tfunk_sb)); funk_sam_ptrs[sm_pos_real + sm_pos_hl] = tmp_funk_sam_ptrs; } } unload_directory(dir_entry_table); } else option = -1; free(dir_entry_table); return option; } /*************************************************************************** * ***************************************************************************/ int get_song_file_name( char *directory, unsigned char *fpos_real, unsigned char *fpos_hl, unsigned char *fpos_hl_old, char *filename) { file_type = FILE_TYPE_SONG; return get_file_name( directory,fpos_real,fpos_hl,fpos_hl_old,filename); } /*************************************************************************** * ***************************************************************************/ int get_sam_file_name( char *directory, unsigned char *fpos_real, unsigned char *fpos_hl, unsigned char *fpos_hl_old, char *filename) { file_type = FILE_TYPE_SAM; return get_file_name( directory,fpos_real,fpos_hl,fpos_hl_old,filename); }