Team Four/Final Paper

From Maslab 2013
(Difference between revisions)
Jump to: navigation, search
Line 41: Line 41:
 
===Architecture===
 
===Architecture===
  
 
+
In our final set of code that the robot ran, we had separate code for processing vision, interacting with the arduino and various sensors, and the finite state machine (FSM).
  
 
===Vision===
 
===Vision===
 +
 +
 +
 
===FSM===
 
===FSM===
  
Line 50: Line 53:
 
So in summary, the robot first looked around for balls by turning around on the spot, and if it saw any, it would chase them down.  If it didn't, the robot would go wall follow until it saw another ball, or for 15 seconds passed, after which it would scan over the field again.  If the robot saw the button, then we would aim for it, as if it were a ball, and ram into it four times consecutively (turns out there was a 20 second delay on it, so it would have been more effective to collect the released balls first).  We continued doing that for the first two minutes.  In the third minute, the robot searched for the yellow wall or the yellow box in the tower, aligned itself, and then released the balls that were sitting in the tower.  After it tried scoring, it would look around and search for any balls (to find the ones that missed the tower or failed to go over the wall), and then try to shoot again with 10 seconds remaining.
 
So in summary, the robot first looked around for balls by turning around on the spot, and if it saw any, it would chase them down.  If it didn't, the robot would go wall follow until it saw another ball, or for 15 seconds passed, after which it would scan over the field again.  If the robot saw the button, then we would aim for it, as if it were a ball, and ram into it four times consecutively (turns out there was a 20 second delay on it, so it would have been more effective to collect the released balls first).  We continued doing that for the first two minutes.  In the third minute, the robot searched for the yellow wall or the yellow box in the tower, aligned itself, and then released the balls that were sitting in the tower.  After it tried scoring, it would look around and search for any balls (to find the ones that missed the tower or failed to go over the wall), and then try to shoot again with 10 seconds remaining.
  
We threaded all of our sensors so that they would continuously be updated and set flags as true or false, which would in turn be read by the state machine.  At first, some of us were afraid that having so many threads would slow down the processing, but it turns out that it didn't actually affect it too much.  On the other hand, it didn't seem to give us any more of an advantage, except for the fact we didn't have to hard code checking the sensors in every state.
+
We threaded all of our sensors so that they would continuously be updated and set flags as true or false, which would in turn be read by the state machine.  At first, some of us were afraid that having so many threads would slow down the processing, but it turns out that it didn't actually affect it too much.  On the other hand, it didn't seem to give us any more of an advantage, except for the fact we didn't have to hard-code checking the sensors in every state.
  
 
===Scoring===
 
===Scoring===
Line 56: Line 59:
 
Because we were able to see the yellow wall from the tower and align to that, we decided to only search for yellow when scoring.  Unfortunately, that meant the robot would be more likely to go for the yellow wall because of its larger size, but if we had enough balls that would be okay.
 
Because we were able to see the yellow wall from the tower and align to that, we decided to only search for yellow when scoring.  Unfortunately, that meant the robot would be more likely to go for the yellow wall because of its larger size, but if we had enough balls that would be okay.
  
In terms of aligning to the tower and the yellow wall, we simply used PID control to target the center of the wall, and then have it drive towards it until it triggered a bump sensor.  Unfortunately, relying only on the bump sensors meant that the robot couldn't bump into any other wall before hand, or else it would dump the balls prematurely.
+
In terms of aligning to the tower and the yellow wall, we simply used PID control to target the center of the wall, and then have it drive towards it until it triggered a bump sensor.  Unfortunately, relying only on the bump sensors meant that the robot couldn't bump into any other wall beforehand, or else it would dump the balls prematurely.
  
 
===Modularity===
 
===Modularity===
Line 66: Line 69:
 
==Placing in the Mock Competitions==
 
==Placing in the Mock Competitions==
  
The only reason why we got second place is because we didn't have to face the Mengineers (Team 3) earlier in the game. And that's because neither of us seeded particularly well, and we were worse than they were.
+
Our mock competition performance was sub-par at best, mainly due to the engineers not having thier act together ahead of time. Throughout the first three weeks we had a lot of mechanical problems to overcome, but the problem that held us back the most was the repeated failure of our roller mechanism. Because we didn’t have a working rubberband roller we couldn’t test all of our systems in one integrated package until the seeding competition, which meant even though our helix worked well the first time we couldn’t propperly test its function.
 +
 
 +
