Help with some Basic Stamp 2 programming for art project
Blake
Posts: 74
Hey, I'm a senior Sculpture undergrad at Cornell University, and I'm using some BASIC stamps in a few of my projects for my thesis. I was wondering if there was anyone who would be willing to provide me with some assistance in writing a few programs. I know the basics of pbasic but not a lot of complex language. I've been learning with the book, Physical Computing.
Here's what I'm doing:
I would like to control typewriters with solenoids. I have two typewriters typing different words on each. I have a bunch of solenoids arrayed with bicycle brake lines, so that they each punch one key, thus typing one character. The solenoids are activated by a motion detector. Thus if the motion detector sense motion, the solenoids might type out, "P" "R" "E" "S" "E" "N" "T" "," "<space>" and wait for the next detection. I need to write a program that takes into account the line length of the typewriter to occasionally press the "<return>" button. Also, I would like to incorporate another motion detector, that, when activated, interrupts the normal flow of the first detector, inserting a new word with other solenoids standing by.
So with the two typewriters, one might type "left, left, left, left" and the other might type "right, right, right, right" but then a third motion detector might insert the word "not" into it so that it becomes, "left, left, left, not, left, not, left, left, left" or "right, right, right, not, right" creating a new message when the viewer glances across both units.
I anticipate needing to know something about "counters" within the code to keep track of how many solenoids have activated.
If any of this sounds interesting, and you could help check my code or something, let me know.
thanks,
blake
bbf3@cornell.edu
Here's what I'm doing:
I would like to control typewriters with solenoids. I have two typewriters typing different words on each. I have a bunch of solenoids arrayed with bicycle brake lines, so that they each punch one key, thus typing one character. The solenoids are activated by a motion detector. Thus if the motion detector sense motion, the solenoids might type out, "P" "R" "E" "S" "E" "N" "T" "," "<space>" and wait for the next detection. I need to write a program that takes into account the line length of the typewriter to occasionally press the "<return>" button. Also, I would like to incorporate another motion detector, that, when activated, interrupts the normal flow of the first detector, inserting a new word with other solenoids standing by.
So with the two typewriters, one might type "left, left, left, left" and the other might type "right, right, right, right" but then a third motion detector might insert the word "not" into it so that it becomes, "left, left, left, not, left, not, left, left, left" or "right, right, right, not, right" creating a new message when the viewer glances across both units.
I anticipate needing to know something about "counters" within the code to keep track of how many solenoids have activated.
If any of this sounds interesting, and you could help check my code or something, let me know.
thanks,
blake
bbf3@cornell.edu
Comments
We'd all be happy to take a look at your code as you go along.
Ryan
▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Ryan Clarke
Parallax Tech Support
RClarke@Parallax.com
a copy of my code is as follows:
' {$STAMP BS2}
' {$PBASIC 2.5}
INPUT 0
total VAR Word
sense:
IF IN0=1 THEN act:
GOTO sense:
act:
'r key
HIGH 1
PAUSE 300
LOW 1
'i key
HIGH 2
PAUSE 300
LOW 2
'g key
HIGH 3
PAUSE 300
LOW 3
'h key
HIGH 4
PAUSE 300
LOW 4
't key
HIGH 5
PAUSE 300
LOW 5
', key
HIGH 6
PAUSE 300
LOW 6
'<space> key
HIGH 7
PAUSE 300
LOW 7
total=total+7
IF total=65 THEN autoreturn:
GOTO sense:
autoreturn:
'<return>
HIGH 8
PAUSE 300
LOW 8
GOTO sense:
END
How does this seem?
I have trouble with the principle of switching between different sections of code using IF/THEN commands
At the end of the act: section, I am trying to have a variable count upwards each time the act: section is used, so that it will press return (go to the autoreturn: section) at 65 characters in length. Does anyone foresee any problems with this code?
Thanks ahead of time for your help,
I'm new at the world of PBASIC,
Blake
bbf3@cornell.edu
I see a couple things that would help your code. Since you are doing things that follow a pattern, you can use a loop to reduce your code to a few lines.
Example:
for keyloop = 1 to 7
high keyloop
pause 300
low keyloop
next
Also, if you add 7 to your total every time, it will never equal 65. You will want to pick a different number or use >= .
Another thing that would be useful is to make your return action a subroutine. That way you can use it from other places in your program.
Hope that helps.
Lee
I've attached a program that uses a more generalized approach to typing words. It defines constants for each solenoid and builds words out of the constants. It then uses loops to type the words. Please note that the program compiles correctly, but I haven't been able to test it so there may be some logic errors.
The program I wrote will work for typing everything on one typewriter and uses all 16 I/O pins. You might run into the problem where using one pin per solenoid you are going to run out of I/O pins on the BS2 if you want to have three motion detectors and be able to type "left", "not", <comma>, <space> & <return> on one typewriter and "right", "not", <comma>, <space> & <return> on another. You might need to use a BS2p40 or maybe a Propeller.
When you want to post code of more than a couple lines, it's best to either attach it or use [noparse][[/noparse]*code] [noparse][[/noparse]/code*] tags (without the asterisks) around it. That way the spacing is maintained and it's much easier to read and use.
▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
OS-X: because making Unix user-friendly was easier than debugging Windows
READ wordAddr, theKey
·· DO WHILE (theKey <> 0)
····· HIGH theKey
····· PAUSE 300
····· LOW theKey
····· letterCount = letterCount + 1
····· WordAddr = wordAddr + 1
····· READ wordAddr, theKey
What does the <> mean?
theKey is a variable, not a command. I've stored the various words as sequences of values in EEPROM. Since the only way to access data stored in EEPROM is by reading it into a variable, I'm reading each value into theKey.
Here's how the Type_Word subroutine works:
The statement "READ wordAddr, theKey" reads the EEPROM data at the address wordAddr into the variable theKey. The HIGH, PAUSE, and LOW statements then set that pin high and low to type the key. letterCount is incremented then wordAddr is incremented. Now wordAddr points at the next address in EEPROM and that value is read into theKey and the loop starts again. When the value read into theKey is 0, the loop stops.
So to type "right, ", you set wordAddr equal to "word_right" and GOSUB Type_Word.
You can type any sequence of characters by creating a DATA statement that has a list of the characters you want followed by a zero. So to type "fortnight, " you'd have the line:
and somewhere in the program you'd have:
I hope that explanation helps.
▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
OS-X: because making Unix user-friendly was easier than debugging Windows
Again, thanks so much for the help,
Blake
In this case word_right will have the value 87. The line "wordAddr = word_right" assigns the value 87 to the variable wordAddr. The line "READ wordAddr, theKey" assigns the value at location 87 to the variable theKey. So theKey gets the value 1. Then "wordAddr = wordAddr + 1" sets wordAddr to 88 and "READ wordAddr, theKey" assigns the value at location 88 to theKey. The loop stops when theKey is set to 0.
▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
OS-X: because making Unix user-friendly was easier than debugging Windows
How can I store a word value into the internal EEPROM?
The internal EEPROM of the BASIC Stamp module (used for both program and data storage) is organized and accessed in units of bytes only. Since a word value is actually two bytes it requires two consecutive memory locations to store it in EEPROM. You must break the word value into its lower and upper byte parts and use two WRITE commands to store the value, or two READ commands to retrieve it.
The following code demonstrates this for the BASIC Stamp 1 module:
W0 = 1250
WRITE 0, B0
WRITE 1, B1
The following code demonstrates this for the BASIC Stamp 2, 2e, 2sx, 2p24, 2p40, and the 2pe modules:
Temp VAR WORD
Temp = 1250
WRITE 0, Temp.LOWBYTE
WRITE 1, Temp.HIGHBYTE
also, i have attached the current updated program:
?
Thanks,
Blake
i think there may be something wrong with how i wired it. Its very simple though. Each pin is connected to the base of a tip120 darlington transistor. The collector is attached to a 24v·bus. the emitter goes to the positive end of a polarized solenoid. The·ground end of the solenoid goes to the ground. This seems logical right?
Thanks,
Blake
Post Edited (Blake) : 5/27/2006 4:05:08 AM GMT
Let me know if you have any other suggestions,
Blake
I've modified your program. I guessed on the pins and I/O groups. I also had to make a couple assumptions, but you can change them if necessary. If you have trouble, let me know.
My assumptions:
1) "wrong" is typed on typewriter 2
2) "right" and "right is" are typed on typewriter 1
Here's how your detector logic works:
If detector_3 is on and detector_1 is on, "wrong. " gets typed.
If detector_2 is on and detector_3 is on, "right is, right, " gets typed.
If detector_2 is on and detector_3 is off, "right, " gets typed.
Is that the way you want it?
Keep in mind that the attached program compiles, but could still have logic errors. I'll have to leave the hardware hookup details to those with experience.
▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
OS-X: because making Unix user-friendly was easier than debugging Windows
Here's how your detector logic works:
If detector_3 is on and detector_1 is on, "wrong. " gets typed.
If detector_2 is on and detector_3 is on, "right is, right, " gets typed.
If detector_2 is on and detector_3 is off, "right, " gets typed.
Your assumptions are correct.
However, the detector logic is not.
Typewriter 2 operates independently of Typewriter 1 and uses only 1 detector, which is detector_3. If detector_3 = 1, then the typewriter should type "wrong,_", regardless of any other detectors.
Typewriter 1 should type "right,_" if detector_2 is on and detector_1 is off. If detector_1 is on, regardless of detector_2, typewriter 1 (on the left side) should type "right_is,_".
▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
OS-X: because making Unix user-friendly was easier than debugging Windows
Thus far, with the current program, the right-side typewriter types "rog._" when the right hand detector (detector_3) senses movement. The left-side typewriter thus far does nothing no matter what. Additionally, when it gets to the end of a line, it does hit return, and move to the next line. It's awesome to watch even just at this phase.
I've tested everything with other simpler programs however, and all solenoids trigger correctly, so i think we have dealt with most hardware issues and are down to software.
Post Edited (Blake) : 5/27/2006 10:49:57 PM GMT
As far as the detectors, it would be great if you could hook up LEDs to Aux I/O pins 4-6. Then you could run a loop like this:
Then you could confirm that your detectors are working. If you can have a computer hooked up at the same time as the detectors, you could do something like this:
You also need to look at the timing of when the detectors are read. Right now, the program first looks at detector 3. If it's active, "wrong. " gets typed. Then the program looks at detector 1. Is detector 1 still going to be active at that point? If not, you need to create three variables to store the detector values at the beginning of the loop like this:
Hopefully this will be enough to get you going. Good luck!
(If you do make any changes to the program, be sure to post your current version if you need any further help.)
▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
OS-X: because making Unix user-friendly was easier than debugging Windows
▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
OS-X: because making Unix user-friendly was easier than debugging Windows