Start with the "What's a Microcontroller?" tutorial and the "BASIC Stamp Syntax and Reference Manual", both downloadable from Parallax's website. Also look at the "StampWorks Manual" which I think has an example of the use of a 7 segment display.
Another good source for ideas and sample code is the Nuts and Volts Columns series on Parallax's website
For all of these, start with the "Resources" tab on the main Parallax webpage, then follow the links for Downloads, then BASIC Stamp Documentation or Stamps in Class Downloads.
I can get you started, although there are probably lots of ways to do this. The simplest I can think of:
The display is simply seven LED's driven by a voltage and ground. There should be seven lines off the display (maybe eight for a period/decimal point). Pull up the data sheet for the device to find out what goes where OR you can just hook it up and see. Most I've seen are common-cathode or all LEDs on the display share the same ground.
Make sure you use a current limiting resistor, something in the range of 300-500 ohm should do nicely. Run each of the seven LED pins on the display through a resistor to seven output pins on the Stamp. Hook up your ground.
Then you'll need to make a data table something like this:
You'll need a counter variable (0,1,2,3,4,5,6,7,8,9) and a pointer to point to the start of the data table. The reference the values in the data table with something like:
datatbl= label for data
counter=3 'number to display
pointer=datatbl+(counter*8)
then read the pointer location, send that value to the corresponding bit, increment and do it seven times
Note that there is a 80ma (I think) limit on how mush the stamp can drive off one bus, so use Ohm's law to figure total current with all segments ON to make sure you don't go over that limit.
Oh, you'll need an input for the button as well.
The method I listed is sloppy, but who cares. Have fun!
Thank you for your replys I have made some progress but still need a little more guidance. I have hooked up a 5" 7 segment led display to a multiplex driver and using the output from the bs2 to display the digits. What I am trying to do is make a game score keeper so when the MC pushes a button it will add 1 number to the contests score.
I have written code to first test the display and on the first button press it displays 0. This is where it gets a little sticky for me. Im stuck. Any help with code would be appreciated. Here is what I have so far.
' What's a Microcontroller - Scorekeeper.bs2
' test each segment then keep score
You need to be more specific. What part are you stuck on? You first need to write a program that reads the pushbutton...Make it send something back through DEBUG. Then modify the program to count the button presses and send that number. Then write a program to display numbers on your LED. Then combine the two programs.
clear the high I/O byte
set the high I/O byte to all outputs
Display 0 through 9 with 500ms between each number for a display test
wait 300ms
display the number 2 and immediately change the high byte of I/O to inputs (which I think will clear the pin states so you probably never see the number 2)
Print "Your score is 0" to the console
Then you read from Pin3..... which I guess is your pushbutton? I have no idea what the High14 through High 8 is for. I'm thinking that's what's not working like you planned?
I would start the program by setting your high byte to outputs: DIRH = %11111111
Set bit 3 to input: INPUT 3
clear your bits: OUTH = %00000000
Then leave your I/O states alone. Keep pin3 as an input and the high byte as output.
Your display test looks ok as a test.
Next you need to set your numbers up in a data table just like I mentioned previously. Instead of hard coding your display test, make your display test a confirmation of your data table.
Now with the data table, every time you press the button, it increments the data pointer by 9 to point to the next number.
I can try to code the data table for you, but it'll take me some time. Lemme know.
Thanks Spiral_72 I will give that a try. Im having problems understanding how to build the data table you suggested. I will dig into the manual some more. I have a little experience with coding because I have been working with a program called trainbrain to computerize my railroad layout but it seams a littlle easier to use. I appriciate all the advise you have its sounds like you have been doing this for sometime. I just bought my first stamp last week so I need to just keep at it and dont expect to much so soon.
ok i think im getting it but im still stuck I am able to getthe first digit but nothing after that what am i missing. Have a look
' What's a Microcontroller - Scorekeeper.bs2
' test each segment then keep score
' {$STAMP BS2}
' {$PBASIC 2.5}
'
[noparse][[/noparse] Program Description ]
'
' When button is pushed displays decimal digits (0 - 9) on a 7-Segment display connected to
' P8-P15.
'
[noparse][[/noparse] I/O Definitions ]
Segs VAR OUTH' Segments on P8 - P15
SegsDirs VAR DIRH ' DIRS for segmen
OUTH = %00000000
DIRH = %11111111
ScoreBtn PIN 3 ' button for adding score
'
[noparse][[/noparse] Variables ]
idx VAR Nib ' counter variable
nexVal VAR Word ' next number
swData VAR Byte ' workspace for BUTTON
newVal VAR Nib ' new value
counter VAR Byte
'
[noparse][[/noparse] EEPROM Data ]
' .GFEDCBA
'
Digit0 DATA %11101111
Digit1 DATA %10001100
Digit2 DATA %11010011
Digit3 DATA %11010110
Digit4 DATA %10110100
Digit5 DATA %01110110
Digit6 DATA %01110111
Digit7 DATA %11000100
Digit8 DATA %11110111
Digit9 DATA %11110110
' .GFEDCBA
'
[noparse][[/noparse] Initialization ]
'
[noparse][[/noparse] Program Code ]
Main:
DO
GOSUB count1
PAUSE 5
' check for button press
BUTTON scoreBtn, 0, 255, 5, swData, 1, Show_score
LOOP
Show_score:
READ (Digit0 + newVal), Segs ' transfer number to segments
GOTO main '
'
[noparse][[/noparse] Subroutines ]
count1:
IF (scorebtn = 1) THEN
nexVal = (counter + 1) ' counter value
newVal = (counter + 1) ' get new value
ENDIF
IF (scorebtn = 0) THEN ' wait fo next button push
GOTO main
READ Segs, ' output to segments
DIRH
ENDIF
RETURN
Alright guy. I'm kinda sticking my neck out here [noparse]:)[/noparse] I wrote this over break with no way to test it. Use at your own risk and let the thrashing on my code begin!
Now how many mistakes did I make???? It's SUPPOSED to work
Lemme know how it works!
' {$STAMP BS2}
' {$PBASIC 2.5}
Digit0 DATA %11101111
Digit1 DATA %10001100
Digit2 DATA %11010011
Digit3 DATA %11010110
Digit4 DATA %10110100
Digit5 DATA %01110110
Digit6 DATA %01110111
Digit7 DATA %11000100
Digit8 DATA %11110111
Digit9 DATA %11110110
DATaddr VAR Word ' Word variable for our pointer
counter VAR byte ' Keep track of current digit
Dchar VAR byte ' Variable to keep digit in
INPUT 3 ' Make pin 3 an input for the button
DIRH ' Make pins 8-15 outputs for the display
' -----[noparse][[/noparse] Program Code ]----------------------------------------------------
counter=0 ' initialize counter
DATaddr = Digit0 ' Make pointer = start of data table
Main: ' Main program loop
READ DATaddr + counter, Dchar ' Read the character (byte size by default) from our marker (Digit0) + counter
OUTH = Dchar ' Send the value to port
DEBUG DEC Dchar ' Send value to console
waitkey:
IF IN3=0 THEN waitkey ' Has the button been pressed? No? try it again
PAUSE 250 ' For a little button debounce, wait 250ms
counter = counter + 1 ' increment counter
if counter > 9 then counter = 0 ' limit the counter and roll it back over to zero
goto main
Post Edited (Spiral_72) : 2/10/2010 3:22:14 PM GMT
OK Spiral he is the $64,000 question can I do this to 3 more 7 segment displays using the same BS2 or do I need a seperate controller for each button to keep score for a total of 4 contestants.
Yea, you should be able to address MANY displays with one stamp. You'd use the same eight outputs for all displays but you'd need one to several more lines for switching (addressing). This is however outside of my experience. I do remember using an IC years ago to do this very thing, but I don't remember what the part number was.
It seems there would be a display driver you can send BCD. That would give you three displays off twelve pins. You'd have to research it, I don't actually know if something like that exists, but it would make sense.
You're not the first person to do this, and every microcontroller doesn't have eight output lines for every display digit. That'd add up pretty quick.
Take A look at Experiment # 10 in the StampWorks Manuel, Pg.67. Its on the Parallax store page, Theres a free download but I recommend the hard copy.
The Experiment shows how to Multiplex four 7seg.led displays using 11 I/O pins way better then I could on this post reply.Its simple wiring and a really short code.
Multiplexing is the way to go when using multiple displays.
If Your running low on I/O pins, A digital shift register or two will help free up some I/O pins.(for Buttons) Take a look at Experiments #23,24,25 Pgs.130-145 in StampWorks.
The shift registers are for Your buttons and not the led displays when Multiplexing.( Theres to many timing issues for a beginner to deal with.)
I think You will find these shift registers very useful in Your model R.R. projects.
▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
The Truth is out there············___$WMc%___···························· BoogerWoods, FL. USA
bs2-man said...
what is the official, working code?
The official Working code is by spiral
Spiral_72 said...
' {$STAMP BS2}
' {$PBASIC 2.5}
Digit0 DATA %11101111
Digit1 DATA %10001100
Digit2 DATA %11010011
Digit3 DATA %11010110
Digit4 DATA %10110100
Digit5 DATA %01110110
Digit6 DATA %01110111
Digit7 DATA %11000100
Digit8 DATA %11110111
Digit9 DATA %11110110
DATaddr VAR Word ' Word variable for our pointer
counter VAR byte ' Keep track of current digit
Dchar VAR byte ' Variable to keep digit in
INPUT 3 ' Make pin 3 an input for the button
DIRH ' Make pins 8-15 outputs for the display
'
[noparse][[/noparse] Program Code ]
counter=0 ' initialize counter
DATaddr = Digit0 ' Make pointer = start of data table
Main: ' Main program loop
READ DATaddr + counter, Dchar ' Read the character (byte size by default) from our marker (Digit0) + counter
OUTH = Dchar ' Send the value to port
DEBUG DEC Dchar ' Send value to console
waitkey:
IF IN3=0 THEN waitkey ' Has the button been pressed? No? try it again
PAUSE 250 ' For a little button debounce, wait 250ms
counter = counter + 1 ' increment counter
if counter > 9 then counter = 0 ' limit the counter and roll it back over to zero
ShaneP said...
Spiral YOU ARE DA MAN... works great just now need a -1 button.
Hey man, you can handle that
A hint: You'll need another button on another input line...... a line of code to handle it decrementing the counter.... and "maybe" one more to make sure the counter doesn't go below zero.
I've not worked with negative numbers on a BS, so I'm sure it's an unsigned number...... You'll have fun with that, Har! Har!...... if you do, remember DEBUG is your friend.... DEBUG the counter.
▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
"puff"...... Smile, there went another one.
Thanks Spiral_72 for the counter code. Can you help me sort something out? When I push the button, it counts up ok, but if the button is held, it coutinues to count. I would like it to stop counting until the button is released and pushed again. Thanks...
You have to have another loop that waits for the button to be released (not pushed) like this:
waitNoKey:
IF IN3=1 THEN waitNoKey
PAUSE 250 ' For a little button debounce, wait 250ms
waitkey:
IF IN3=0 THEN waitkey ' Has the button been pressed? No? try it again
PAUSE 250 ' For a little button debounce, wait 250ms
If you've got a bouncy button, I'd suggest using the BUTTON statement instead of the IF / THEN statements. See the Stamp Manual or help files for details and examples.
Comments
Another good source for ideas and sample code is the Nuts and Volts Columns series on Parallax's website
For all of these, start with the "Resources" tab on the main Parallax webpage, then follow the links for Downloads, then BASIC Stamp Documentation or Stamps in Class Downloads.
The display is simply seven LED's driven by a voltage and ground. There should be seven lines off the display (maybe eight for a period/decimal point). Pull up the data sheet for the device to find out what goes where OR you can just hook it up and see. Most I've seen are common-cathode or all LEDs on the display share the same ground.
Make sure you use a current limiting resistor, something in the range of 300-500 ohm should do nicely. Run each of the seven LED pins on the display through a resistor to seven output pins on the Stamp. Hook up your ground.
Then you'll need to make a data table something like this:
0 = 1,1,1,1,1,1,0
1 = 0,1,0,0,0,0,0
2 = 1,1,0,1,1,0,1
3 = xxxxx........
4 = .....
You'll need a counter variable (0,1,2,3,4,5,6,7,8,9) and a pointer to point to the start of the data table. The reference the values in the data table with something like:
datatbl= label for data
counter=3 'number to display
pointer=datatbl+(counter*8)
then read the pointer location, send that value to the corresponding bit, increment and do it seven times
Note that there is a 80ma (I think) limit on how mush the stamp can drive off one bus, so use Ohm's law to figure total current with all segments ON to make sure you don't go over that limit.
Oh, you'll need an input for the button as well.
The method I listed is sloppy, but who cares. Have fun!
a.k.a start simple
I have written code to first test the display and on the first button press it displays 0. This is where it gets a little sticky for me. Im stuck. Any help with code would be appreciated. Here is what I have so far.
' What's a Microcontroller - Scorekeeper.bs2
' test each segment then keep score
' {$STAMP BS2}
' {$PBASIC 2.5}
OUTH = %00000000
DIRH = %11111111
'······· BAFG.CDE
OUTH = %11100111···· 'Number 0
PAUSE 500
OUTH = %10000100···· 'Number 1
PAUSE 500
OUTH = %11010011···· 'Number 2
PAUSE 500
OUTH = %11010110···· 'Number 3
PAUSE 500
OUTH = %10110100···· 'Number 4
PAUSE 500
OUTH = %01110110···· 'Number 5
PAUSE 500
OUTH = %01110111···· 'Number 6
PAUSE 500
OUTH = %11000100···· 'Number 7
PAUSE 500
OUTH = %11110111···· 'Number 8
PAUSE 500
OUTH = %11110110···· 'Number 9
PAUSE 300
OUTH = %11010110
DIRH = %00000000
DEBUG " Your score is 0"
DO
IF (IN3 = 1) THEN
HIGH 14
HIGH 15
HIGH 13
HIGH 11
HIGH 10
HIGH 9
HIGH 8
ELSE
· ENDIF
· LOOP
Thanks again for your help
Stickystamp
clear the high I/O byte
set the high I/O byte to all outputs
Display 0 through 9 with 500ms between each number for a display test
wait 300ms
display the number 2 and immediately change the high byte of I/O to inputs (which I think will clear the pin states so you probably never see the number 2)
Print "Your score is 0" to the console
Then you read from Pin3..... which I guess is your pushbutton? I have no idea what the High14 through High 8 is for. I'm thinking that's what's not working like you planned?
I would start the program by setting your high byte to outputs: DIRH = %11111111
Set bit 3 to input: INPUT 3
clear your bits: OUTH = %00000000
Then leave your I/O states alone. Keep pin3 as an input and the high byte as output.
Your display test looks ok as a test.
Next you need to set your numbers up in a data table just like I mentioned previously. Instead of hard coding your display test, make your display test a confirmation of your data table.
Now with the data table, every time you press the button, it increments the data pointer by 9 to point to the next number.
I can try to code the data table for you, but it'll take me some time. Lemme know.
' What's a Microcontroller - Scorekeeper.bs2
' test each segment then keep score
' {$STAMP BS2}
' {$PBASIC 2.5}
'
[noparse][[/noparse] Program Description ]
'
' When button is pushed displays decimal digits (0 - 9) on a 7-Segment display connected to
' P8-P15.
'
[noparse][[/noparse] I/O Definitions ]
Segs VAR OUTH' Segments on P8 - P15
SegsDirs VAR DIRH ' DIRS for segmen
OUTH = %00000000
DIRH = %11111111
ScoreBtn PIN 3 ' button for adding score
'
[noparse][[/noparse] Variables ]
idx VAR Nib ' counter variable
nexVal VAR Word ' next number
swData VAR Byte ' workspace for BUTTON
newVal VAR Nib ' new value
counter VAR Byte
'
[noparse][[/noparse] EEPROM Data ]
' .GFEDCBA
'
Digit0 DATA %11101111
Digit1 DATA %10001100
Digit2 DATA %11010011
Digit3 DATA %11010110
Digit4 DATA %10110100
Digit5 DATA %01110110
Digit6 DATA %01110111
Digit7 DATA %11000100
Digit8 DATA %11110111
Digit9 DATA %11110110
' .GFEDCBA
'
[noparse][[/noparse] Initialization ]
'
[noparse][[/noparse] Program Code ]
Main:
DO
GOSUB count1
PAUSE 5
' check for button press
BUTTON scoreBtn, 0, 255, 5, swData, 1, Show_score
LOOP
Show_score:
READ (Digit0 + newVal), Segs ' transfer number to segments
GOTO main '
'
[noparse][[/noparse] Subroutines ]
count1:
IF (scorebtn = 1) THEN
nexVal = (counter + 1) ' counter value
newVal = (counter + 1) ' get new value
ENDIF
IF (scorebtn = 0) THEN ' wait fo next button push
GOTO main
READ Segs, ' output to segments
DIRH
ENDIF
RETURN
Now how many mistakes did I make???? It's SUPPOSED to work
Lemme know how it works!
Post Edited (Spiral_72) : 2/10/2010 3:22:14 PM GMT
YOU THE MAN!
Thank you very much Let me know what I owe you
Glad I could be of help, and I can't believe it worked without troubleshooting! wow.
Have fun guy!
Post Edited (Spiral_72) : 2/11/2010 1:39:27 PM GMT
Thanks agian for all you help
Saluete
It seems there would be a display driver you can send BCD. That would give you three displays off twelve pins. You'd have to research it, I don't actually know if something like that exists, but it would make sense.
You're not the first person to do this, and every microcontroller doesn't have eight output lines for every display digit. That'd add up pretty quick.
http://www.maxim-ic.com/app-notes/index.mvp/id/2791
Sweet! BCD to 7-segment display!! Three of those and you'd be in business.
http://www.allaboutcircuits.com/vol_6/chpt_7/9.html
TTL 74LS47 or 74LS48
Take A look at Experiment # 10 in the StampWorks Manuel, Pg.67. Its on the Parallax store page, Theres a free download but I recommend the hard copy.
The Experiment shows how to Multiplex four 7seg.led displays using 11 I/O pins way better then I could on this post reply.Its simple wiring and a really short code.
Multiplexing is the way to go when using multiple displays.
If Your running low on I/O pins, A digital shift register or two will help free up some I/O pins.(for Buttons) Take a look at Experiments #23,24,25 Pgs.130-145 in StampWorks.
The shift registers are for Your buttons and not the led displays when Multiplexing.( Theres to many timing issues for a beginner to deal with.)
I think You will find these shift registers very useful in Your model R.R. projects.
▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
The Truth is out there············___$WMc%___···························· BoogerWoods, FL. USA
Here's the link for StampWorks
http://www.parallax.com/Portals/0/Downloads/docs/books/sw/Web-SW-v2.1.pdf
BoogerWoods is in the cross roads of Hurricane Charlie, Francis, and Gene.About 50 east of Tampa and 50 miles south of Orlando.
▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
The Truth is out there············___$WMc%___···························· BoogerWoods, FL. USA
I think You like using the old seven seg. displays too.
I've work at the FPL plant on the ST.Johns River in southern Sanford,Rite off of I-4.
I worked on some old seven seg. displays there,BCD mostly.
Here at Home, About 20 miles due south of Winter Haven, I use %BINARY instead of BCD.
▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
The Truth is out there············___$WMc%___···························· BoogerWoods, FL. USA
The official Working code is by spiral
Hey man, you can handle that
A hint: You'll need another button on another input line...... a line of code to handle it decrementing the counter.... and "maybe" one more to make sure the counter doesn't go below zero.
I've not worked with negative numbers on a BS, so I'm sure it's an unsigned number...... You'll have fun with that, Har! Har!...... if you do, remember DEBUG is your friend.... DEBUG the counter.
▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
"puff"...... Smile, there went another one.