During the final competition, we got to second place mainly through luck. Our series of matches were mainly wins due to us malfunctioning a little bit less than our opponent, even though our robot seemed to work so well in testing.  
  
 
=Problems Encountered=
 
=Problems Encountered=
Line 72: Line 77:
 
==Mechanical Design==
 
==Mechanical Design==
 
==Electronics==
 
==Electronics==
 +
=== 5V Regulator ===
  
We also soldered connections onto the Arduino shields in order to make better, more reliable, and more permanent electronic connections from our sensors to the Arduino.  However, in addition to its benefits, there were its own problems, probably resulting from inexpert soldering...
+
Because we got a pin stuck in the 5V power source on the Arduino, we had to power all our sensors through the 5V regulator.  As a result, since our 5V regulator was sourcing a lot of current, we had to use two 5V regulators in parallel so that they would not overheat and turn off.  The two regulators were loaded with the various sensors as equally as possible.  Comments online suggested not putting only two 5V regulators in parallel (e.g. branching out into two 5V regulators and then combining those two branches back into one), because even a small difference between the regulator output voltages would result in one regulator sourcing all the current, which would defeat the point of having regulators in parallel at all.
 +
 
 +
===Arduino Connections===
 +
 
 +
We soldered connections onto the Arduino shields in order to make better, more reliable, and more permanent electronic connections from our sensors to the Arduino, compared to using a breadboardWe decided to do this because our hardware did not seem to be functioning reliably.  In the mock competition earlier that day, we had rogue motors, which resulted from pwm and direction pins plugged in backwards (which happened when trying to find out why another motor was rogue because of somewhere in the code),  Later in the day, we couldn’t get one of our motors to run at all.  When trying to identify the issue, which we thought was coming from a bad connection in the motor controller, we accidentally fried our motor controller with the output voltage wire from the 5 V regulator, which was disconnected in order to prevent it from over-heating.  (The battery should have been disconnected, but wasn’t).  Therefore, in addition to adding a 5 V regulator in parallel to the one we already had, we wanted to finalize our wiring.  Additionally, since we had gotten everything to work at least once before, we theoretically knew how to do everything, so we figured we would not have too much trouble doing so.
 +
 
 +
However, in addition to its benefits, there were its own problems, mostly resulting from inexpert soldering...  For example, sometimes things you thought were connected with solder actually were not, and sometimes connections you thought were reliably somehow disconnected, though they were working well earlier.  And even worse, somehow, though the sensors might have been working earlier, and though the sensors might be working on the board and reading voltages as expected, the information is no longer being transmitted to the Arduino through the pin it’s connected to.  We only “solved” this last issue by completely changing the pin that the sensor was soldered to.  If you choose to solder, then the multimeter will be your best friend.
  
 
==Code==
 
==Code==
 +
 +
Turns out that for some reason, you can’t use digital pins and analog pins of the same number.  This should be a bug in the arduino firmware provided by staff, and hopefully it’ll be corrected soon.
 +
 
==During the Competition==
 
==During the Competition==
 +
 +
Unfortunately, our robot didn’t perform as well during the competition as we would have liked/as we tested before.  One of the most noticeable problems that we encountered during the competition and not during the practice runs was the noise from the audience.  We didn’t filter the vision to ignore everything above the blue line, though we probably should have.  Before, we had adjusted the camera to be positioned such that it couldn’t see over the six inch wall,  but when we reattached it, the camera seems to have been able to see a bit higher.  At first, we thought the vision code would be robust enough to withstand a little noise, but we didn’t consider the situations when it only sees objects off the field, like a red box, or an audience member’s bright red sweater.
 +
 
==Hindsight is 20/20==
 
==Hindsight is 20/20==
 +
 +
Considering we only actually had a functioning robot within the last 48 hours of MASlab, we think we did pretty well!  We think it’s because we had our awesome design, and because we had our code mostly written by the end of the month, even though we were delayed in testing it.  However, it is obvious that if we had more time to test the code more, perfect the PID constants, and improve localization strategies, we would have done better.
 +
 +
