micro.CAL
a microtonal CakewalkTM Application Language program

© 1999 by Joseph L. Monzo


    micro.CAL is my little microtonal user-input program for the popular CakewalkTM music sequencer software.

    It allows the user to input ratios as fractions, right at the computer, to indicate the pitches using the step-time method (i.e., putting the notes in one at a time, as opposed to playing live).

    It allows the user to specify note-durations in the way musicians are ordinarily used to doing it: as fractions of a metrical unit. This also gives the ability to input any kind of tuplet and have the computer do the timing calculations.

    The "NOW" parameter is automatically updated to the next tick after the end of the note just inputted, so you can just continue adding notes on a single track until you're finished.

    There are a few default values programmed in, and they are all fully commented in the code, so they're easy to edit.

    Also, a few lines that can provide additional input (such as 'tonic' and 'meter') have been commented out. The semicolons which designate comments can simply be removed if you want or need to use this input. I always use double semicolons, just to make sure CAL doesn't try to turn my comments into lines of code! (If you're a CAL programmer, that's a good habit to develop.)

    By the way, it was difficult to get CAL to do this, since CAL uses only integer math and does not have logarithms. I got around the integer math by multiplying all the numbers by 10000 or 1000000. The lack of logarithms was a more difficult hurdle, but finally solved, thanks to Alexander Ellis's ingenious augmented bidmodulus formula, which is accurate to within 2 cents for any ratio.

    (See p 447 in Ellis's great translation of Helmholtz's On The Sensations Of Tone.)

    It is my intention to eventually allow input of prime-factor notation for just-intonation, and also to allow input of degrees in non-12 equal temperaments, but so far only ratio input is working.

    The input also needs to be cleaned up a little. It only enters notes in one "octave" right now, and you have to edit the "octave" of the note after you finish inputting it with CAL.

    Also, I noticed one bug recently, where it entered an "A" instead of a "D". There are probably still a few small bugs in it. But overall, it works nicely and is much easier than entering the pitch-bend manually.

    My version of CAL is the ancient v. 21, which came with my CakewalkTM Pro for Windows 2.01. So it should work on just about anyone's version of CakewalkTM.

    Please feel free to offer any improvements, and to submit this link to CakewalkTM discussion groups.

    Download micro.CAL

    (It downloads as a text file, which it is. Just click on 'View|Source' on the menu bar, and when it opens in 'notepad', save it as "micro.cal" with 'File|Save As')

CakewalkTM is a trademark of Twelve-Tone Systems. (how ironic)


