/* * Playlist calculator */ #include #include #include #define BLANK_COLUMN " " #define PROMPT "Song number? " #define LINE_LEN 80 /* max allowed input line length */ #define SONG_LEN 28 /* max displayed name (and artist) length */ #define TAPE_LEN 50 /* available recording time in minutes */ /* Column type - the two columns of the display */ typedef enum { left, right } columns; const char kPlaylistFilename[] = "playlist.txt"; typedef struct { char song[LINE_LEN]; /* song name */ char artist[LINE_LEN]; /* who sang it */ int time; /* song duration in seconds */ int year; /* release year */ columns column; /* which column currently contains the song */ } song_t; /* Display an integer number of seconds as minutes and seconds in the form MM:HH */ void showTime(int seconds) { printf("%2d:%02d", seconds/60, seconds%60); } /* Calculate remaining time available to record */ int getRemainingTime(const song_t songList[], /* song times in seconds */ int numberSongs) /* how many songs in the list */ { int total = 0; /* total time of all songs to be recorded */ int item; for (item = 1; item<=numberSongs; item++) { /* If the song is in the selected column accumulate time */ if (songList[item].column == 1) { total = total + songList[item].time; } } if (total > TAPE_LEN * 60 ) { total = TAPE_LEN * 60; } return TAPE_LEN * 60 - total; } /* Display the two column table of songs */ void showTable(song_t songList[], /* song list */ int numberSongs) /* how many songs in the list */ { int total = 0; /* total time of all songs to be recorded */ int remain; /* recording time available */ int i1 = 1; /* index to song pool */ char title[SONG_LEN+1]; /* Loop until all songs are shown */ while (i1 <= numberSongs) { /* If there are any songs in the pool left to be displayed */ if (songList[i1].column == 1) { /* Display blanks in column 1 */ printf(BLANK_COLUMN); printf(" "); /* column separator */ /* Add this song's time to the total of selected songs */ total = total + songList[i1].time; } /* Display the song info */ printf("[%2d] ", i1); showTime(songList[i1].time); strncpy(title, songList[i1].song, SONG_LEN); title[SONG_LEN] = '\0'; printf(" %s", title); printf("\n"); /* Advance to the next song */ i1++; } /* Convert the total time into minutes:seconds and show it */ printf(BLANK_COLUMN); printf (" Total: "); showTime(total); /* Compute time remaining and show it */ remain = getRemainingTime(songList,numberSongs); printf(" Remaining: "); showTime(remain); printf("\n"); } /* Save the playlist to a file using entire song and artist names */ void saveTable(song_t songList[], /* song list */ int numberSongs) /* how many songs in the list */ { FILE *inf; int i; int written = 0; /* count of songs written */ inf = fopen(kPlaylistFilename, "w"); { for (i=1; i<=numberSongs; i++) { if (songList[i].column) { fprintf(inf, "%4d %4d %-30s %-30s\n", songList[i].time, songList[i].year, songList[i].song, songList[i].artist); written = written + 1; } } } fclose(inf); printf("%d records written to %s.\n", written, kPlaylistFilename); } /* Fill the list of songs from the data file */ int fillTable(song_t songlist[]) /* song list */ { FILE *inFile; /* file handle */ int input_status; /* i/o status indicator */ int count = 1; /* song counter */ /* Open the song file for reading */ inFile = fopen("songdata.txt", "r"); if (inFile == NULL) { printf("Unable to open songdata.txt - missing file?"); exit(1); } /* Obtain the song info */ input_status = fscanf(inFile, "%s%d%s%d", songlist[count].song, &songlist[count].time, songlist[count].artist, &songlist[count].year); /* Loop until EOF */ while (input_status != EOF) { /* Increment how many songs we've read */ count = count + 1; /* Get the next entry in the file */ input_status = fscanf(inFile, "%s%d%s%d", songlist[count].song, &songlist[count].time, songlist[count].artist, &songlist[count].year); } return count - 1; } int main(void) { song_t songlist[99]; /* a list of song records */ int numberSongs; /* final count of number of songs */ int userSelection; /* song number entered by user */ numberSongs = fillTable(songlist); /* Interact with user until they enter a zero */ do { showTable(songlist,numberSongs); printf(PROMPT); scanf("%d", &userSelection); /* If attempting to add a song to selected list */ if (songlist[userSelection].column == 0) { /* See if there is enough time */ if (getRemainingTime(songlist,numberSongs) > songlist[userSelection].time) { /* Toggle column indicator for this item: false means col 1, true means col 2 */ songlist[userSelection].column = !songlist[userSelection].column; } else { printf("\n **** Not enough remaining time for song #%d ****\n\n",userSelection); } } else /* remove song from playlist column */ { songlist[userSelection].column = !songlist[userSelection].column; } }while (userSelection != 0); saveTable(songlist,numberSongs); return (0); }