home *** CD-ROM | disk | FTP | other *** search
/ Computer Music Interactif…cial Edition 1999 Winter / cd 3.iso / mac / Mac / Shares / Midishare™1.68 / Development Tools / Smalltalk / MidiShareInterface.st < prev    next >
Encoding:
Text File  |  1995-10-10  |  5.7 KB  |  302 lines  |  [TEXT/ttxt]

  1. 'From Objectworks\Smalltalk(R), Release 4.1 of 15 April 1992 on 10 October 1995 at 12:40:12 pm'!
  2.  
  3. Object subclass: #MidiShareInterface
  4.     instanceVariableNames: 'open serial incoming tempo offset starttime recording '
  5.     classVariableNames: ''
  6.     poolDictionaries: ''
  7.     category: 'Midi'!
  8. MidiShareInterface comment:
  9. 'This class implements an interface to the GRAME MidiShare 1.68 Midi System.
  10.  
  11. Instance Variables:
  12.     open    <Boolean>     current state of the interface
  13.     serial    <Object>    serial port used for midi in/out (modem, printer)
  14.     incoming    <Object>    received events
  15.     tempo    <Object>    tempo for playback
  16.     offset    <Object>    offset for playback (sequencer ticks)
  17.     starttime    <Object>    offset of last start
  18.     recording    <Boolean>    enabled/disabled recording'!
  19.  
  20.  
  21. !MidiShareInterface methodsFor: 'constants'!
  22.  
  23. defaultConnector
  24.     ^self class connectorModem! !
  25.  
  26. !MidiShareInterface methodsFor: 'initialize-release'!
  27.  
  28. initialize
  29.     
  30.     open := false.
  31.     tempo := 120. "default"
  32.     offset := 0.
  33.     incoming := OrderedCollection new.
  34.     recording := true.! !
  35.  
  36. !MidiShareInterface methodsFor: 'control'!
  37.  
  38. close
  39.  
  40.     "Close MidiShare interface"
  41.     
  42.     self isOpen ifFalse:[^self].
  43.     open := false.
  44.     recording := false.
  45.     
  46.     self primClose.!
  47.  
  48. offset: o tempo: t resolution: resolution delay: ms
  49.  
  50.     "Define the timing constants for playing/recording"
  51.     
  52.     tempo := t.
  53.     offset := o.
  54.     ^self 
  55.         primSetOffset: o 
  56.         tempo: t 
  57.         resolution: resolution 
  58.         delay: ms!
  59.  
  60. open
  61.  
  62.     "Open a MidiShare connection"
  63.     
  64.     self isInstalled ifFalse:[^self error:'MidiShare not installed'].
  65.     self isOpen ifTrue:[^self].
  66.     serial := self defaultConnector.
  67.  
  68.     self primOpen.
  69.     open := true.!
  70.  
  71. recordDisable
  72.     "Disable the collection of incoming events"
  73.     recording := false.!
  74.  
  75. recordEnable 
  76.     "Enable the collection of incoming events"
  77.     recording := true.!
  78.  
  79. start
  80.  
  81.     "Start everything playing & recording"
  82.     
  83.     self isOpen ifFalse:[^self].
  84.     
  85.     incoming := OrderedCollection new.
  86.     self primClearEvents.
  87.     starttime := self getTime.
  88.     self primStart.!
  89.  
  90. stop
  91.     "Stop everything playing. Fetch all events that
  92.     have been received since last start"
  93.     
  94.     self isOpen ifFalse:[^self].
  95.  
  96.     self primStop.
  97.     
  98.     self isRecording ifTrue:[
  99.         self receiveEvents.
  100.     ].! !
  101.  
  102. !MidiShareInterface methodsFor: 'accessing'!
  103.  
  104. getFreeSpace
  105.     self isInstalled ifFalse:[^0].
  106.     ^self primGetFreeSpace!
  107.  
  108. getTime
  109.     self isOpen ifFalse:[^0].
  110.     ^self primGetTime!
  111.  
  112. getTotalSpace
  113.     self isInstalled ifFalse:[^0].
  114.     ^self primGetTotalSpace!
  115.  
  116. getVersion
  117.  
  118.     "Answer a verbose string showing the current MidiShare version"
  119.     
  120.     |v|
  121.     
  122.     self isInstalled ifFalse:[^'MidiShare Controlpanel not installed.'].
  123.     ^'MidiShare ', 
  124.         ((v := self primVersion) // 100) printString,'.',
  125.         (v \\ 100) printString!
  126.  
  127. port
  128.     ^serial!
  129.  
  130. status
  131.     "Answer a verbose string showing the 
  132.     current status of the interface"
  133.     
  134.     self isInstalled ifFalse:[^'MidiShare not installed.'].
  135.     self isOpen ifFalse:[^'MidiShare stopped.'].
  136.     
  137.     ^self getVersion,
  138.         ' memory total:', self getTotalSpace printString, 
  139.         ', free:', self getFreeSpace printString! !
  140.  
  141. !MidiShareInterface methodsFor: 'testing'!
  142.  
  143. isInstalled
  144.     <primitive: 11001>
  145.     self primitiveFailed!
  146.  
  147. isOpen
  148.     ^open == true!
  149.  
  150. isRecording
  151.  
  152.     ^recording == true! !
  153.  
  154. !MidiShareInterface methodsFor: 'receiving - private'!
  155.  
  156. convertULong: aByteArray at: startIndex
  157.  
  158.     |  answer i |
  159.  
  160.     i := startIndex.
  161.     answer := 0.
  162.     
  163.     #(16777216 65536 256 1)  do: 
  164.         [ : n |
  165.                     answer := answer + ((aByteArray at: i) * n).
  166.                     i := i + 1
  167.                 ].
  168.                 
  169.     ^answer!
  170.  
  171. receiveConvert: aByteArray
  172.  
  173.     "Create an internal event-object from the received 
  174.      byte array (MidiShare event struct).
  175.      This method has to be changed to be appropriate for
  176.      the host musical system."
  177.     
  178.     | event |
  179.  
  180.     "*** this is only an example taken from my own system:
  181.     event := MidiEvent new.
  182.     event 
  183.         type: (aByteArray at: 9) 
  184.         clock: (MidiInterface clock: (self convertULong: aByteArray at: 5) - starttime tempo: tempo)
  185.         port: (aByteArray at: 11) 
  186.         channel: (aByteArray at: 12) 
  187.         data1: (aByteArray at: 13)  
  188.         data2: (aByteArray at: 14)
  189.         data3: (aByteArray at: 15).
  190.     "
  191.         
  192.     ^aByteArray!
  193.  
  194. receiveEvents
  195.  
  196.     "Fetch all received events pending"
  197.     
  198.     | e |
  199.     
  200.     [ (e := self primReceiveEvent) notNil ]
  201.                 whileTrue:[
  202.                     incoming add: (self receiveConvert: e) ].! !
  203.  
  204. !MidiShareInterface methodsFor: 'receiving'!
  205.  
  206. received
  207.     "Answer the collection of all received events"
  208.     ^incoming! !
  209.  
  210. !MidiShareInterface methodsFor: 'primitives'!
  211.  
  212. primClearEvents
  213.     <primitive: 11043>
  214.     self primitiveFailed!
  215.  
  216. primClose
  217.     <primitive: 11004>
  218.     self primitiveFailed!
  219.  
  220. primGetFreeSpace
  221.     <primitive: 11021>!
  222.  
  223. primGetTime
  224.     <primitive: 11005>!
  225.  
  226. primGetTotalSpace
  227.     <primitive: 11020>!
  228.  
  229. primOpen
  230.     <primitive: 11003>
  231.     self primitiveFailed!
  232.  
  233. primReceiveEvent
  234.     <primitive: 11042>
  235.     self primitiveFailed!
  236.  
  237. primSend: clock port: port chan: chan type: type data1: d1 data2: d2 data3: d3
  238.     "Send a MIDI event"
  239.     
  240.     <primitive: 11006>
  241.     self primitiveFailed!
  242.  
  243. primSetOffset: o tempo: t resolution: resolution delay: ms
  244.     "Define timing constants before sending events"
  245.     <primitive: 11022>
  246.     self primitiveFailed!
  247.  
  248. primStart
  249.     <primitive: 11031>
  250.     self primitiveFailed!
  251.  
  252. primStop
  253.     <primitive: 11030>
  254.     self primitiveFailed!
  255.  
  256. primVersion
  257.     <primitive: 11002>
  258.     self primitiveFailed! !
  259. "-- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- "!
  260.  
  261. MidiShareInterface class
  262.     instanceVariableNames: ''!
  263.  
  264.  
  265. !MidiShareInterface class methodsFor: 'constants'!
  266.  
  267. connectorModem
  268.     ^0!
  269.  
  270. connectorPrinter
  271.     ^1!
  272.  
  273. eventTypeCtrlChange
  274.     ^4!
  275.  
  276. eventTypeKeyOff
  277.     ^2!
  278.  
  279. eventTypeKeyOn
  280.     ^1!
  281.  
  282. eventTypeNote
  283.     ^0!
  284.  
  285. eventTypePitchwheel
  286.     ^7!
  287.  
  288. eventTypeProgChange
  289.     ^5!
  290.  
  291. midiManagerPort0
  292.     "Answer port which is redirected to MidiManager Out0"
  293.     ^9!
  294.  
  295. midiManagerPort1
  296.     "Answer port which is redirected to MidiManager Out1"
  297.     ^10! !
  298.  
  299. !MidiShareInterface class methodsFor: 'instance creation'!
  300.  
  301. new
  302.     ^super new initialize! !