; CPU configuration processor 16f84 include __config _HS_OSC & _WDT_OFF & _PWRTE_ON ; memory map ; ---------- ; 20 time <- start ; 21 length ; 22 curmap ; ... ; 30 map 0 size <- map sizes block start ; 31 map 1 size ; 32 map 2 size ; ... ; 40 <- event maps ; } map 0 events ; 50 ; } map 1 events ; 60 ; } map 2 events ; 70 ... ; ... #define BUTTON_PIN 0 #define MAP_SIZES_ADDR 30 #define MAP_ADDR 40 time equ H'20' length equ H'21' curmap equ H'22' temp equ H'23' ; state #define STATE_DEBOUNCE 0 state equ H'23' ; Program start: movlw B'00000000' tris PORTA ; init port A as output movlw B'11111111' tris PORTB ; init port B as input bsf PORTA, 0x02 ; init midi out pin state ; init clrf time clrf curmap clrf state movlw D'10' movwf length ; init map sizes ; todo - only one map for now clrf MAP_SIZES_LOC mainloop: incf time ; increment time movf length, w ; load the total length subwf time,w ; time-length skpnc ; skip on no carry clrf time ; reset clock to start of loop call checkinput ; check button ; set event if necc ; check maps goto mainloop ;---------------------------------------------------------------- ; read the input bit checkinput: btfss PORTB,BUTTON_PIN ; skip if button down clrf state,STATE_DEBOUNCE ; clear the debounce state (button up) btfsc state,STATE_DEBOUNCE ; skip if debounce is clear return ; exit if pressed last time and still down btfss PORTB,BUTTON_PIN ; skip if set return ; exit if not pressed bsf state,STATE_DEBOUNCE ; set debounce state (we're pressed) ; todo - only one map for now incf MAP_SIZES_ADDR ; inc map size movfw MAP_SIZES_ADDR ; load contents of the first size addwf MAP_LOC,w ; add size to map top to get dest addr movwf temp ; put addr in temp movf time, return ;---------------------------------------------------------------- ; send a midi event if the time is right, checking all maps sendevents: return ;---------------------------------------------------------------- ; send a midi event now! send: movlw 0x90 ; note on, channel 1 movwf xmit call sendmidi movlw 0x3C ; middle C movwf xmit call sendmidi movlw 0x7F ; velocity 127 movwf xmit call sendmidi ; movlw 0x80 ; note off, channel 1 ; movwf xmit ; call sendmidi ; movlw 0x3C ; middle C ; movwf xmit ; call sendmidi ; movlw 0x7F ; velocity 127 ; movwf xmit ; call sendmidi return ;---------------------------------------------------------------------- ; secdelay delays for one second ( 2500000 instructions ) ; kloop = (2 + 254 * 3 + 1 * 2) = 766 ; jloop = 2 + kloop * 255 + (3 * 254 + 1 * 2) = 196096 ; iloop = 2 + jloop * 13 + (3*254 + 1*2) = 2550014 = 1.02 seconds ; x = secdelay: movlw D'13' movwf i iloop: movlw D'255' movwf j jloop: movlw D'255' movwf k kloop: decfsz k,f goto kloop decfsz j,f goto jloop decfsz i,f goto iloop return include "midi.inc" end