Therefore, we would suggest deciding on a strategy as quickly as possible, setting up a finite state machine as quickly as possible, and getting started on the code as quickly as possible, even if the robot hasn’t been completely built yet.  That way, you can even definitively decide on what sensors you will need--the the mechanical engineers and design for them, and the coders can code for them.  Also, as guided by the check-offs, getting the vision done quickly and is a good idea too. 
 +
 +
Additionally, making things as modular as possible is going to help out a lot.  For example, our alignment to the tower, yellow wall, and cyan button was exactly the same as our method used for ball following/alignment.  We simply had to calibrate the vision to detect a certain color, and then we could use PID to align ourselves with the target.  Then, because our PID method was relatively general, we were able to do PID on following and all of the alignment just by setting the error and the constants depending on our situation.  This made it easier to do a relatively wide range of tasks while keeping things simple.  Though the results weren’t perfect, they were effective.

Revision as of 15:06, 4 February 2013

Contents

Overall Strategy

Our strategy for this game was to collect as many balls as possible and then score all of them in the last minute by shooting them into the tower or over the yellow wall, whichever one it saw first. However, we built our robot such that it was tall enough to score into the blue tower for 50 points, in the event the robot did aim for the tower. We originally were going to just aim for the blue tower, because we thought the middle tower would have a large capacity. But, when we found out that the blue tier could only fit four or five, we started aiming for the yellow wall as well, because that offered more points than scoring in the purple tier would. If we had enough time, we would have optimized the code to score balls in the top two tiers, and then the rest over the wall. However, we didn't have time to get that running. We also anticipated that our robot would have a much larger capacity than the other robots, which ended up being kind of true, so our strategy involved pressing the cyan button to put as many balls on the field as possible. We also thought that clearing the field would be a good strategy, but figured it would be difficult to do reliably, especially if there was a ball in a relatively isolated location that the robot never got to. Though we would have mechanisms to theoretically find all the balls, it might have taken a long time. Also, since the button released the balls in small area, theoretically, it would not have been difficult to pick up all of those balls in the area and then move on.

Mechanical Design

Drive System

In order to maximize the amount of traction we could get on carpet, we made ridiculously dangerous wheels with spikes. However, the field was changed to a black foam, and our wheels would have destroyed it. Therefore, we put tape around the circumference of our wheels, and that seemed to do the trick. However, sometimes the robot got stuck in small kinks on the field (like where the pieces of foam came together), and sometimes didn't seem to move terribly well on the foam.

Rubber Band Pick Up System

In previous years, this design seemed to work well. For other teams, this design seemed to work relatively well too. This was actually the system we had the most trouble with. The first time, the roller was too low, and the balls jammed the roller. In fact, it ruined our first motor. The second time, the roller was too high, and the balls didn't grip the balls enough. The third time, we finally got the height about right, even though we had to add zip-ties to help grab the balls and kick them into the tower system that lifted the balls. Unfortunately, though the zip-ties helped us out, they also sometimes caused the motor to jam when picking up the balls. Additionally, the roller seemed to stall when picking up multiple balls at once.

Double Helical Brush Lift System

Deoxyrobonucleic acid :P

Shooting Bridge

Four-point joint thing??


Sensors

In addition to the camera, we used two bump sensors in the front, 1 short-range IR sensor, 1 long-range IR sensor. Ideally we could have used more sensors, but what we had was satisfactory. The short-range IR sensor, positioned on the left side of the robot pointing forward 45 degrees, was used for wall-following; the long-range IR sensor, positioned on the right front and angled 45 degrees to the right, was used to prevent it from crashing into walls in front of it during wall-following; and the bump sensors were used throughout all of the states to tell the robot when it crashed into a wall. The bump sensors were also used to tell us when the robot hit the wall or tower when it was trying to shoot, but we realized a bit too late that that didn't guarantee that we were actually at our target.

IR Sensors

The IR sensors were put at approximately 45 degree angles, such that as much information about the robot could be determined. Not only would diagonal IR sensors provide information about more locations around the robot than just in one spot, it would be able to tell us about any "orientation perturbations." If the IR sensor were point at the wall at a 90 degree angle, it wouldn't be able to tell if the robot were tilted inwards or outwards from the wall, because it would be detecting a larger distance either way. Also, since the short-range IR sensor positioned on the side was facing forwards, it also gave us more information about the wall closer to the front of the robot, so the robot could react in a timely manner.