LINKS

    You can find a ton of information on CAL at:

    • John S. Allen's excellent CAL pages.
      (lots of other good info on microtonal music and bicycles too,
      and one of the very few places where Fokker has a web presence).

    • Glen Cardenas's great CAL tutorial.

    • Alan Myers's big collection of CAL links.


    Below is a print-out of micro.cal in plain text form, for those who wish to just read it or copy and paste it into CAL themselves.

    
    ;;===================================================
    ;;
    ;; MICRO.CAL  v. 1.2 (c) 1999 by Joe Monzo
    ;; 1999-4-7 adds automatic update of Start Time
    ;; 1999-4-5 adds metrical input - now working
    ;;
    ;; in v 1.1 'metric input' code is commented out,
    ;; so v 1.1 works with 'duration input'.
    ;; comments quoting Ellis deleted to save space - see v 1.1
    ;;-----------------------------------------------------------------------------------------
    ;; 1999-3-31 *** THIS VERSION WORKS  ****
    ;;-----------------------------------------------------------------------------------------
    ;; 1999-3-25
    ;;
    ;; CAL routine to calculate pitch-bend from a ratio
    ;;   and insert it, with a note, into a Cakewalk file
    ;;
    ;; The user may change the NOW time for the insertion.
    ;;
    ;; - still needs if-then for "ET or JI?" routines
    ;; - still needs ratio calculation procedure for ETs
    ;; - figure out how to indicate octaves with exp2
    ;; - a loop is necessary, so whole phrases can be entered
    ;;
    ;;====================================================
    ;; START PROGRAM
    
    (do
    
       ;;================================
       ;; DECLARATIONS
    
       ;;--------------------------------------------
       ;; Declare constants
    
    	(long bendcalc (/ (* 2 1000000) 8192))	;; 2 multiplied for int math
    	(dword bimodulus1 3477)
    	(dword multiplier 10000)
    	(dword bimodulus (* bimodulus1 multiplier))	;; Ellis's bimodulus 3477 multiplied for int math
    
    
       ;;--------------------------------------------
       ;; Declare variables for user input
    
    	(dword Time Now)     ;; these are all simply
    	(int ScaleSize 12)   ;; default initial values -
    	(int Degree 0)       ;; they can be changed
    	(int MaxDegree 11)   ;;
    	(int WhlAmt 0)       ;;
    	(int duration 120)   ;;
    
    	(int tupnum 1)
    	(int tupdenom 1)
    	(int noteval 4)  ;;SET METER DENOMINATOR
    	(int dur 1)
    
    	(word numerator 1)
    	(word denom 1)
    
    	;; These variables will be used when
    	;; prime-factor notation is implemented
    	;;
    	;; (int exp2 0)
    	;; (int exp3 0)
    	;; (int exp5 0)
    	;; (int exp7 0)
    	;; (int exp11 0)
    	;; (int exp13 0)
    
    
       ;;--------------------------------------------
       ;; declare variables for cents calculation
    	(word larger 0)
    	(word smaller 0)
    	(long cents 0)
    	(long centsadd 0)
    
       ;;--------------------------------------------
       ;; declare variables for pitch-bend calculation
    
    	(long semitones)
    	(long hisemitones)
    	(long closest12eq)
    	(long eqerror)
    	(long pitchbend)
    	(int midinote 60)
    	(int tonic 0)	;; SET 12-EQ VALUE OF 1/1
    
       ;;========================
       ;; INPUT
    
       ;;--------------------------------------------
       ;; User input
    
    	;;---------------
    	;; timing info
    
    	;;(getInt tonic "Key or tonic (0=C, 1=Db, 2=D, 3=Eb, 4=E, 5=F, 6=F#, 7=G, 8=Ab, 9=A, 10=Bb, 11=B) :" 0 11) ;;MAY BE COMMENTED OUT
    	;;(getTime Time "Starting Time of note:" )  ;;REALLY NOT NECESSARY NOW
    	;;(getInt duration "Duration (240 = half, 120 = quarter, 60 = 8th, 40 = triplet 8th, 30 = 16th, 20 = triplet 16th):" 1 4800) ;;REALLY NOT NECESSARY NOW
    
    	;;---------------------------
    	;; variables for metrical input
    	;;
    	;;(getInt noteval "denominator of rhythmic value of note (1=whole, 2=half, 4=quarter, etc.) :" 1 32) ;;MAY BE COMMENTED OUT
    	(getInt dur "duration of note in units of denominator (1, 2, 3, etc.):" 1 32)
    	;;(getInt tupdenom "tuplet: number of notes in tuplet - hit enter if not a tuplet:" 1 12) ;;MAY BE COMMENTED OUT
    	;;(getInt tupnum "tuplet: number of notes ordinarily occupying tuplet space - hit enter if not a tuplet:" 1 32) ;;MAY BE COMMENTED OUT
    
    	;;----------------
    	;; CALCULATE DURATION	 - for metrical input
    
    	(do
    		(= duration
    			(-
    				(/
    					(* (* TIMEBASE 4) (* tupnum dur))
    					(* tupdenom noteval)
    				)
    				1		;;1 unit subtracted to leave room for pitch-bend timing
    			)
    		)
    	)
    
    	;;----------------
    	;; ET or JI?
    
    	;; THIS STILL NEEDS TO BE DONE for combined ET/JI version
    
    
    	;;----------------
    	;; ET section now used only in ET-only version of program
    	;;
    	;;(getInt ScaleSize "Number of EQ steps in scale:" 5 72)
    	;;(= MaxDegree (- ScaleSize 1))
    
    	;;(getInt Degree "What is the Degree of this note:" 0 MaxDegree)
    
    
    	;;----------------
    	;; JI section - to be combined with ET in future version
    
    	(getWord numerator "Numerator of ratio:" 1 65000)
    	(getWord denom "Denominator of ratio:" 1 65000)
    
    
        ;;========================
        ;; CALCULATIONS
    
        ;; calculate cents, without logarithms using Ellis's augmented bimodulus
    
    	(if (== numerator denom)
    		(do
    			(= smaller numerator)
    			(= larger denom)
    		)
    	)
    
    
    	(if (> numerator denom)
    		(do
    			(= larger numerator)
    			(= smaller denom)
    		)
    	)
    
    	(if (< numerator denom)
    		(do
    			(= smaller numerator)
    			(= larger denom)
    		)
    	)
    
    
    	(while (> larger (* 2 smaller) )
    
    		(if (== (% larger 2) 0)
    
    			(do (= larger (/ larger 2) ) )
    			(do (= smaller (* smaller 2) ) )
    
    		)
    	)
    
    
    
    	(while (> (* 3 larger) (* 4 smaller) )
    
    		(if (< (* 2 larger) (* 3 smaller) )
    
    			(do
    				(= larger (* 3 larger) )
    				(= smaller (* 4 smaller) )
    				(= cents (* 498 multiplier) )
    			)
    
    			(do
    				(= larger (* 2 larger) )
    				(= smaller (* 3 smaller) )
    				(= cents (* 702 multiplier) )
    			)
    		)
    	)
    
    
    	(do
    		(= centsadd
    			(/
    				(* (- larger smaller) bimodulus)
    				(+ larger smaller)
    			)
    		)
    	)
    
    
    
    	(if (> centsadd (* 450 multiplier) )
    		(do
    			(= centsadd (+ centsadd (* 1 multiplier) ) )
    		)
    	)
    
    
    	(do
    		(= cents (+ cents centsadd) )
    	)
    
       ;;--------------------------------------------
       ;; calculate pitch-bend and midi-note
       ;;
       ;; all numbers multiplied by 10^6 for integer math
       ;; MIDI-notes calculated from "middle-C"
    
    	(do
    		(= semitones cents)
    		(= hisemitones (+ cents 500000) )
    		(= closest12eq (- hisemitones (% hisemitones 1000000) ) )
    		(= eqerror (- semitones closest12eq) )
    		(= pitchbend (/ eqerror bendcalc) )
    		(= midinote (+ (+ 60 tonic) (/ closest12eq 1000000) ) )
    	)
    
    
       ;;========================
       ;; OUTPUT
    
       ;;--------------------------------------------
       ;; Insert the new event into Cakewalk file
    
    	(do
    		(insert Time 1 WHEEL pitchbend)
    		(insert (+ Time 1) 1 NOTE midinote 64 duration)
    	)
    
    	;;-------------------------------------------
    	;; Automatically update the Start Time for the next entry
    
    	(do
    		(= Now
    			(+ Time
    				(+ duration 1)
    			)
    		)
    	)
    )
    
    ;; END PROGRAM
    ;;=======================================================
    
    

updated:
2006.09.22 -- source code of micro.cal added as text onto webpage


  • If you don't understand my theory or the terms I've used, start here
    or try some definitions.
  • I welcome feedback about this webpage:
    corrections, improvements, good links.
    Let me know if you don't understand something.


    return to my home page
    return to the Sonic Arts home page
    om?subject=micro-CAL> feedback about this webpage:
    corrections, improvements, good links.
    Let me know if you don't understand something.

    return to my home page
    return to the Sonic Arts home page L>