Coding TomBot

Tags: control
Personhours: 14
Coding TomBot By Cooper and Jose

Task: Use existing code from the code base to program TomBot

To code TomBot, we decided to use the codebase from Frankendroid, as its the one we were most comfortable with. This will change after the qualifier, as we recognize that the robot is more like last year's robot, Icarus. This will, in the long run, help us as we will be able to minimize the amount of refactoring we have to do. But in the meantime, we made 4 major changes in the code for Tombot.

Change #1 - Mecanum Drive to Differential

The first was the change from a mecanum drive to a differential, arcade style control. This was done by commenting out the lines for strafing, and changing the method call to a dormant method, which was a remnant from some testing done with a linear op mode for an early version of FrankenDroid. We got rid of the power assignment for the front motors, and just used the back two motors to represent our 2 drive motors. This gave us some trouble, which I’ll cover later. After that trouble, the method was still broken, as the left stick y was controlling the left motor, and the right stick x was controlling the right motor. This was due to the incorrect power assignments in the code. With that fix done, it drove as it should after the switching of an encoder cable.

Change #2 - Rolling Gripper to 3-finger gripper

The next 'big' change was the change from the rolling gripper on frankenDroid to the 3- finger design on TomBot. I use the word big lightly, as it wasn't more than commenting out the lines for one of the servos. However, this will have a major impact, which can be seen in the details in our grippers post. This is also note worthy in terms of auto, as it will have adverse effects on auto. This is due to the current instability and overall unpredictability of it. So, in auto, we will have to compensate for it.

Change #3 - Turret

One of the biggest changes to the code base we made was with the Turntable class that I wrote. This was also, therefore, the hardest part. Due to the fact I'm still relatively new to this, I got a lot of my examples from the Crane class that Ahbi wrote last year. I started first by tackling making a basic skeleton, including methods like rotateTo() and rotateRight(). Then I started filling them in. For some reason, the first go around at this, I decided to through out all the things they taught me in school and use rotateRight() and rotateLeft() as my lowest level method, instead of rotateTo(). Another thing I failed to realize is that I didn't fully get the Crane class, and made a redundant positionInternal variable for the encoder values that is assigned at the rotate method calls and then another variable called currentPosition was assigned to that, and then the encoder value for the motor was set to that. This sounds stupid, because it was. This cost me a good day of working and was a great lesson in taking my time understanding something before I go off and do it

Once I had realized my misunderstandings of the Crane class, I was able to move on. I cut out all the unnecessary positionInternal code, using the other variable (currentRotation) to be changed in the rotate mehtods. Speaking of, I also got some sense into me and changed the rotate methods to use setRotation() as its lower-level method, making the code more professional in nature. This, still, was not our only problem. Next was encountered a bizzare glitch-like attribute to using the rotate methods. There was a sporadic, sudden movement whenever we pressed the button assigned for turning the table (the a button as it was just a test). After many looks at all the possible variables of failure, we whittled it down to be the fact that we assigned it to the controllers A button. What we observed was the turntable working, just not how we thought we were telling it to. In the button map, there was a method called toggleAllowed() infront of all the boolean-value button. This, unbeknownst to me was actually a toggle method written by Tycho many years ago. This toggle made it so the action assigned to the button only happened once, which is useful for things like latches and poses, as the driver could overshoot it if left to un-press the button in the correct amount of time. This, however, in our case led to the turnLeft() method (the one assigned at the time) only happen once, which was that sudden, sporadic movement after the a button.

Once we changed it to a trigger, it worked-- almost. there was still some bug in the code that made it do some pretty funky stuff, which is hard to describe. After we whittled it down to just a small error of changing a negative to a positive, it worked perfectly.

Change #4 - XML file

During the Woodrow Scrimmage, I spent most of my time dealing with null pointer exception errors and incorrect XML assignments. This was, again, due to a lack of knowledge of the code base. I tried to comment out certain motors, which led to the null pointers, and tried to get rid of those null pointers in the XML file. After awhile of this loop, I realized my mistake in that the null pointers were due to a method call on an uninstantiated object. When I put all the assignments back in the Init, I was finally able to get it running

Next Steps

My next steps are to tune the PID values for auto, so I can use the skeleton from FrankenDroid. Then I need to take some of the sounds from the driver phone, like the critical error one, as it can severely affect workflow and my sanity. Finally, I need to change the turret to make it so that it uses the IMU heading instead of entirely the encoder value from the turntable.

Date | November 20, 2019