Even though our long-range IR sensor was only detecting things in front of the robot, having it at a 45 degree angle was crucial since we were only using one. This way, the IR sensors were able to detect things on the right and on the left instead of only just in front of it. However, since we were wall-following on the right, our IR sensor ideally would have been on the left, so we could get information about walls turning away too. However, with PID correction on the robot's distance from the wall was effective enough for wall-following.

In the situation where the walls were bending inwards at an angle similar to the angle of the long-range IR sensor, the robot still managed to avoid the wall, (because of the forward facing short-range IR sensor on the side, but it was a bit close for comfort. In situations like these, it would have been useful to have two long-range IR sensors, both pointing inwards at 45 degree angles.

Bump Sensors

The bump sensors could have been improved if they were more integrated in the mechanical design. Otherwise, they are difficult to make reliable. If they are not properly fixed onto the robot, they can be pushed but not be triggered. Also, most provide small coverage, making it a matter of chance that when the robot hits the wall it will actually hit the bump sensor. We tried adding extensions to our whisker bump sensors, and repositioned them many many times. Only after many iterations, and securely attaching the sensors onto the robot the day before the competition did they work reasonably well (until we accidentally broke one off right before our final match >.>). Note that bump sensors need a pull down resistor (essentially a resistor in series) in order to work properly.


Software

Architecture

In our final set of code that the robot ran, we had separate code for processing vision, interacting with the arduino and various sensors, and the finite state machine (FSM).

Vision

FSM

Our finite state machine had two basic states: the exploring/ball collection state, and the scoring state. Within these two basic states, we had "substates" that would mostly control the behavior of the robot. We first sketched out our state machine, which essentially looked like this... [insert picture of state machine]

So in summary, the robot first looked around for balls by turning around on the spot, and if it saw any, it would chase them down. If it didn't, the robot would go wall follow until it saw another ball, or for 15 seconds passed, after which it would scan over the field again. If the robot saw the button, then we would aim for it, as if it were a ball, and ram into it four times consecutively (turns out there was a 20 second delay on it, so it would have been more effective to collect the released balls first). We continued doing that for the first two minutes. In the third minute, the robot searched for the yellow wall or the yellow box in the tower, aligned itself, and then released the balls that were sitting in the tower. After it tried scoring, it would look around and search for any balls (to find the ones that missed the tower or failed to go over the wall), and then try to shoot again with 10 seconds remaining.

We threaded all of our sensors so that they would continuously be updated and set flags as true or false, which would in turn be read by the state machine. At first, some of us were afraid that having so many threads would slow down the processing, but it turns out that it didn't actually affect it too much. On the other hand, it didn't seem to give us any more of an advantage, except for the fact we didn't have to hard-code checking the sensors in every state.

Scoring

Because we were able to see the yellow wall from the tower and align to that, we decided to only search for yellow when scoring. Unfortunately, that meant the robot would be more likely to go for the yellow wall because of its larger size, but if we had enough balls that would be okay.

In terms of aligning to the tower and the yellow wall, we simply used PID control to target the center of the wall, and then have it drive towards it until it triggered a bump sensor. Unfortunately, relying only on the bump sensors meant that the robot couldn't bump into any other wall beforehand, or else it would dump the balls prematurely.

Modularity

The advantage of having sensor code, vision code, and the finite state machine in different places was the modularity of how the robot was going to behave. This was particularly useful for the mock competitions, so we could work on coding for the final competition, but still have our robot function minimally even if not everything was working at the moment.

We also wrote simple test modules, which would allow us to test our sensors and motors quickly. That proved to be extremely useful before and during the competition to make sure everything was functioning.

Placing in the Mock Competitions

Our mock competition performance was sub-par at best, mainly due to the engineers not having thier act together ahead of time. Throughout the first three weeks we had a lot of mechanical problems to overcome, but the problem that held us back the most was the repeated failure of our roller mechanism. Because we didn’t have a working rubberband roller we couldn’t test all of our systems in one integrated package until the seeding competition, which meant even though our helix worked well the first time we couldn’t propperly test its function.

During the final competition, we got to second place mainly through luck. Our series of matches were mainly wins due to us malfunctioning a little bit less than our opponent, even though our robot seemed to work so well in testing.

Problems Encountered

Mechanical Design

Electronics

5V Regulator

Because we got a pin stuck in the 5V power source on the Arduino, we had to power all our sensors through the 5V regulator. As a result, since our 5V regulator was sourcing a lot of current, we had to use two 5V regulators in parallel so that they would not overheat and turn off. The two regulators were loaded with the various sensors as equally as possible. Comments online suggested not putting only two 5V regulators in parallel (e.g. branching out into two 5V regulators and then combining those two branches back into one), because even a small difference between the regulator output voltages would result in one regulator sourcing all the current, which would defeat the point of having regulators in parallel at all.

Arduino Connections

We soldered connections onto the Arduino shields in order to make better, more reliable, and more permanent electronic connections from our sensors to the Arduino, compared to using a breadboard. We decided to do this because our hardware did not seem to be functioning reliably. In the mock competition earlier that day, we had rogue motors, which resulted from pwm and direction pins plugged in backwards (which happened when trying to find out why another motor was rogue because of somewhere in the code), Later in the day, we couldn’t get one of our motors to run at all. When trying to identify the issue, which we thought was coming from a bad connection in the motor controller, we accidentally fried our motor controller with the output voltage wire from the 5 V regulator, which was disconnected in order to prevent it from over-heating. (The battery should have been disconnected, but wasn’t). Therefore, in addition to adding a 5 V regulator in parallel to the one we already had, we wanted to finalize our wiring. Additionally, since we had gotten everything to work at least once before, we theoretically knew how to do everything, so we figured we would not have too much trouble doing so.

However, in addition to its benefits, there were its own problems, mostly resulting from inexpert soldering... For example, sometimes things you thought were connected with solder actually were not, and sometimes connections you thought were reliably somehow disconnected, though they were working well earlier. And even worse, somehow, though the sensors might have been working earlier, and though the sensors might be working on the board and reading voltages as expected, the information is no longer being transmitted to the Arduino through the pin it’s connected to. We only “solved” this last issue by completely changing the pin that the sensor was soldered to. If you choose to solder, then the multimeter will be your best friend.

Code

Turns out that for some reason, you can’t use digital pins and analog pins of the same number. This should be a bug in the arduino firmware provided by staff, and hopefully it’ll be corrected soon.

During the Competition

Unfortunately, our robot didn’t perform as well during the competition as we would have liked/as we tested before. One of the most noticeable problems that we encountered during the competition and not during the practice runs was the noise from the audience. We didn’t filter the vision to ignore everything above the blue line, though we probably should have. Before, we had adjusted the camera to be positioned such that it couldn’t see over the six inch wall, but when we reattached it, the camera seems to have been able to see a bit higher. At first, we thought the vision code would be robust enough to withstand a little noise, but we didn’t consider the situations when it only sees objects off the field, like a red box, or an audience member’s bright red sweater.

Hindsight is 20/20

Considering we only actually had a functioning robot within the last 48 hours of MASlab, we think we did pretty well! We think it’s because we had our awesome design, and because we had our code mostly written by the end of the month, even though we were delayed in testing it. However, it is obvious that if we had more time to test the code more, perfect the PID constants, and improve localization strategies, we would have done better.

Therefore, we would suggest deciding on a strategy as quickly as possible, setting up a finite state machine as quickly as possible, and getting started on the code as quickly as possible, even if the robot hasn’t been completely built yet. That way, you can even definitively decide on what sensors you will need--the the mechanical engineers and design for them, and the coders can code for them. Also, as guided by the check-offs, getting the vision done quickly and is a good idea too.

Additionally, making things as modular as possible is going to help out a lot. For example, our alignment to the tower, yellow wall, and cyan button was exactly the same as our method used for ball following/alignment. We simply had to calibrate the vision to detect a certain color, and then we could use PID to align ourselves with the target. Then, because our PID method was relatively general, we were able to do PID on following and all of the alignment just by setting the error and the constants depending on our situation. This made it easier to do a relatively wide range of tasks while keeping things simple. Though the results weren’t perfect, they were effective.

Personal tools