BS2 ---> Propeller (Hardware) ================== LED Change from 470 ohm to 100 ohm PB Change from 220 ohm to 100 ohm I/O Pin (Protection) Change from 220 ohm to 100 ohm PBASIC ---> Spin ================ Remove the following from PBASIC programs (Comment out with ') ----------------------------------------- Stamp directives ' {$STAMP BS2} ' {$PABSIC 2.5} NEXT LOOP END DEBUG -----> PST (Parallax Serial Terminal - Object) ---------------------------------------------------- ' DEBUG BIN8 OUTH ---> pst.Bin(outa[8..15],8) ' DEBUG CLS ---> pst.Char(pst#CS) ' DEBUG CLS ---> pst.Str(string(pst#CS)) ' DEBUG CR ---> pst.NewLine ' DEBUG CRSRUP ---> pst.Str(string(pst#MU)) [cursor up] ' DEBUG DEC variable ---> pst.DEC(variable) ' DEBUG DEC2 counter ---> pst.Dec(counter) [2-digit decimal format] ' DEBUG DEC4 variable ---> pst.Dec(variable) [4-digit decimal format] ' DEBUG DEC4 duration ---> pst.Dec(duration) [4-digit decimal format] ' DEBUG DEC5 variable ---> pst.Dec(variable) [5-digit decimal format] ' DEBUG HOME ---> pst.Clear ' DEBUG HOME ---> pst.Char(pst#HM) ' DEBUG HOME ---> pst.Str(string(pst#HM)) ' DEBUG ? variable ---> pst.Dec(variable) ' DEBUG ? IN3 ---> pst.Bin(ina[3],1) ' DEBUG ? IN4 ---> pst.Bin(ina[4],1) ' DEBUG "Text" ---> pst.Str(string("Text")) ' DEBUG "Text", CR ---> pst.Str(string("Text", pst#NL)) ***** NOTE - ObjectName#ConstantName references a constant that is defined in that Object Parallax Serial Terminal (PST) ------------------------------ PUB Bin(value, digits) PUB Hex(value, digits) PUB Chars(bytechr, count) {{Send multiple copies of a single-byte character. Waits for room in transmit buffer if necessary. Parameters: bytechr - character (ASCII byte value) to send. count - number of bytechrs to send.}} PUB Dec(value) | i, x {{Send value as decimal characters. Parameter: value - byte, word, or long value to send as decimal characters.}} x := value == NEGX 'Check for max negative if value < 0 value := ||(value+x) 'If negative, make positive; adjust 'for max negative Char("-") 'and output sign i := 1_000_000_000 'Initialize divisor repeat 10 'Loop for 10 digits if value => i Char(value / i + "0" + x*(i == 1)) 'If non-zero digit, output digit; 'adjust for max negative value //= i 'and digit from value result~~ 'flag non-zero found elseif result or i == 1 Char("0") 'If zero digit (or only digit) output it i /= 10 'Update divisor DEBUG -----> PST (Parallax Serial Terminal - Object) ---------------------------------------------------- pst.Str(string("This is a test message!")) pst.NewLine pst.Str(String("Enter a decimal value: ")) value := pst.DecIn pst.Str(String(pst#NL, "You entered", pst#NL, "---------------")) pst.Str(String(pst#NL, "Decimal: ")) pst.Dec(value) pst.Str(String(pst#NL, "Hexadecimal: ")) pst.Hex(value, 8) pst.Str(String(pst#NL, "Binary: ")) pst.Bin(value, 32) repeat 2 pst.NewLine pst.Char(pst#CS) pst.Str(String("Pushbutton States", pst#NL)) pst.Str(String("-----------------", pst#NL)) repeat pst.PositionX(0) pst.Bin(ina[23..21],3) pst.Char(pst#CS) dira[4..9]~~ repeat pst.Str(String("Enter 6-bit binary pattern: ")) outa[4..9] := pst.BinIn repeat pst.Str(@MyString) pst.Dec(counter++) pst.Str(@MyOtherString) pst.Str(@BlankLine) waitcnt(clkfreq + cnt) DAT MyString byte "This is test message number: ", 0 MyOtherString byte ", ", pst#NL, "...and this is another line of text.",0 BlankLine byte pst#NL, pst#NL, 0 pst.Str(String(pst#NL, pst#NL, "Working on other tasks", pst#NL)) repeat 22 pst.Char (".") waitcnt(clkfreq/60 + cnt) ' Measurement has been ready for a while. Adjust ticks between phsa~ and dira[17]~. time := (phsa - 624) #> 0 ' Display Result pst.Str(String(pst#NL, "time = ")) pst.Dec(time) repeat ' Detect object. dira[1]~~ waitcnt(clkfreq/1000 + cnt) ' Wait 1 ms state := ina[0] ' Store I/R detector output dira[1]~ ' I/O pin -> input to stop signal ' Display detection (0, detected, 1 not detected) pst.Str(String(pst#HM, "State = ")) pst.Dec(state) pst.Str(String(pst#NL, "Object ")) if state == 1 pst.Str(String("not")) pst.str(String("detected.", pst#CE)) waitcnt(clkfreq/10 + cnt) DEBUGIN -----> PST (Parallax Serial Terminal - Object) ------------------------------------------------------ ' DEBUGIN character ---> character := pst.CharIn ' DEBUGIN DEC value ---> value := pst.DecIn ' DEBUGIN DEC duration ---> duration := pst.DecIn ' DEBUGIN DEC pulses ---> pulses := pst.DecIn DO -----> REPEAT ---------------- DO...LOOP ---> repeat DO.....UNTIL (IN7 = 0)...LOOP ---> repeat UNTIL ina[7] == 0 HIGH and LOW ------------ ' HIGH Pin ---> dira[Pin] := outa[Pin] := 1 ' LOW Pin ---> outa[Pin] := 0 PAUSE -----> WAITCNT(clkfreq + CNT) ----------------------------------- ' PAUSE 1 ---> waitcnt(clkfreq/1000 + cnt) [1 ms = 0.001 seconds = 1/1000] ' PAUSE 10 ---> waitcnt(clkfreq/100 + cnt) [10 ms = 0.01 seconds = 1/100] waitcnt(clkfreq/100*3 + cnt) [30 ms = 0.03 seconds = 3/100] waitcnt(clkfreq/100_000 + cnt) ' Wait for circuit to charge (10 us) ' PAUSE 50 ---> waitcnt(clkfreq/20 + cnt) [50 ms = 0.05 seconds = 1/20] ' PAUSE 100 ---> waitcnt(clkfreq/10 + cnt) [100 ms = 0.1 seconds = 1/10] ' PAUSE 125 ---> waitcnt(clkfreq/8 + cnt) [125 ms = 0.125 seconds = 1/8] ' PAUSE 200 ---> waitcnt(clkfreq/5 + cnt) [200 ms = 0.2 seconds = 1/5] ' PAUSE 250 ---> waitcnt(clkfreq/4 + cnt) [250 ms = 0.25 seconds = 1/4] ' PAUSE 300 ---> waitcnt(clkfreq/10*3 + cnt) [300 ms = 0.3 seconds = 3/10] ' PAUSE 400 ---> waitcnt(clkfreq/5*2 + cnt) [400 ms = 0.4 seconds = 2/5] ' PAUSE 500 ---> waitcnt(clkfreq/2 + cnt) [500 ms = 0.5 seconds = 1/2] ' PAUSE 1000 ---> waitcnt(clkfreq + cnt) [1000 ms = 1 second = 1] ' PAUSE 1500 ---> waitcnt(clkfreq/2*3 + cnt) [1500 ms = 1.5 seconds = 3/2] ' PAUSE 3000 ---> waitcnt(clkfreq*3 + cnt) [3000 ms = 3 seconds = 3] waitcnt(clkfreq*4 + cnt) [4000 ms = 4 seconds = 4] FOR...NEXT -----> REPEAT ------------------------ FOR counter = 1 TO number...NEXT ---> repeat number FOR variable = start TO finish...NEXT ---> repeat variable from start TO finish ' FOR variable = start TO finish STEP rate...NEXT ---> repeat variable from start TO finish STEP rate FOR counter = 5 TO 0 ---> repeat counter from 5 TO 0 ' Changed FOR to repeat, and = to from REPEAT ------ REPEAT REPEAT Variable FROM Start TO Finish REPEAT ((UNTIL/WHILE)) Condition(s) REPEAT Statements(s) ((UNTIL/WHILE)) Condition(s) IF...THEN -----> IF...ELSE -------------------------- ' IF (IN3 = 1) THEN ---> if INa[3] == 1 IF-THEN...ELSE...ENDIF ---> IF...ELSE ' ELSEIF (IN4 = 1) THEN ---> ELSEIF INa[4] == 1 ' IF-THEN...ELSEIF...ELSE...ENDIF ---> IF...ELLSEIF...ELSE Assignment Statements --------------------- timeCounter := timeCounter + 1 ' Changed from = to := ' OUTH = %00000000 ---> outa[8..15] := %00000000 ' DIRH = %11111111 ---> dira[8..15] := %11111111 ' LOOKUP index, [7, 85, 19, 167, 28], value ---> value := LOOKUP(index: 7, 85, 19, 167, 28) ' LOOKUP is for index from 1 to N ' LOOKUPZ is for an index from 0 to N-1 ' LOOKDOWN value, [7, 85, 19, 167, 28], index ---> index := LOOKDOWN(value: 7, 85, 19, 167, 28) ' LOOKDOWN is for index from 1 to N ' LOOKDOWNZ is for an index from 0 to N-1 ' READ Notes + index, noteLetter ---> noteLetter := byte[@Notes][index] SELECT...CASE -----> CASE ------------------------- ' SELECT variable...ENDSELECT ---> CASE variable ' CASE values ---> values: ' CASE start to finish ---> start..finish: ' CASE ELSE ---> OTHER: Subroutine -----> Method (Spin Subroutine/Function) ------------------------ ' GOSUB Subroutine ---> Subroutine ' EXIT ---> quit ' Subroutine ---> PRI Subroutine ***** NOTE - PRI declares a Private Method which is only available to the Spin program it's in ' DCD noteOctave ---> 1 << noteOctave [DCD: N ---> 2^N] (each Left Shift is the same as multiplying by 2) Add the following ----------------- ----------------- CON ' Added _xinfreq = 5_000_000 ' external oscillator frequency (5.00 MHz) [Added] _clkmode = xtal1 + pll16x ' multiply external oscillator frequency by 16 (5 x 16 = 80 MHz) [Added] OBJ ' Added pst : "Parallax Serial Terminal" ' Added for DEBUG PUB Init ' (Added) ' Start Parallax Serial Terminal; waits 1 s for you to click Enable button (Added) pst.Start(115_200) ' Added for DEBUG main ' Call the Main method [Method Call] (Added) PUB Main | time ' Method declaration (Added) PUB LedOnOff ' Pubic Method declaration (Added) PUB LedOnOffTenTimes | counter ' Public Method declaration (Added) ' Counter is a variable ' Changed from counter VAR Word to | counter in Method Declaration PUB ServoCenter | tc, tHa, t, tInc ' Public Method declaration (Added) PUB PolledRcTimer | tc, tHa, t, tInc, counter, timeCounter ' Method declaration (Added) ' Changed from counter VAR Word to | counter in Method Declaration ' Changed timeCounter VAR Nib to |timeCounter in Method Declaration ***** NOTE - Public Methods are available to any Spin program dira[14] := 1 ' Set P14 to output (Added) tInc := clkfreq/1_000_000 ' Determine time increment for pulse and cycle times. (us, 1 ms = 1000 us) [Added] tC := 20_000 * tInc ' Use time increment to set the variable that holds the cycle time. (20 ms = 20,000 us) tHa := 1_500 * tInc ' Use time increment to set the high time for the A counter module. (1.5 ms = 1500 ms) t := cnt ' Records the cnt register at an initial time. (Mark counter time) repeat ' Manage the pulse train. (Repeat PWM signal) t += tC ' Calculate next cycle repeat (Adds tC, the cycle time of ticks, to t, the target time for the next cycle to start.) waitcnt(t) ' Wait for next cycle repeat counter from 1 to 15 ' Manage the pulse train. (Repeat PWM signal for approximately 3 seconds) ' Changed from FOR to repeat and = to from repeat counter from 1 to 150 ' Manage the pulse train. (45 degrees - Repeat PWM signal for approximately 3 seconds) ' Changed from FOR to repeat and = to from duration := duration #> 700 <# 2_300 ' Changed from = to :=, MIN to #>, 350 to 700, MAX to <#, and 1150 to 2_300 repeat pulses ' Manage the pulse train. (Repeat PWM signal) ' Changed from FOR to repeat, and removed counter = 1 TO repeat counter from 1000 TO 2000 STEP 16 ' Manage the pulse train. (Repeat PWM signal - us) ' Changed from FOR to repeat, = to from, 500 to 1000, 1000 to 2000, and 8 to 16 repeat ' Changed from DO to repeat (Endless loop prevents program from ending) duration := duration #> 700 <# 2_300 ' Changed from = to :=, MIN to #>, 350 to 700, MAX to <#, and 1150 to 2_300 PUB Init ' (Added) ' Start Parallax Serial Terminal; waits 1 s for you to click Enable button (Added) pst.Start(115_200) ' Added main ' Call the Main method [Method Call] (Added) PUB Main | time ' Method declaration (Added) ' Changed from time VAR Word to, | time in Method Declaration waitcnt(clkfreq + cnt) ' Changed from PAUSE 1000 to waitcnt(clkfreq + cnt) [1 second] repeat ' Changed from DO to repeat (Endless loop prevents program from ending) dira[7] := outa[7] := 1 ' Starts charging the capacitor (Set pin to output-high) ' Changed from HIGH 7 to dira[7] := outa[7] := 1 waitcnt(clkfreq/10 + cnt) ' Make the Terminal display update at about 10 times per second ' Changed from PAUSE 100 to waitcnt(clkfreq/10 + cnt) [1/10 second] waitcnt(clkfreq/100_000 + cnt) ' Wait for circuit to charge (10 us) [Added] dira[17]~ ' Let the capacitor discharge itself though the resistor. (Pin to input stops charging circuit) [Added] time := (phsa - 624) #> 0 ' Subtract the number of clock ticks between phsa~ and dira[7]~. (Added) pst.Dec(time) ' Changed from DEBUG DEC5 to pst.Dec( ) [5-digit decimal format] ''ControlledServoWithPot.bs2 - Chapter 5, Activity #4 PUB Init ' Added ' Start Parallax Serial Terminal; waits 1 s for you to click Enable button (Added) pst.Start(115_200) ' (Added) dira[14] := 1 ' Set P14 to output (Added) main ' Call the Main method [Method Call] (Added) PUB Main | tc, tHa, t, tInc, time ' Tracks how long it takes the capacitor to discharge through R (us?) [Added] ' Changed from time VAR Word, | time in Method Declaration tInc := clkfreq/1_000_000 ' Determine time increment for pulse and cycle times. (us, 1 ms = 1000 us) [Added] tC := 20_000 * tInc ' Use time increment to set the variable that holds the cycle time. (20 ms = 20,000 us) waitcnt(clkfreq + cnt) ' Changed from PAUSE 1000 to waitcnt(clkfreq + cnt) [1 second] pst.Str("Program Running!")) ' Changed from DEBUG to pst.Str(string( )) repeat ' Changed from DO to repeat (Endless loop prevents program from ending) dira[7] := outa[7] := 1 ' Starts charging the capacitor (Set pin to output-high) ' Changed from HIGH 7, to dira[7] := outa[7] := 1 waitcnt(clkfreq/100 + cnt) ' Make the Terminal display update at about 100 times per second ' Changed from PAUSE 10 to waitcnt(clkfreq/100 + cnt) [1/100 second] waitcnt(clkfreq/100_000 + cnt) ' Wait for circuit to charge (10 us) [Added] dira[7]~ ' Let the capacitor discharge itself though the resistor. (Pin to input stops charging circuit) [Added] time := (phsa - 624) #> 0 ' Subtract the number of clock ticks between phsa~ and dira[7]~. (Added) time = time */ 185 ' Scale by 0.724 (X 256 for */). time = time + 500 ' Offset by 500. ' Removed LOOP CON ' Constant Declarations (Added) ' I/O Pin Definitions rcPin = 7 ' Changed from CON to = servoPin = 14 ' Changed from PIN to = ' Constants scaleFactor = 185 ' Changed from CON to = offset = 500 ' Changed from CON to = delay = 10 ' Changed from CON to = (ms) ''Chapter5Project1.spin - Chapter 5, Project #1 'Add a bicolor LED circuit to Activity #4. 'Modify the example program so that the bicolor LED is red when the servo is rotating counterclockwise, ' green when the servo is rotating clockwise, and off when the servo is holding its position. CON ' Added ' System clock -> 80 MHz _clkmode = xtal1 + pll16x ' Added _xinfreq = 5_000_000 ' Added ' I/O Pin Definitions rcPin = 7 ' Changed from PIN to = servoPin = 14 ' Changed from PIN to = ' Constant Declarations scaleFactor = 185 ' Changed from CON to = offset = 500 ' Changed from CON to = delay = 10 ' Changed from CON to = (10 ms = 1/100 s) OBJ ' Added pst : "Parallax Serial Terminal" ' Use with Parallax Serial Terminal to display values (Added) PUB Init ' Initialization (Added) ' Start Parallax Serial Terminal; waits 1 s for you to click Enable button (Added) pst.Start(115_200) ' (Added) dira[14] := 1 ' Set P14 to output (Added) main ' Call the Main method [Method Call] (Added) PUB Main | tc, tHa, t, tInc, time, oldTime ' Tracks how long it takes the capacitor to discharge through R (us?) [Added] ' Changed from time VAR Word, | time in Method Declaration tInc := clkfreq/1_000_000 ' Determine time increment for pulse and cycle times. (us, 1 ms = 1000 us) [Added] tC := 20_000 * tInc ' Use time increment to set the variable that holds the cycle time. (20 ms = 20,000 us) waitcnt(clkfreq + cnt) ' Changed from PAUSE 1000 to waitcnt(clkfreq + cnt) [1 second] repeat ' Changed from DO to repeat (Endless loop prevents program from ending) dira[7] := outa[7] := 1 ' Starts charging the capacitor (Set pin to output-high) ' Changed from HIGH 7, to dira[7] := outa[7] := 1 waitcnt(clkfreq/100 + cnt) ' Make the Terminal display update at about 100 times per second ' Changed from PAUSE 10 to waitcnt(clkfreq/100 + cnt) [1/100 second] waitcnt(clkfreq/100_000 + cnt) ' Wait for circuit to charge (10 us) [Added] dira[7]~ ' Let the capacitor discharge itself though the resistor. (Pin to input stops charging circuit) [Added] time := (phsa - 624) #> 0 ' Subtract the number of clock ticks between phsa~ and dira[7]~. (Added) 'time = time */ 185 ' Scale by 0.724 (X 256 for */). 'time = time + 500 ' Offset by 500. ' Removed LOOP { us - a millionth of a second. 1 ms = 1000 us tC := clkfreq ' Set up cycle and high times ' Sets the variable that holds the cycle time to the number of clock ticks in one second. t := cnt ' Mark counter time ' Records the cnt register at an initial time. ' A variable or constant can be used to store a time increment for pulse and cycle times. tInc := clkfreq/1_000_000 ' Determine time increment (us) } { '' Repeatedly takes and displays P17 RC decay measurements. repeat dira[17] := outa[17] := 1 ' Set pin to output-high waitcnt(clkfreq/100_000 + cnt) ' Wait for circuit to charge (10 us) dira[17]~ ' Pin to input stops charging circuit pst.Str(String(pst#NL, pst#NL, "Working on other tasks", pst#NL)) repeat 22 pst.Char (".") waitcnt(clkfreq/60 + cnt) time := (phsa - 624) #> 0 ' Display Result pst.Str(String(pst#NL, "time = ")) pst.Dec(time) waitcnt(clkfreq/2 + cnt) clkfreq/100_000 = 10 us clkfreq/10_000 = 100 us 1 s = 80,000,000 clock ticks (12.5 ns each, 0.0000000125) phsa := clkfreq/1_000_000 (1 us PWM pulse) phsa~ ' Clear counts 624 clock ticks x 12.5 ns/clock tick = 7800 ns = 7.8 us = 0.0000078 s 1 ms = 0.001 s = 1000 us = 1,000,000 ns 1 us = 0.000001 s = 1000 ns i ns = 0.000000001 s } { ''SquareWaveTest.spin ''Send 2093 Hz square wave to P27 for 1 s with counter module. CON _clkmode = xtal1 + pll16x ' Set up clkfreq = 80 MHz _xinfreq = 5_000_000 PUB TestFrequency dira[27]~~ ' Set P27 to output waitcnt(clkfreq + cnt) ' Wait for tone to play for 1 s ''TwoTones.spin ''Play individual notes with each piezospeaker, then play notes with both at the ''same time CON _clkmode = xtal1 + pll16x ' System clock -> 80 MHz _xinfreq = 5_000_000 OBJ SqrWave : "SquareWave" PUB PlayTones | index, pin, duration 'Initialize counter modules repeat index from 0 to 1 pin := byte[@pins][index] spr[8 + index] := (%00100 << 26) + pin dira[pin] 'Look up tones and durations in DAT section and play them. repeat index from 0 to 4 frqa := SqrWave.NcoFrqReg(word([@Anotes][index]) frqb := SqrWave.NcoFrqReg(word([@Bnotes][index]) duration := clkfreq/(byte[@durations][index]) waitcnt(duration + cnt) DAT pins byte 27, 3 'index 0 1 2 3 4 durations byte 1, 2, 1, 2, 1 anotes word 1047, 0, 0, 0, 1047 bnotes word 0, 0, 1319, 0, 1319 ' C6 D6 E6 F6 G6 A6 B6 C7 ' notes long 56_184, 63_066, 70_786, 74_995, 84_181, 94_489, 105_629, 112_528 } WAM - Chapter 2 --------------- pst.Str(string("The LED connected to P14 is blinking!")) ' Changed from DEBUG to pst.Str(string( )) ' Changed from DO to repeat ' Changed from HIGH 14 to outa[14] := 1 ' Changed from PAUSE 500 to waitcnt(clkfreq/2 + cnt) [1/2 second] ' Changed from LOW 14 to outa[14] := 0 ***** Activity #3 (LedOnOffTenTimes) PUB LedOnOffTenTimes | counter ' Method declaration (Added) repeat counter from 1 to 10 ' Repeat 10 times ' Changed from FOR to repeat and = to from pst.Dec(counter) ' Changed from DEBUG ? to pst.Dec( ) pst.Str(string("All done!")) ' Changed from DEBUG to pst.Str(string( )) pst.Str(string("Program Running!")) ' Changed from DEBUG to pst.Str(string( )) ' Changed from HIGH 15 to outa[15] := 1 ' Changed from LOW 15 to outa[15] := 0 ' Changed from PAUSE 1000 to waitcnt(clkfreq/2 + cnt) [1 second] pst.Str(string("Program Running!", pst#NL)) ' Changed from DEBUG to pst.Str(string( )) and CR to pst#NL pst.Str(string("Green...")) ' Changed from DEBUG to pst.Str(string( )) ' Changed from PAUSE 1500 to waitcnt(clkfreq/2*3 + cnt) [1-1/2 seconds] pst.Str(string("Red...")) ' Changed from DEBUG to pst.Str(string( )) pst.Str(string("Off...", pst#NL)) ' Changed from DEBUG to pst.Str(string( )) and CR to pst#NL