Swerve Drive Control

Hello everyone,
Our team 876 has expressed some interest in building a swerve drive practice bot. Up to this point we have only done tank drive. While building a practice bot (on a budget of course) presents it’s own set of challenges, as programmer I have a whole different set of issues. Let me bring you up to speed on what we can assume about this robot.

Drivetrain: Swerve, since this is our first time using swerve drive I decided to keep is simple. Each of the 4 swerve modules will be turned **individually** via window motor. They will turn 90 degrees (allowing for full swerve motion without using coaxial swerve). The modules will be synced via potentiometers, not encoders. The wheels will be driven in the classic swerve style of the CIM turning with the wheel on the "Z" axis. Over all motor count: 4 CIMs and 4 window motors.

Control: Here is where I am lost, we have always used tank drive and I would like to stick with a two joystick system as long as it is not outrageously complicated. I feel like most teams use a single joystick to control direction of travel and some other method to control the orientation of the robot. **What is the best control scheme to drive in swerve?** A joystick with rotation on the "Z" axis is an option, as is an Xbox controller. **But I would like to use two regular joysticks how can this best be accomplished?

**

Here is my guess on how a 2 joystick system can work, I am sure there are flaws with this concept:

The values from both joysticks are averaged if they are both within a certain range of each other, when they are out of that range the program checks the "Y" values of the joysticks and turns at the appropriate speed based on the difference of those two values. For example:<br><br>![Joysticks.png|300x300](upload://fCDvFlZcbNSKdD6WakgVr3hW9ke.png.png)<br><br><br>![Joysticks.png|300x300](upload://fCDvFlZcbNSKdD6WakgVr3hW9ke.png.png)<br>

Our team has gone through a few joystick options, but we’ve settled on double joysticks.
We have one joystick that has X/Y axes used for strafing, and second 3d joystick where we only use the Z axis (for rotation).
Xbox controller comes in second-- X/Y on the left for strafing, and X on the right for rotation
As for a single 3d joystick, I find it really hard to control

That double joystick layout you have looks pretty interesting… maybe I’ll test it out myself.
However, I think it might be rather difficult to control the rotation like that, but I can’t think of any better double X/Y layouts.

5 years back (Lunacy I think) we built what you are talking about. We made it drive in multiple modes. In the main mode one joystick moved it like a swerve (translating) and a second joystick rotated the robot.In a second mode, it drove like a car. In a third mode it drove like a tank.

We tried window motors also but beware. You must gear them up (3:1) so they do not overheat and cutoff and/or NOT use hi-traction treaded wheels. Ours worked well (window motors to turn at 1:1) on the Lunacy low-friction field but the next year it was not strong enough to turn on carpet. I would recommend you consider another motor for turning, a bag motor and a planetary transmission perhaps?

A potentiometer is good enough for direction control but you should use encoders for the wheel speed. Or you can chain all the swerve modules together which gets kinda heavy and messy.

Do this in the off-season, build a proof-of-concept. Don’t try it for the first time during the build season.

  • what do you mean by 2 joy sticks?
    The way we program our swerve drive and the way i have seen every swerve programmed is an X-box controller with one stick driving the X and Y planes (forward side ways and back) and the other with the chassis orientation. Most of our members have played some video games and by having it in the same set up as the a first person shooter it makes getting use to much faster.

Mechanically i would like to see how you plan on using window motors to steer with out using a coaxle.

One more thing to watch for is the wires getting tangled up if you are not running a coaxle.

That is what I figured most teams were doing. I want this to be an integration with tank drive if at all possible, I would hate for our drivers to completely learn a new scheme of controls. However if the scheme that you described first seems to work I'll give it a try, I just wish there was a better method for rotation.

With this robot built in the off season our drivers will have plenty of time to practice. Thanks.

The window motor simply turns the bracket the wheel is mounted on, it’s a proven concept.
If the modules are limited to a rotation of 90 degrees I don’t see wire tangling being an issue.

Other thoughts:
In response to the xbox controller, I was thinking on using the analog triggers to control rotation.

Would handling rotation through the use of buttons (off of the cypress board) be a feasible control scheme? Or too hard to control?

I will take a video tonight when we have our robot our of the bag of how it drives under different controls. With the rotation on the second stick of the X-box controller you can use it to decide how fast you spin(spinning at full power is fun to watch but should never be needed). With fancy math (im not a programmer i just drive and check math) you can do circle strafing and intergreat the 2 sticks. You can pm me and i can get you in contact with our programmer about the algorithms and the set up better then i can.

If you plan on building a swerve its going to take time to get use to no matter what. You want your driver to be drive it like a swerve not like a tank drive. If you drive it like a tank drive then you are wasting a lot of resources.

We use the side bumpers on our controler to change where the center of rotation is. (the drive in its default state rotates in the dead center of the robot) We can change the center of rotation to any of the 4 corners so we can role out of a pushing match’s using the other robots force to get us up to speed faster. We have been writing code for about 8 months for the swerve’s and we have yet to do half the things we want.

Well, regardless of joystick control, switching from tank to swerve will take training and adjusting.

For these buttons, will they be just boolean inputs? I think that would be rather hard to control.

I haven’t tried it, but I guess triggers could work. I suppose it’s just a matter of driver preference
For me, I prefer an independent twisting controller to rotate.

Ooh, that’s pretty cool. Do you mind sharing how that works mathematically?

I honestly didn’t think of that, analog input would defiantly be to your advantage.

Ditto on the center of rotation thing, that’s awesome! It eliminates a lot of the problems with pushing matches with swerve drive.

I’ll take some time to respond to this properly later (swerve drive control is a passion of mine), but feel free to check out our swerve drive C++ code here. It’s 5 years in development.

2012 and 2013 used a steering wheel on analog input via cypress board. The Macys robot used a single joystick.
Feel free to borrow whatever code you want.

Hello, 2517 programmer here.

I made a presentation about the swerve mainly to show to judges, but it should work well enough here. It was meant to be accompanied by an oral presentation, so feel free to ask questions if things don’t make sense. I’m planning on adding more code specific examples later as well.

Here are all the links:

Presentation in pdf:

Presentation on google drive:

Our actual code, sorry it’s pretty messy at the moment:

Also, the center of rotation doesn’t even need to be inside the robot. For instance, we could set the center of rotation to be a goal. Then, with our control system, the x axis on the right stick would have the robot orbit the goal while continuing to face it.

This can be made to work, but realize you will not achieve “full” swerve motion.

With the 90 degree limitation, there will be maneuvers you will not be able to execute acceptably, especially using a (low power) window motor for steering.

Just to give one example, suppose you try to maneuver the robot while driving sideways. Since the wheels are all at or near their maximum allowing turning angle (90 degrees), every time you need the wheels to cross that 90 degree limit you have to turn them 180 degrees the other way and reverse the drive motor.

I would very much recommend using an xbox style controller setup like a first person shooter. It is very intuitive. Forward and strafe on one stick. Turn on the other.

We started with Bombsquad’s code with the intention of writing our own. It worked so good, we never bothered. The only thing we did was throw out their crazy steering wheel. (no offense)

I would also not recommend spending too much time on a field centric system. Use that time for driver practice, and you’ll have better results.

Here is our 2014 version of Bombsquad’s swerve code:

One last point when porting code from other robots: If your steering system just twitches like its having a seizure, the position feedback is probably inverted from the original robot.

Why not spend the time on field centric?
I would think that a robot centric swerve drive would be much harder to control.

In our (LabVIEW) code, it only took a few blocks to make it field centric. I stole the rotate vector block from the default holonomic drive code, used it to rotate the translational vector by the gyro reading, and that’s about it.
Well, I don’t know about C++, though

It’s not difficult, it’s just completely unreliable outside of the first few seconds of a match unless you reset the gyro at some point.

What we’ve settled on is “steering” as the default control and then switching to “crab” when we pull the trigger. Steering purely a robot-centric drive system.
We reset the gyro when the trigger is pulled, so any rotational input is based on the robot’s orientation at that point. What takes practice is that the crab x/y is based on the robot’s orientation at that point also.
(Hope that made sense).

Ah, I see what you’re saying. That’s a pretty cool system.
I guess you’re right about the gyro problems, we often reset it mid-match.

I highly recommend that you try field-centric control. It is generally very intuitive, and allows for some complicated maneuvers to be very easy. If you do implement field-centric code, I highly recommend using a filter between gyro and compass sensors. (so that there is no drifting problem)

Also, because your driver is going to have to learn something new anyway, make sure you put in all your code before your driver gets too much stick time. Our driver drove in robot space for quite a while before we added field code. Now he just keeps it in robot-centric mode.:smiley:

Hmm, how does this work with a compass? I’d love to get rid of gyro drifting

You also have to take into account the hits (especially this year). The hits can max out the gyro and cause you to lose your orientation.

Add an easily-accessed joystick button in your code that the driver can simply press to re-zero the gyro whenever the robot is physically in the correct orientation.