DECLARE SUB CAKETIME (MEASBEATTICK$, AdLibEventStartTime%) DECLARE SUB OPENFILE (BUFNUM%, MODE$, DEFAULT$, A$, DAFLAG%, EXT$) DECLARE SUB FILESPEC (DR$, NAME$, FILENAME$) DECLARE SUB ANYKEY (ZA$) DECLARE SUB INPUTUCASE (STRNG$) OPTION BASE 1 REM $INCLUDE: 'COMDEF.BAS' DIM HEADER AS STRING * 48 DIM TPB AS STRING * 1 DIM BPM AS STRING * 1 DIM BYTE AS STRING * 1 DIM TEMP2 AS STRING * 2 DIM TEMP4 AS STRING * 4 DIM TEMP11 AS STRING * 11 DIM AdLibNoteData AS STRING * 4 SIZE& = FRE(-1) 'Dynamically allocate array size for users memory SIZE& = (SIZE& - 1000) / 8 'Need 1000 bytes for rest of variables IF SIZE& > 32767 THEN SIZE& = 32767 DIM TrackNum(SIZE&) AS INTEGER 'Track number DIM AdLibEventStartTime(SIZE&) AS INTEGER 'Time the event started (in AdLib ticks). 'Measured from the start of the song. DIM CakeNote(SIZE&) AS INTEGER 'MIDI note number DIM CakeDur(SIZE&) AS INTEGER 'Duration of the event (in Cakewalk ticks) SCREEN 0 MESSAGE% = 10 'Color used for printing messages and prompts EMPH% = 12 'Emphasized color for messages and prompts DATACOLOR% = 11 'Color used for entering data COLOR EMPH%, 0 CLS PRINT PRINT PRINT PRINT PRINT " A D L 2 C A K E" PRINT COLOR MESSAGE%, 0 PRINT " Version 1.0" PRINT PRINT " Nov. 1, 1988" PRINT PRINT PRINT PRINT PRINT PRINT " Written by Fred A. McGiven" PRINT " CIS <70325,520>" PRINT PRINT PRINT PRINT PRINT " With the amount of memory in your machine:" PRINT " you are limited to a total of"; SIZE&; "note events." PRINT PRINT CALL ANYKEY(AN$) FI1$ = "FILE NAME (ENTER = " FI2$ = ", A to Abort)" CLS PRINT "This program reads a song data file created by Ad Lib's (TM) Visual Composer" PRINT "and converts it to a Cakewalk ASCII file. After the conversion you" PRINT "will need to use the ASC2CAKE conversion utility furnished with" PRINT "Cakewalk to make the file usable in Cakewalk. You may have to deselect" PRINT "the Ad Lib percusion tracks in Cakewalk. This program only supports" PRINT "conversion of note data, i.e. it does not look at volume or tempo data." PRINT PRINT "Ad Lib Inc. makes a plug in synthesizer card and a number of related software" PRINT "packages for the IBM PC/XT/AT or compatible. If you have a high speed computer" PRINT "you may need to set it to a lower speed in order to make it work properly." PRINT PRINT "Cakewalk is made by Twelve Tone Systems and is Copyrighted by Greg Hendershot." PRINT "Cakewalk is a MIDI sequencer program that allows you to record, edit, and play" PRINT "music on your synthesizer/keyboard. You will need a Roland MPU-401, MPU-IPC," PRINT "or equivalent along with a MIDI instrument in order to use this program." PRINT PRINT "Feel free to make any modifications you want to this program. If there are any" PRINT "energetic programmers out there who improve on this program please upload your" PRINT "your new masterpiece for others to share. I hope you enjoy this program." PRINT PRINT CALL ANYKEY(AN$) ADLIBFILE$ = "TEST.ROL" CAKEWALKFILE$ = "TEST.ASC" START: BUFNUM% = 1 MODE$ = "B" CLS PRINT "Name of the AdLib file to be converted (usually has .ROL extension)" DAFLAG% = 0 EXT$ = ".ROL" CALL OPENFILE(BUFNUM%, MODE$, ADLIBFILE$, A$, DAFLAG%, EXT$) IF A$ = "N" THEN CLOSE CLS GOTO TRYAGAIN END IF BUFNUM% = 2 MODE$ = "O" PRINT PRINT "Name of the new Cakewalk file (normally has .ASC extension)" DAFLAG% = 0 EXT$ = ".ASC" I% = INSTR(ADLIBFILE$, ".") IF I% > 1 THEN CAKEWALKFILE$ = LEFT$(ADLIBFILE$, I% - 1) + EXT$ END IF CALL OPENFILE(BUFNUM%, MODE$, CAKEWALKFILE$, A$, DAFLAG%, EXT$) IF A$ = "N" THEN CLOSE GOTO TRYAGAIN END IF GET #1, 1, HEADER 'Get first 48 bytes from the file TPB$ = MID$(HEADER, 45, 1) 'Read timimg info from AdLib file BPM$ = MID$(HEADER, 47, 1) TicksPerBeat% = ASC(TPB$) BeatsPerMeasure% = ASC(BPM$) TicksPerMeasure% = TicksPerBeat% * BeatsPerMeasure% TRACK% = 0 'Initialization AdLibTickDur% = 0 FOUNDTRACK% = 0 EVENT% = 0 NEXTTRACK: 'Read AdLib Visual Composer file 'Find ?Voix in the file EXITFLAG% = 0 PRINT "Searching for track data" DO GET #1, , BYTE$ 'Get 1 byte from the file IF BYTE$ = "?" THEN GET #1, , TEMP4$ 'Get next four bytes IF TEMP4$ = "Voix" THEN EXITFLAG% = 1 END IF END IF LOOP UNTIL EXITFLAG% = 1 OR EOF(1) IF EOF(1) THEN IF FOUNDTRACK% = 1 THEN PRINT PRINT "Sorting all tracks by time" GOSUB SortByStartTime PRINT #2, "[VARIABLES]" PRINT #2, "Tempo=120" PRINT #2, "Tempo1=60" PRINT #2, "Tempo2=120" PRINT #2, "Tempo3=240" TIM$ = RTRIM$(LTRIM$(STR$(BeatsPerMeasure%))) PRINT #2, "Timesig="; TIM$; "/4" PRINT #2, "Keysig=0" PRINT #2, PRINT #2, "[TRACKS]" FOR I% = 1 TO TRACK% PRINT #2, LTRIM$(STR$(I%)); " "; CHR$(34); "Track"; I%; CHR$(34); " PLAY 0 0 0" NEXT PRINT #2, PRINT #2, "[EVENTS]" FOR I% = 1 TO EVENT% PRINT #2, LTRIM$(STR$(TrackNum(I%))); " 1 "; 'Track & MIDI channel (1) CALL CAKETIME(MEASBEATTICK$, AdLibEventStartTime(I%)) PRINT #2, MEASBEATTICK$; " N"; PRINT #2, CakeNote(I%); PRINT #2, "64"; 'Velocity PRINT #2, CakeDur(I%) NEXT PRINT #2, PRINT #2, "[END]" ELSE PRINT "Conversion NOT successful!" END IF CLOSE GOTO TRYAGAIN END IF 'If Voix is found program drops through to here GET #1, , TEMP11$ 'Discard next 11 bytes GET #1, , TEMP2$ 'Read total number of ticks on the AdLib track 'TRACKTICKS% - total number of ticks on the AdLib track TRACKTICKS% = ASC(MID$(TEMP2$, 1, 1)) + 256 * ASC(MID$(TEMP2$, 2, 1)) IF TRACKTICKS% = 0 THEN GOTO NEXTTRACK'If no data for the track go on to the next one TRACK% = TRACK% + 1 TOTALTICKS% = 0 ' counter to keep track of how many trackticks have been processed PRINT "Reading track number "; TRACK% DO ' Loop to read and process the track note/duration data EVENT% = EVENT% + 1 'EVENT% = number of events (all tracks combined) GET #1, , AdLibNoteData$ 'Get four bytes of note data CakeNote(EVENT%) = ASC(MID$(AdLibNoteData$, 1, 1)) AdLibTickDur% = ASC(MID$(AdLibNoteData$, 3, 1)) + 256 * ASC(MID$(AdLibNoteData$, 4, 1)) AdLibEventStartTime(EVENT%) = TOTALTICKS% TOTALTICKS% = TOTALTICKS% + AdLibTickDur% BM! = BeatsPerMeasure% ADLTD! = AdLibTickDur% CakeDur(EVENT%) = INT(.5 + 120 / TicksPerBeat% * ADLTD!) 'Subtract one from duration (either Cakewalk or my synthesizer 'doesn't like one note starting exactly when another ends) IF CakeDur(EVENT%) > 15 THEN CakeDur(EVENT%) = CakeDur(EVENT%) - 1 TrackNum(EVENT%) = TRACK% IF CakeNote(EVENT%) = 0 THEN EVENT% = EVENT% - 1 'Discard if no note is being played LOOP UNTIL TOTALTICKS% >= TRACKTICKS% FOUNDTRACK% = 1 GOTO NEXTTRACK TRYAGAIN: INPUT "Do you want to convert another (Y/N)"; AN$ AN$ = LTRIM$(UCASE$(AN$)) IF AN$ = "" THEN AN$ = "Y" IF LEFT$(AN$, 1) = "Y" THEN GOTO START STOP SortByStartTime: J = 2 K = 1 M = EVENT% WHILE J > K M = INT(M / 2) IF M = 0 THEN TEMP = FRE("") RETURN ELSE J = 1 K = EVENT% - M END IF WHILE J <= K I = J LOOPFLAG% = 1 WHILE LOOPFLAG% = 1 L = I + M IF AdLibEventStartTime(I) >= AdLibEventStartTime(L) THEN SWAP TrackNum(I), TrackNum(L) SWAP AdLibEventStartTime(I), AdLibEventStartTime(L) SWAP CakeNote(I), CakeNote(L) SWAP CakeDur(I), CakeDur(L) I = I - M IF I >= 1 THEN LOOPFLAG% = 1 ELSE LOOPFLAG% = 0 END IF ELSE LOOPFLAG% = 0 END IF WEND J = J + 1 WEND WEND RETURN FILEHANDLER: IF ERR <> OLDERR% THEN CLS PRINT "FILE Error "; ERR CALL ANYKEY(AN$) CLS OLDERR% = ERR END IF ERRFLAG% = ERR RESUME NEXT END SUB ANYKEY (ZA$) PRINT "Hit any key to continue" ZA$ = "" WHILE ZA$ = "" ZA$ = INKEY$ WEND END SUB SUB CAKETIME (MEASBEATTICK$, AdLibEventStartTime%) SHARED BeatsPerMeasure%, TicksPerBeat%, TicksPerMeasure% 'This subprogram converts a AdLib event starting time (in Ad Lib ticks) 'to the form of..... measure:beat:tick that Cakewalk wants to see. NUMMEASURES% = INT(AdLibEventStartTime% / TicksPerMeasure% + .01) TICKSLEFT% = AdLibEventStartTime% - NUMMEASURES% * TicksPerMeasure% NUMBEATS% = INT(TICKSLEFT% / TicksPerBeat% + .01) TICKSLEFT% = TICKSLEFT% - NUMBEATS% * TicksPerBeat% ADLTD! = TICKSLEFT% NUMTICKS% = INT(.5 + 120 / (TicksPerBeat%) * ADLTD!) MEAS$ = LTRIM$(RTRIM$(STR$(NUMMEASURES% + 1))) BEAT$ = LTRIM$(RTRIM$(STR$(NUMBEATS% + 1))) TICK$ = LTRIM$(RTRIM$(STR$(NUMTICKS%))) MEASBEATTICK$ = MEAS$ + ":" + BEAT$ + ":" + TICK$ END SUB SUB FILESPEC (DR$, NAME$, FILENAME$) STATIC REM January 10, 1987 ON ERROR GOTO FILEHANDLER IF INSTR(NAME$, ":") <> 0 OR INSTR(NAME$, "\") <> 0 THEN FILENAME$ = NAME$ ELSE TEMP$ = RIGHT$(DR$, 1) IF TEMP$ = ":" OR TEMP$ = "\" THEN FILENAME$ = DR$ + NAME$ ELSE IF DR$ <> "" THEN FILENAME$ = DR$ + "\" + NAME$ ELSE FILENAME$ = NAME$ END IF END IF END IF END SUB SUB INPUTUCASE (STRNG$) STATIC INPUT STRNG$ STRNG$ = UCASE$(STRNG$) END SUB SUB OPENFILE (BUFNUM%, MODE$, DEFAULT$, A$, DAFLAG%, EXT$) STATIC REM October 30, 1988 SHARED MESSAGE%, EMPH% SHARED DRIVE$ ON ERROR GOTO FILEHANDLER ERRFLAG% = 0 FI1$ = "FILE NAME (ENTER = " FI2$ = ", A to Abort)" CR$ = CHR$(13) IF ERRFLAG% <> 0 THEN GOTO OPENEXIT OPENFILESTART: IF DAFLAG% = 1 THEN A$ = DEFAULT$ GOTO DONTASK END IF SCREEN 0, 1 COLOR MESSAGE%, 0 PRINT FI1$; COLOR EMPH%, 0 IF INSTR(DEFAULT$, ".") = 0 THEN DEFAULT$ = DEFAULT$ + EXT$ PRINT DEFAULT$; COLOR MESSAGE%, 0 PRINT FI2$; CALL INPUTUCASE(A$) IF A$ = CR$ OR A$ = "" THEN A$ = DEFAULT$ IF A$ = "A" OR ERRFLAG% <> 0 THEN A$ = "N" GOTO OPENEXIT END IF IF INSTR(A$, ".") = 0 THEN A$ = A$ + EXT$ DEFAULT$ = A$ DONTASK: CALL FILESPEC(DRIVE$, A$, FILENAME$) OPEN "R", BUFNUM%, FILENAME$ IF LOF(BUFNUM%) = 0 THEN CLOSE BUFNUM% KILL FILENAME$ FSTAT$ = "N" ELSE CLOSE BUFNUM% FSTAT$ = "Y" END IF IF ERRFLAG% <> 0 THEN GOTO OPENEXIT IF MODE$ = "O" AND FSTAT$ = "Y" AND DAFLAG% = 0 THEN COLOR EMPH%, 0 PRINT A$; COLOR MESSAGE%, 0 PRINT " Already Exists! OVERWRITE? (Y/N)"; CALL INPUTUCASE(AN$) IF AN$ = "Y" THEN GOTO OPENIT ELSE GOTO OPENFILESTART END IF END IF IF (MODE$ = "I" OR MODE$ = "B") AND FSTAT$ = "N" THEN A$ = "N" PRINT "File does not exist" INPUT "Hit ENTER to continue"; AN$ PRINT IF DAFLAG% = 1 THEN GOTO OPENEXIT GOTO OPENFILESTART END IF OPENIT: CALL FILESPEC(DRIVE$, A$, FILENAME$) OPEN MODE$, BUFNUM%, FILENAME$ OPENEXIT: END SUB