In my previous post, I talked about getting a new Lego Mindstorms NXT 2.0 robotics kit and about building TrophyBot to carry around a Lego trophy Catherine Eibner won for being an awesome evangelist. In this post, as promised, I'll talk about how I programmed the robot to move around, shouting "HORRAY!" whenever it bumped into anything.
The Lego Mindstorms NXT software is a really nice piece of work. It's a Flash player preloaded with the always excellent step-by-step instructions for building four very cool robots, a vehicle (ShooterBot), an animal (Robogator), a machine (Color Sorter) and a humanoid (Alpha Rex). Lego instructions are exceptionally thorough, which means that even a novice can construct a working robot in fairly short order.
Aside: I've been thinking a bit about the corollary between these step-by-step logo instructions and how I started programming, which was copying 100 or so lines of code out of a magazine to do <insert inane or mundane thing here>. Having something to copy meant that I had a base to experiment from, to draw conclusions about and to formulate patterns around. I could generalise and improvise. This fed my curiosity far more than I see my childrens' being fed by the current "download 1000 lines and a couple of libraries from the internet". I think that actually typing in the code and fixing the inevitable typos gave me more insight. I've noticed this trait in my kids though when they build Lego. The instructions are very clear, but they have to execute every one of them to make the robot (or what ever they're building) work. They're much more familiar with it than if I'd built it for them and said "have a look at this and see how it works". My gut feel (completely devoid of any science) is that their curiosity is awakened by the feeling of ownership and achievement that comes with building it themselves.
I used the first section of Shooterbot - the driving base - for Trophybot
To this I needed to add a bump sensor (so Trophybot could detect and move away from obstacles) and a platform to hold the trophy.
Ignore the ultrasonic sensor (that looks like a pair of eyes), it's not used at this stage.
The next step was to actually make Trophybot do something. First, I had to connect the NXT to the computer. There are a couple of ways to do this, either tether via USB or connect via Bluetooth. the instructions for both are pretty straightforward, so I did both.
Now it was time to write the first bit of code. In fact, using the NXT software, it's actually a matter of assembling and wiring together programming blocks. Initially, I just wanted Trophybot to go forwards and I'd manually pick it up and turn it off.
I created a new program called, originally enough, "Go Forward" and was presented with a blank canvas:
I grabbed the Move block from the top of the toolbar and dropped it where it says "Start". When the new block's selected, a properties pane appears at the bottom of the screen to let you set properties for that block. I set the duration property to Unlimited and hit the download button.
I pressed the orange button on the NXT brick 4 times to run the program I'd just downloaded and nothing happened - hmm.
OK - maybe the environment's smart enough not to get into an infinite loop, so I added some logic - what I thought might be a sensible way to represent an event (in this case, the sensor getting pressed). I chose the complete palette in the blocks toolbox and dropped a touch sensor on the canvas. I didn't connect it to anything because I figured this would be an event that happened and broke into whatever was going on at the time.
The sensor block stayed greyed-out, which I guessed meant that it wouldn't be used. More work needed.
Next I tried putting all the logic in a loop that polled the state of the sensor each iteration and then took the appropriate action.
Loop If sensor not pressed or bumped Go forward 1 second Else Go back 1 revolution Turn right 1 revolution EndIf End Loop
Which at least made the robot move but it had two drawbacks:
- It moved forward in 1 second jerks followed by a small break; and
- It didn't react to a bump or press until the second of forward motion was done.
Interestingly, the way to fix this is to make the motion in the top part of the loop unlimited instead of making it a specific duration. The unlimited move block is a special case that actually means keep moving until the condition at the start of the loop changes. It also doesn't work outside a loop (which is why my first, single block, program failed) because it "falls through immediately to the next step.
Finally, I added some randomness to the program that meant that the robot turns in a random direction and a random number of degrees when it hits something. This seems to give it more of a chance to get out of corners and away from complex obstacles. I also added a play sound block to make the bot say "Horray!" whenever it bumped into something.
The final program looks like this:
All-in-all, this was a really fun start to what's going to be a much longer term project. I've managed to acquire a Lego Technics truck that is ripe for roboticising and I'm looking forward to having a play with the .NET programming environment provided by Microsoft Robotics Studio.
I'll keep you in the (infinite) loop.