leonardthall's Posts (12)

Sort by

FPV Racing using Arducopter


Hi All,

This is intended to help people who are interested in using Arducopter for FPV Racing and/or mini quads.

Personally I started using Arducopter because I wanted to fly FPV and get aerial video of my 4wd trips. I also wanted the comfort of RTL and Loiter to get me out of trouble and help me learn. Arducopter's focus at the time was autonomous flight and I was told that we don't have time to focus on manual flight, other boards like the KK were for that stuff. My argument has always been that making Arducopter capable of aggressive manual flight provides the foundation of robust autonomous flight.

Three years later so much has changed. Arducopter is expected to handle the most serve weather conditions the hardware can fly in, while carrying out a way point mission with the grace of the most skilled pilot (I don't believe we are quiet there yet). This has come about by focusing on achieving the best control we understand is possible. This focus on the basics of control means that Arducopter is a very capable FPV and acrobatic controller.

There have been a number of advancements over the last three years that have taken us to this point.
1. Introduction of the Rate D term,
2. Earth frame to body frame conversion,
3. The Stability Patch,
4. IMU filtering understanding and improvements,
5. Our first stabilized ACRO http://diydrones.com/profiles/blogs/acro-for-ardupilot-3-1,
6. The Onion rewrite,
7. The post Onion ACRO rewrite,
8. Autotune,
9. Thrust linearisation and current limiting,

And on the immediate list of things to do

10. Conversion to Quaternion attitude controller,
11. One Shot support.

Some of the key people that have taken an active interest in ACRO and it's development over the last 3 years are Robert Lefebvre (responsible for the first stabilized ACRO algorithm), Randy Mackay, Jonathan Challinger, Paul Riseborough, Josh Welsh, Bob Doiron and many people I can't name who gave feedback and risked their copter testing ACRO.

So enough of the reminiscing about old times.

My role on the Development team focuses primarily on the control and navigation code in arducopter. While many people see Arducopter as targeted at larger copters and autonomous missions, I have found small powerful quads to be the best test platform for this development. Copters in the 250 to 300 size range not only crash well, there agility and power make them very sensitive to controller design and tuning. Further, the standards we aspire to, are reaching a level where the only way to properly test them is with FPV and a combination of on board video and logging. On top of all that, they make testing FUN :)

So this has been my primary test platform for the last 12ish months (after one of many hard landings):


Name: QAV 250
Weight: 624g
Motors: Baby Beast 2206 2150 kV
Battery: 1300 mAh, 3s
Props: HQProp 5x4.5 Bullnose
Power: 480 W
Current: 40A continuous and full throttle
Thrust: 1.68 kg Thrust at full throttle

My setup on the QAV is relativly low power compared to what some of the best pilots are flying so I decided to build something a little more extreem while ensuring I didn't need to continuously replace puffed batteries and burnt out ESC's and motors. I came up with this:


Name: My kids call it Willy for some reason (don't ask me!)
Weight: 940g
Motors: Sunny Sky 2208 2600 kV
Battery: 2200 mAh, 4s
Props: Gemfan 6x4.5, Gemfan 6x4 Bullnose, HQProp 6x4.5, APC 6x4E Speed, Quanum 6 x 4.5 Carbon (still experimenting)
Power: 1.4 kW continuous, 2 kW for short bursts
Current: 120 A continuous, 160 A for short bursts
Thrust: 4kg continuous, +6kg for short bursts
Has a custome 200A 4s power module based arround the ACS758ECB-200U-PFF-T.

Setting up an FPV racer


Vibration is a major issue on these copters. They tend to be small, light, stiff, operate at high speed and rpm, with relatively large surfaces under the props. This means that lots of vibration is created and it is directly transfered to the base of the autopilot. There are two main sources of vibration, the first is when the high pressure wave created by the prop hits the top of the arm. The second happens during fast forward flight. When the blade of the propeller travels forward into the airstream it creates significantly more lift than when it is traveling with the airstream. This causes a torque on the shaft of the motor twice for every time the propeller rotates. Both of my copters create enough vibration to cause clipping on the accelerometers at full throttle.

My personal rule is I don't add vibration dampening unless it is needed and most of the time it is caused by loose screws or overly flexible frames. While my QAV 250 doesn't experience enough clipping to need any special attention, Willy creates an amazing amount of high frequency clipping that can destroy our attitude estimation (the autopilot doesn't know what direction is up). The solution I use (thanks Paul) is four 11 mm squares of Latex Foam. The foam below doesn't come with tape so I add thin double sided tape to each side before I cut it into squares.

Vibration handling

Below is my vibration isolation in Willy, it is worth pointing out how I kept the cables away from the Pixhawk and ensured any cables connecting to the Pixhawk had a nice bend to minimize vibration transfer from the frame.


Another serious source of vibration is vertical slop in the motor bell. This means that as the motor rotates the magnetic force that rotates the bell also causes it to jump up and down against the thrust of the propeller. Without the propeller attached this sounds like sand in the bearings. You can easily feel this my moving the bell up and down with your hand. If you feel a small amount of movement or hear a tick every time you move the bell, then you need to adjust the bell on the shaft. I do this with a press I made with the help of Sneezy:


It is based on this device and some square steal tube.

If I find a problem motor I loosen off the grub screw and very carefully press the bell down over the shaft until I no longer detect any vertical movement of the bell.

ESC Setup

Larger copters don't require the fast response of Simon K and BLHeli and can result in sync loss or burnt motors or ESC's. It is especially important to ensure the ESC can handle not only the average current your motors draw but also the much higher peak currents caused by the aggressive response of the Simon K and BLHeli firmware. The only significant advantage these firmware provide large copters, especially lightly loaded, is active breaking.

For small FPV racers Simon K and BLHeli provide massive benefits. These copters have high powered motors and small propellers that are more an capable of taking advantage of the faster response time these firmware offer. There are three areas these firmware offer significant improvements.

The first is the removal or reduction of input filtering. This means that your commanded input to the ESC is directly passed to the motor without a slow ramp. The slow ramp up on standard ESC's keeps the peak currents from becoming too large and damaging the ESC and motor. That is why we need to make sure your ESC and motor can handle these short but high current spikes.

The second is active breaking. If you take your ESC and pump the throttle you will notice that the motor speed up much faster then they slow down. This is especially obvious on large props that are very lightly loaded because the drag on the propeller is very small and their momentum large, they don't tend to slow down quickly causing control and tuning problems. On small copters active breaking causes the motors to slow down almost as quickly as they speed up. The result is significantly more control torque on the air frame, provided with less delay.

The final improvement is One Shot (also an advantage of CAN bus ESC's). These ESC's speed up the communication between the autopilot and the ESC. The reduced latency makes it possible to have higher PID gains and tighter control. It is sort of like reading this blog post and being able to skip all the woffle to get to the good bits. :)

This is a screenshot of my BLHeli setup. You can see I have enabled Damped Light. This is the active breaking feature of BLHeli. Arducopter doesn't support One Shot yet but we are working towards that and I will let you know how this improves control when we get it going.


Center of Gravity (CG)

It is very important to get the CG right on any copter. The smaller the copter the more precise you should try to be. For a dedicated racing copter there it may be worth moving the CG slightly forward to counter what I understand is referred to as Propeller-Flapping-Torque. This is the tendency for the propellers to want to rotate away from the incoming airflow like an umbrella on a windy day. You can see the effects of this in forward flight by comparing the motor outputs. You will see that during fast forward flight the rear motors tend to have a higher setting than the front motors. A slightly forward CG can even up this imbalance and let you get the most power out of your motors.

The ideal CG changes based on exactly how you are using your copter. During tuning the CG should be as close to perfect as possible. For racing you may get small improvements by moving it forward. High powered racers that fly at 60 degrees pitch or more don't seem to experience as much Propeller-Flapping-Torque because the airflow is closer to 90 degrees to the propeller disk.

Camera Tilt and Field of View (FOV)

Until recently most copters didn't offer any significant camera tilt out of the box. As an FPV pilot I quickly realized that hovering, especially attempting to land, is the most difficult thing to do because of the limited field of view provided by the camera. As soon as I started moving forward my mind automatically fills in the world around me from the objects that I have recently passed by. For slow cruising around zero tilt is fine however as I started moving faster I found myself constantly looking at the ground. The obvious solution to this problem is tilting the camera back and making use of a camera with a large FOV.

As I started flying around object more confidently I started to shoot through holes and under trees. I needed to adjust for the wide FOV as I found that objects I thought I easily passed under would clip my rear props as they passed by with the annoying delay in fun. Unfortunately the larger FOV also limits the details I can see. This has caused a number of branches to suddenly appear in front of me in, what a second earlier, looked like a lovely open tunnel for me to fly through.

I am currently experimenting with 2.8 mm and 3.6 mm lenses on my FPV cameras and printed camera mounts at approximately 30 degrees. Fast forward flight is great but landing is very difficult because I get a view of nothing but sky. I have found the way to get around this is to come into landing by skimming along the ground then doing a turn to wash off speed while dropping the throttle to put me on the ground. However I am still experimenting to work out what I like and I am sure everybody will need to fine their own personal preference for the copter they fly.

Interesting Features of Arducopter

Now we get to the nuts and bolts but before I go too much further I would like to highlight the difference between FPV Acrobatics and FPV racing. FPV Acrobatics requires lightning fast roll and pitch rates combined with crisp yaw rates. FPV racing benefits from very controlled, smooth, turns with maximum stability. For this reason, maximum rates, acceleration and expo settings can be very different between the two. In general an FPV racer will be much easier for a beginner to fly than the same copter set up as an FPV Acrobatic quad.

Basic setup

There are a number of parameters that control how the copter will handle in ACRO.
ACRO_BAL_PITCH : Rate of pitch auto leveling in Trainer mode.
ACRO_BAL_ROLL : Rate of pitch auto leveling in Trainer mode.
ACRO_EXPO : applied to roll and pitch.
ACRO_RP_P : maximum rate of roll and pitch. It is multiplied by 45 to get degrees per second. Acrobatics will get as high as 20 while Racing will benefit from numbers like 6 or 8.
ACRO_TRAINER : This turns on angle limiting and self leveling. You can also set this using a ch7/8 switch. This is great for learning!!
ACRO_YAW_P : Like ACRO_RP_P, this defines the maximum yaw rate.
RC1_DZ, RC2_DZ, RC4_DZ : is the stick dead zone for Roll, Pitch, and Yaw. These are way too high for ACRO and need to be reduced to something like 5. Be careful though if you make them too small they may prevent Autotune from running because Autotune will think you are making a correction if the stick input exits this dead zone.
MOT_SPIN_ARMED : This should be set to a high enough value to ensure the motors are spinning assertively and can't be stalled easily. If you have an ESC that will reliably restart your motors after they are stalled then you can safely go a little lower. Make this too high and you reduce the usable thrust range, too low and you risk stalling a motor and crashing.
RATE_RLL_FILT_HZ, RATE_PIT_FILT_HZ, INS_GYRO_FILTER : These are the main filter setting used in the control loops of Arducopter. The smaller quads need more bandwidth and lower delays to achieve acceptable control-ability. I use a setting of 40 Hz on each of these filters, however, I suspect I may need to increase this to 80 Hz on roll for my high powered quad (Willy).

Thrust linearization setup

This is how Arducopter addresses the oscillation we see when we apply full throttle. There are two mechanisms that cause this oscillation.

The first is the small dead zone at the top of the ESC throttle range. This is somewhere between 7.5% and 2.5%. It is like driving an old car with play in the steering wheel. Once the controllers get into this region they don't get any response from the motors until they get large enough to get out of this range. The result is a fast oscillation from side to side. We remove this dead zone using the MOT_THST_MAX variable. By setting this to 0.95 we are instructing Arducopter to use only the first 95% of the ESC range.

The second is the tendency for propeller thrust to be proportional to the square of RPM and therefore ESC input (roughly speaking). This effectively increases the gain of the Rate loops as the throttle is increased. The increased gains can become unstable and cause oscillation. The thrust curve is approximated using the MOT_THST_EXPO parameter. This parameter changes for different propeller/ESC/battery combinations but for 5 to 6 inch props 0.65 is a good number.

The thrust is also dependent on your battery voltage and the gain of the Rate loops is adjusted to account for this. The parameters MOT_THST_BAT_MAX and MOT_THST_BAT_MIN defines the voltage range over which the algorithm will adjust the gain. I simply set these parameters to 4.2 x cell count and 3.3 x cell count.


So you have finished building your copter, done all the calibrations, and had a bit of fun flying it around. Now you want to tune it up to get the most out of the little beast.

I don't think I need to go into too much detail about how to do Autotune. I personally set ch7 to Autotune, AUTOTUNE_AXES to 1, 2 or 4 (I do each axis on a fresh battery), and AUTOTUNE_AGGR to 0.1 for roll, 0.05 for pitch and 0.1 for Yaw. I find that Roll and Yaw can benefit from a slightly more aggressive tune while Pitch doesn't need it. However, I suspect I can improve the performance of Roll using a more optimal tune (0.05) if I get the filter settings correct.

To ensure a good Autotune, make sure your CG is perfect, be patent and wait for a very calm day (or be willing to repeat it when you get a calm day), and always set the axis being tuned 90 degrees from the wind. The only other suggestion I can make here is if your copter starts to build up speed in one direction or another use a short stick input between twitches to bring the copter to a stop.

Input shaping

Input Shaping is the term used to describe the adjustments we make to the pilots input to ensure the copter is able to follow the pilots commands perfectly. This lets us have a copter that reacts to external disturbances very aggressively but feels very docile to fly. There are 4 parameters of interest here ATC_ACCEL_P_MAX, ATC_ACCEL_R_MAX, ATC_ACCEL_Y_MAX and RC_FEEL. The ACCEL parameters define the maximum rotation acceleration the copter will be asked to achieve while RC_FEEL softens the feel of STABILIZE mode. Autotune will make measurements during the tune and set ATC_ACCEL_P_MAX, ATC_ACCEL_R_MAX, ATC_ACCEL_Y_MAX. You may increase these if you have a very high powered copter however, at hover you may see a little bounce back because it is only able to achieve the full control authority when your throttle is high. For racing you may want to reduce these to make the copter more predictable in the turns.

Saturated Yaw Headroom

This is new for Arducopter, the parameter MOT_YAW_HEADROOM controls how Arducopter prioritizes Roll, Pitch and Yaw when the combined request exceeds the ESC range available. The Stability Patch manages how the Roll, Pitch, Yaw, and Throttle commands are passed to each ESC. When the demands exceed the available ESC range (saturation), Roll and Pitch are prioritized to ensure the copter can stay level (there is no point providing throttle if the copter is upside down). MOT_YAW_HEADROOM determines how much ESC range is made available to Yaw during saturation.

During high speed cornering the copter can stall some or all of the propellers. When this happens the Stability patch can become saturated as it attempts to keep the copter under control while the lift from each propeller is changing dramatically. During this time the copter can spin out though loss of yaw control or drop an arm excessively through loss of roll or pitch control. How the copter varies depends on the CG, speed, and pilot inputs. By adjusting the MOT_YAW_HEADROOM parameter the pilot can adjust the tendency of the copter to spin out vs drop a motor.

I find the fastest way to break into a sharp corner is by rolling the copter 90 degrees then pitching the copter up 90 degrees while looking at the apex of the corner. This creates a massive amount of turbulence but gets me accelerating out of the corner very quickly. I personally find that loss of yaw control is completely disorientating, while dropping a motor can be easily recovered provided my focus point doesn't leave the FOV of my camera. By adjusting MOT_YAW_HEADROOM I can equalize the moment experience in Roll, Pitch and Yaw during high speed hair pin maneuvers.

Current limiting

You may have noticed that many pilots are pushing batteries, ESCs, and motors way beyond their current ratings. This provides the pilots with small bursts of power, however, if this power is applied too long the heat builds up and the smoke forever leaves one component or another. The parameter MOT_CURR_MAX lets you set a maximum continuous current draw based on the specification of your equipment. If the current exceeds the desired maximum the throttle is reduced over 2 seconds until the current is back at safe levels.

And we are done

Well, I hope that is helpful. In the future I hope we see more small Arducopter boards. The development team is very focused on providing the best control we can squeeze from these sensors and we use these small copters as a primary development platform. Currently Arducopter isn't even on the list of FPV Racing Autopilots but I hope we can change that.

Finally I would like to share a situation that always gives me a little smile. When flying FPV with a few friends, there is always the occasional loss of video. This may be because the transmitter failed or because another pilot turned on their copter to the same frequency as mine. When this happens there is normally a panic as the pilot rips off their goggles shouting "I have lost my video", looking for their copter. Pilots on the ground pulling out batteries in case it is their transmission that have caused the problem. When this happens to me I say in a relaxed voice "I think you are on my channel" or "Oh crap, my video transmitter just gave out". I switch to loiter or RTL, I take my goggles off as my eyes adjust to the light. Well, the Arducopter pilots understand, but it is quiet novel for pilots of other systems :)

Read more…

Printed high speed AVC copter and crash

3689599934?profile=originalHi all,

I thought I would share the copter I hoped/hope to fly at ACV this year. I wanted to try to see what speeds I could get from a quad. I also thought it would be interesting to see what I could to with a 3d printer. I have access to a Makerbot 2x and I was also adding a heated bed to a friends printer. So based on the maximum dimensions of the Makerbot I designed the quad you see above and rendered below.


The quad consists of 4 arms with a semi aerodynamic cross section that is angled forward by 60 degrees. The round nose holds a tennis ball and the bottom swings open using a servo to drop the ball. The battery is held in the center of the frame and the 4 esc's are recessed into the side of the body to provide them with cooling without adding too much drag. The copter is held together using screws and nylock nuts that are pressed into the plastic.

I did some basic calculations to try to get an idea of what angle I was going to be able to sustain. My calculations suggested that I should be able to maintain 60 degrees if the air frame drag stops the copter from moving fast enough to reduce the lift of the props. I found I had to make some guesses about the air frame drag (I used coefficient of drag of a tennis ball as a starting point) and the area of the copter (I think this may have been a little low). In the end I concluded that without wind tunnel testing and a much better understanding of propeller aerodynamics I wasn't going to get too much out of the calculations.

What I did get was a reasonable estimate of the power I was going to need from each motor, 700 W total or 175 W per motor. This was well below the 285 W the NTM 28-26A 1200 kv motors are rated at. It also looks like it may be easier to get higher speeds as the weight of the copter increases. This is because the increased weight means the copter must hold a lower pitch angle at a given speed because of the increased lift required to stop the copter from loosing altitude. I limited my pitch angle to -60 degrees to ensure the copter didn't get too close to gimbal lock. The calculation of the airflow angle over the arms as speed increases and the copter pitches forward. What I found is the airflow becomes dominated y the forward airflow very quickly. In my case the airflow is only 3 degrees off the 60 degree angle of the arms at maximum speed.

3689599873?profile=originalSo I did an autotune and took the copter out to the local model club to see what I could do. I found the copter would accelerate very quickly and the frame was amazingly strong and ridged. While the flame wheel frame I tested the power train on would bend under full acceleration, the 3d printed frame was a rock. With the 45 degree maximum pids I couldn't take the throttle past about half way without climbing. So I checked over the logs for any obvious problems (other than the one I had) and increased the maximum angle to 60 degrees. I also found that I had to adjust the yaw pids to control the frame a high speeds because it wanted to turn the frame sideways to the airflow. This is a well known effect. Just shoot an arrow without feathers or fire a rocket without fins. I was able to adjust the yaw pids to keep the copter right where I wanted it in the following flight.

The following flight I was able to really wind it out. I was very happy with the performance of the copter. It wasn't getting up to the speeds I was hoping for but things were looking good. After about 3 minutes of high speed passes I saw a clear line of white smoke coming from the copter followed by...... unhappiness.

3689599997?profile=originalThe front left motor was burning hot and the smoke was the insulation on the winding's burning off. The logs showed that the front left motor was pegged during each high speed run and there was obviously a problem with it. The logs also showed maximum velocity of 107 km/h but it was happy sitting at 90 km/h even into a small head wind. The props / motor / battery combination would max out at 126 km/h on a normal plane.

So overall I was pretty happy with the performance. And I can say that a quad can be very effectively 3d printed provided the arms are designed to take advantage of the strengths of 3d printing. In this case each arm and body section attached to it was 70 g. The strength was high enough such that I couldn't break a arm by trying to bend it in my hands.

So now I need to work out if I can print a replacement before I fly to AVC. I need to print 6 parts, each taking approximately 12 hours. So each is an overnight print and I have 6 nights before I need to leave.... I may need to fly the Y6 :(

Things to remember. (this is a "note to self" but I thought I would share)

Always check the position of the bell on the motor shaft and adjust it to get the optimal location. This problem sounds like a bearing problem in flight. This is also a good time to ensure the grub screw is tightened properly.

After the first flight check the motor output of the autopilot at maximum throttle to see if any motor is consistently maxing out before others. This is the tell tail sign of a motor or esc problem and would have saved me here. I didn't look at this because all the motors were brand new.... bugger :)

Always check every screw and prop before the first flight. This is where little things can go wrong.

Yaw stability in a copter will take a big load of the yaw controller in a high speed copter.

Read more…

ACRO for ArduPilot 3.1


Hi all,

My motivation to get involved in the development team was to bring a good ACRO mode to ArduCopter. Three or four months ago Robert Lefebvre suggested that we could integrate the rate error and use it to correct the platform in the body frame. He went on to demonstrate this on Heli's. We have since learned that MultiWii use a similar approach and code was developed by Bob Dorion based on MultiWii and discussed here http://www.diydrones.com/forum/topics/flipping-arducopter.

I have taken Robert's approach and integrated it with the current ACRO trainer aids with the help of Robert and Bob. Here is the result:


This code is based on ArduCopter 3.01rc1 so if you haven't got this flying yet, don't bother with this code.


Replace Earth Frame ACRO with Body Frame ACRO

Reduce the dead band on the roll and pitch inputs

In the same way as you could before you can disable all trainer functions by setting

For my flight testing I have been using:

Things to discuss are:

Is the performance acceptable?

What additional features are needed? (switched trainer functions, zero throttle doesn't stop motors)

Is there a better algorithm?

Do you see any problems with the code?

How does the performance and feel compare with other systems? (please only comment if you have flown those systems and this system on a well set up copter, anything less is a waist of every bodies time)

I have spent at least 20 minutes doing nothing but flips and rolls of various combinations and mixtures and a similar amount of time doing yank and bank maneuvers. I have not found a problem or any bad habits.

I look forward to your feedback and ideas.

Read more…


Hi all,

I thought I would attempt to draw up a couple of diagrams of the PID loop in the ArduCopter 2.9 release.


Alt Hold Controller3689498721?profile=original

What we are trying to do with this controller is remove the need for the different stages of altitude changing that was in there before. This controller can handle both the altitude hold function as well as the fast altitude changes. We have tested it up to 5 m/s. This lets us do the very fast reduction in altitude I think you were asking for. It also does this with very little overshoot.

We use the square root of distance relationship to slow the airframe at reasonable accelerations to remove the very large accelerations that a linear distance vs velocity relationship applied. We took this one step further by combining the linear relation P loop with the square root relationship. This provides a smooth transition between the two modes in both acceleration and velocity.

The linear distance calculation is the distance that the square root relationship needs to be moved in order for the linear velocity relationship to be a tangent to the square root velocity relationship. This provides a step free transition between the two at the linear distance x 2. Acceleration of the two curves is also equal at this distance meaning that the motors don't pulse as we swap between the two curves.


The graph below is for the default Alt Hold parameters.

3689498850?profile=originalThe 250 cm/s/s is the maximum acceleration that will be required of the copter while still allowing the copter to stop without overshoot. The copter will not reach these accelerations unless it is instructed to travel over approximately 125 cm/s. This shouldn't happen during Alt Hold but can happen during Altitude changes. This limit was chosen because it should be achievable for all reasonably designed copters. To not be capable of this acceleration the copter would have a cruise throttle of over 700.

Using this controller you can still move the requested altitude slowly however if we need to stop or change direction it is able to still follow that request. In fact, the controller is not limited in the acceleration it can ask for. In an emergency this controller will be able to do it in less than 1 second and 2.5m. (I realize these are simple calculations and this situation only occurs if the user asks for stupid things).

We now have different speed limits for up and down but currently they are set to the same thing. We did this because the controller can now handle much faster rates so we didn't think we needed to limit it to such small values going down. I assume this was done for safety.

The final thing I should mention is the design of the controller with respect to the pid loops. This is a (P/sqrt) -> PD -> PI (Position -> Velocity -> Acceleration) controller by default. However, there may be advantages to using (P/sqrt) -> PD -> PID with correct filtering.

 So why no I term in position. This is because the I terms in these loops will reduce the following error when using this controller with a moving set point. The current design of the controller ensures that the distance between the moving altitude request and the current altitude is enough for the controller to stop the aircraft in that distance without accelerating beyond 250 cm/s/s. This is how we achieve such a small overshoot from very fast decent rates. This is also why we don't use an I term in the Velocity controller, we don't want overshoots due to I term build up.

The other parameter that is critical in this function is the velocity D term. This has the effect of minimizing the error between the requested velocity and the desired velocity during deceleration. This is set as large as it can be without noticing any jerkiness or oscillation during altitude changes.


I hope this helps people understand how a number of these control loops work.



Read more…

New Throttle PID Idea


Hi All,

I have been thinking about the way we have implemented our throttle and the performance issues that we have observed. First of all I would like to say that I get great altitude hold. I can cruise around at 1 or 2 meters above the ground with no problems. It is only when I start to get aggressive with my pitch, roll and speed that I start to see areas that we could improve. So I started thinking about how we are doing things and why this might cause us problems.

So the problems I see are:

  1. The pwm input to the esc is not linear with respect to the lifting force generated by the motors. Randy improved this by adding a throttle curve, however this can only be truly accurate for a particular combination of esc, motor, and propeller AT HOVER. When we start to climb, descend or move forward, the curve changes and we are back to a non linear response.
  2. Boost throttle compensates for the angle that the copter is compared to the ground. But how much do we compensate? We don’t know because of point 1. We know what force we need but not how this translates to pwm. Hang on...... Force.... Acceleration.....

So I got thinking about how we could ensure we could get the correct acceleration from the props for any given situation. Then I thought we have a sensor to measure that!!! Why don’t we put the Z accelerometer in a pid loop to directly measure and calibrate the lifting force supplied by the motors and propellers. The Pid loop design I started thinking about is shown above and compared to our current design at the top of the figure.

This has a number of advantages over the current system:

  1. The last pid loop, running at 100 Hz, takes an acceleration request then uses the z-axis accelerometer to vary the motor pwm until the required acceleration is achieved.
  2. The last pid loop linearises the rest of the system making analysis and tuning simpler.
  3. The frame translation takes care of the angle boost function automatically.
  4. When at hover or in fast forward flight changes in pitch will cause much smaller variations in altitude because the last pid loop will be working to ensure the vertical acceleration (in the earth frame) will stay as close to 9.9g as possible. We no longer are waiting to detect a change in altitude, we are reacting when we feel that we are accelerating at the very beginning of the unwanted movement.
  5. This should also improve the rise on yaw problem. As the yaw command is entered we experience a positive acceleration body frame z axis. The final control loop should sense this very quickly and reduce the throttle to bring it back to 9.8G.

There are a number of problems we may also need to solve:

  1. The z accelerometer will have noise that may need to be filtered. A moving average filter is the best choice for this because it give the greatest noise reduction with the fastest step response. This filter will be one of the biggest contributors to the delay in the throttle control.
  2. When at rest on the ground the copter will experience an acceleration in the vertical direction of 9.8G provided the motors are going slower than that required to lift off. How do we ensure that the copter provides the user with the appropriate feedback to let them know that they are near hover or not? How does the user know when the copter is about to lift off? This could be a problem because the integrator could wind the motors down to minimum throttle. This may not increase until the requested G increases above 9.8 and then it could increase very quickly to make the copter take off as requested. I believe that these effects could be minimized by sensible selection of Imax in the final loop but only experience will say.

Ok, so that pretty much sums up my idea. I would really appreciate any feedback that people can give. Has this been tried before? Does anybody know if this is being done in other systems?

Thanks for taking the time to read this far,


Read more…

3689478184?profile=originalI lost this post so I have attempted to reconstruct what I can of everybody’s replies. I think I did ok in the end. I continued my discussion of the topic here:


Hi all,

I wanted to do a post on this for a while now but it is hard to separate the Yaw issues I want to talk about from a number of other issues regarding the interaction between Roll, Pitch, Yaw, and Throttle.

I will attempt to focus on a couple of issues I would like to point out:

  1. Default Yaw PID’s parameters and/or Yaw PID loop design could be improved.
  2. ESC linearization can only be partially implemented and doesn’t necessarily fix the altitude variation problem. This is because we always have the non-linearity below 0% and above 100%. And Yaw is very capable of pushing the outputs into these areas.
  3. Maximum motor limits in the MotorMatrix library are only effective for the HEX configuration. Quad’s and Octo’s experience a Yaw when the maximum outputs are limited because “opposite” motors are spinning in  the same direction.
  4. Maybe we can improve the way we handle Maximum and Minimum motor outputs. This is a complex problem and I am only starting to get it clear in my head.

In this Blog Post I will focus on point 1 because I have run out of time.

A quick summary of what everybody knows

Roll and Pitch are controlled by using the lifting force generated by each propeller to create a toque on the airframe and rotate the airframe in a given direction. Yaw on the other hand uses the drag of each propeller to rotate the airframe about its vertical axis. To rotate clockwise, the counter clockwise propellers are speed up, increasing the drag, while the clockwise propellers are slowed, decreasing the drag. The difference between the clockwise and counter clockwise drag, and therefore toques, on the propellers causes the rotation of the airframe. So basically, Roll and Pitch are controlled using the force that propellers are designed to do well while Yaw is controlled by the toque that the propellers are designed to minimise. This is why multi-rotors have poor yaw authority.

Sudden Full Yaw Input

If a sudden yaw input is applied to the PID’s using the default PID parameters results in 4500 x 7 x 0.25 = 7875. This is 1.75 times the maximum Yaw Rate Output. This is particularly significant because an output of 4500 is enough change the ESC output by 100%. (Correct me if I am wrong there). So basically Yaw input has much stronger control over the propeller RPM than any other control with the exception of manual Throttle… Maybe (There is a Max Throttle variable).

My impression is that the default YAW PID parameters and PID loops have been chosen to compensate for the lack of yaw authority at the expense of Roll, Pitch, and Throttle/Altitude control. I believe that this is a problem since Yaw is the least important control. In fact we have modes setup to control the copter while it is spinning in the Yaw axes.

My Suggestions

This is difficult because there is a real compromise between Yaw control and control in Pitch, Roll, and Altitude/Throttle. How we juggle these issues depends on our priorities. If our priority is an easy to fly and tune system then I would suggest a number of things we could do to potentially improve things:

  1. Reduce default STB_YAW_P parameter.
  2. Multiply the Stick input by ACRO_P instead of STB_YAW_P to calculate the desired rate. Keep STB_YAW_P for its named purpose, stabilising the yaw heading.
  3. Reduce the Rate output limit to something like 2250.
  4. If the user wishes to increase Yaw authority they could be encouraged to increase the angle of the propellers up to 10 degrees. It is suggested that up to 3 degrees should be included in large Octo’s.

Here the link to the starship enterprise copter with the angled props.




Thanks for taking the time to read this.


Nick Mann:

Thanks for that. Interesting thoughts. 





        Great post and very timely as I'm looking at a couple of these area.  Suggestions #1 and #2 look fairly straight forward to implement so no problems there.


        I'm very interested in your thoughts on a better "stability patch".  Jason and I were discussing this a few weeks ago about how to improve it.  As you say, simply reducing the opposite motor is probably not the optimal soluiton.  I was thinking that in the AP_MotorsMatrix library when we're doing the mixing we should remember the roll, pitch yaw and throttle contribution for each motor..then when it comes to doing the stability patch we review those motors that have gone over 100% (or under 0%) and then look at the make-up of what caused them to go over.  So say it's got a big +ve yaw component to the number..well, we can remove that surplus and then go around to the other motors and take away an equivalent -ve yaw.  That might all come from one motor or it might be from a few different motors.


         Generally I think we all agree that we should prioritise control so that #1 maintain altitude, #2 roll+pitch, #3 yaw.  So yaw is the first to be sacrificed if necessary.  That's perhaps not quite true though if you're talking about maintaining a roll/pitch of 45deg at the expense of yaw..in those cases you'd probably prefer to give up some roll/pitch.  So maybe there's some minimum stability which must be maintained and then beyond that it's a luxury and is open to be sacrificed.



Hi Randy,


    I agree, 1 and 2 are the easiest and most sensible way to address most of this problem.I should have put them in the opposite order though. I think we should multiply the stick input by ACRO_P because that is what ACRO_P was intended to be used for (Ok, I am guessing here). This would then leave STB_YAW_P to be tuned for best PID performance (We don't even have to change that then).


    In the current setup, full stick movement, from a stationary level copter, requests 315 degrees per second from the Yaw rate PID. Using ACRO_P will reduce that to 202.5 degrees per second. To put this in perspective, the maximum rate that the stabilised Rate PID's request from a level position is is 202.5 degrees per second, (default acro mode is 180 or 202.5 degrees per second depending if AXIS_ENABLE is set or not).


    Now to translate these figures to the peek commanded to the motors in a + configuration. Max Yaw will command plus or minus 100% (limited from 175% out of the Rate PID) from the motors. Considering that many copters will hover between 30% and 50% throttle, this is massive.


    In comparison the roll or pitch will request a maximum of 78% is Stabilise and 70% in Acro mode with AXIS_ENABLE set. These numbers drop to 55% and 50% for a copter in the x configuration because of the 1/root(2) factor. On top of this, because roll and pitch are so directly effected by the lifting force of the propellers, the rate will increase very quickly reducing these numbers substantially.


    So while it will be very difficult to make roll and pitch reach the output rate limit (and if it does it will be very brief), Yaw can increase to almost double the output limit quiet easily (and because the input into this limiter can easily reach double, it can last for a relatively long time).



Ok, a lot to digest here and I haven't done that completely but a few bits from me in any case..


Propeller lifting force is approximately proportional to the RPM squared. So if a copter will hover at 50% throttle then it will have approximately 4 times it's lifting capacity in reserve, so lets say that in the real world we have 2 times in reserve.


I didn't know this so thanks for the info.  Although we don't get to control the RPM of the motors but rather just provide a PWM...I've plotted the pwm vs thrust curves for a number of motor + esc combinations and although the curve does get steeper as the throttle goes up I'm not seeing quite as much variation as I'd expect from the above...maybe there's some scaling going on inside the ESC, or maybe the rpm between min throttle and max throttle is actually not that different and so I'm only seeing a small part of the curve so the thrust = rpm^2 bit is not obvious.  I'll get a tachometer.


Ok, fair enough on prioritising the axis as: #1/#2 roll+pitch, #3 throttle, #4 yaw.


What Leonard wrote below is similar to the solution I like best but I don't think that roll/pitch should always overwhelm yaw control in all situations. For example, I think it's much better to abandon a request from an autopilot for a 45 degree pitch forward in favour of maintaining yaw.


Other solutions do away with opposite motors all together and instead reduce multiple motors that combine to create an opposite. The idea is to minimise the amount that any motor has to be reduced and therefore keep a motors in a similar part of their throttle curve. (minimise the impact of throttle curve on PID gain being different from motor to motor). However this approach will still reduce all motors equally on a quad since this is the only solution to the problem without inducing a yaw, pitch or roll.


Anyway, sounds like we're at the point where we need to try out some of these ideas...



Leonard, good analysis.  As Randy said, we were talking about this recently.


An overpowered quad is the worst case scenario.  This is because they hover at 20-30% throttle which means they have less control room before one of the motors hits 0%.  The more overpowered you are, the worse it is.  This was demonstrated by the disagreement between Jason and I about my yaw control changes that were in 2.7.1-ish.  My quad flew well with them, but he found it was causing pitch/roll problems.  This is because if he input a yaw command, even a gentle one, it was shutting down one of the motors causing loss of attitude control.


However on my quad which is moderately powered, hovers around 50-60%, I had no problem, because I had much more room to move before hitting a limit.


Quads without tilted motors makes the situation that much worse, and of course the 3DR Quad kit has no tilt because it's a flat boom design.


You say that Octos have a problem as well, but I think less so.  Reason is, an octo should be able to shut down all the CW or CCW rotating motors and still have attitude control because the remaining CCW or CW rotating motors are still layed out in an X configuration.


But your point about the hexas being the best case is probably true.  It's also a better arrangement for motor redundancy because the opposite motor turns in the reverse direction, simply shutting down two opposite motors causes no loss of control.  (This is why I've also thought about building a decacopter).


Now, did you notice in the motors library, some part of code called "Tridge's Stability Patch"?  This does look at which motors are "clipping" on the high side, and reducing negative control on the opposite motor to match.  The problem is it does not work on the low side clipping.


Anyway, I'm going to cut and paste in here something I wrote on the devlist about this issue.

So what we discussed is the possibility of

Sorry I don't have any more.



Coming out of the discussion about the yaw contribution patch, and how it affected the performance of "overpowered" quads, I'd like to put some collaborative effort into rethinking how this is done.  Currently, this is done in the function AP_MotorsMatrix::output_armed() in AP_MotorsMatrix.cpe.  It's a large function, and is pretty much the last step in calculating the actual motor output.  I'll step through it piece by piece:


This part here constrains the throttle controller output obviously, keeping it between 0 and whatever the _max_throttle parameter is.  This is to avoid having the throttle controller overpower the yaw, pitch and roll controllers, allowing them some headroom to work.  This is based on the fact that _max_throttle is typically 80 or 90%, leaving 10-20% headroom where the attitude controllers can do their job.

// Throttle is 0 to 1000 only

_rc_throttle->servo_out = constrain(_rc_throttle->servo_out, 0, _max_throttle);


This part set the minimum throttle output to _min_throttle whenever the throttle is above the bottom. 

if(_rc_throttle->servo_out > 0)

out_min = _rc_throttle->radio_min + _min_throttle;


I haven't back-checked this part, but I assume it is causing all of the controller objects to calculate PWM ranges between 1000-2000.  I think the comment should read: "capture desired roll, pitch, yaw and throttle from attitude controllers" since these values obviously don't come from the Rx directly, but from the attitude controller.

// capture desired roll, pitch, yaw and throttle from receiver






This part here has the remnants of the yaw_contribution patch.  The idea was that in order to stop copter rising during yaw, we should slow down some motors more than we speed up the others.  The problem in case you missed the other email about this, is that the effect of this can cause the output of this bit to hit min_throttle, which "clips" the output of the controller.  Basically the yaw_contribution can clobber the ability of the pitch and roll controllers to do anything.  This isn't much of a problem on "underpowered" quads (50-60% throttle to hover) since they operate well above throttle_min. But overpowered quads which only require 20-30% throttle to hover, it doesn't take much yaw_contribution before you start hitting throttle_min.  Once one or more of the motors are on throttle_min, you start to lose stability.

// mix roll, pitch, yaw, throttle into output for each motor

for( i=0; i<AP_MOTORS_MAX_NUM_MOTORS; i++ ) {

if( motor_enabled[i] ) {

/*yaw_contribution = _rc_yaw->pwm_out*_yaw_factor[i];

if (yaw_contribution > 0 ){

yaw_contribution *= 0.7;


yaw_contribution *= 1.42;


motor_out[i] = _rc_throttle->radio_out +

_rc_roll->pwm_out * _roll_factor[i] +

_rc_pitch->pwm_out * _pitch_factor[i] +





The stability patch is doing something similar to what I want to do, but it operates on the high side rather than the low throttle settings.  If any given motor has an output greater than out_max, it sets that output to out_max, and then subtracts the amount that it is "clipping" from the opposite motor. 

// stability patch

for( i=0; i<AP_MOTORS_MAX_NUM_MOTORS; i++ ) {

if( motor_enabled[i] && motor_out[i] > out_max ) {

if( opposite_motor[i] != AP_MOTORS_MATRIX_MOTOR_UNDEFINED ) {

motor_out[opposite_motor[i]] -= motor_out[i] - out_max;


motor_out[i] = out_max;




Then we have this part, which simply makes sure all the motors are above min.  This is where the trouble occurs with the yaw_contribution, or really any yaw control.  If any given motor is below out_min (aka: min_throttle) then set it to out_min.  So the problem is, if you have a strong yaw control, it can reduce one motor of a quad below out_min, which is then clipped and set to out_min.  But the opposite motor does not suffer this.  The result is the quad will have a pitch/roll movement about the axis perpendicular to the affected axis.  ie: if the yawcontroller output causes motor 1 to go below out_min, then the quad will wobble about the 2-4 axis. 

// ensure motors are not below the minimum

for( i=0; i<AP_MOTORS_MAX_NUM_MOTORS; i++ ) {

if( motor_enabled[i] ) {

motor_out[i] = max(motor_out[i], out_min);




This is the part that needs to be fixed.



So now to discuss what to do about this.


The first thing that must be decided is: Do we want to completely throw out Yaw stabilization if that yaw stabilization causes an instability in pitch/roll? I think the answer is yes. But I'm afraid if we do that, we'll have more complaints about lack of yaw authority. The problem is, I think, simply a case that people with powerful motors are operating too close to the out_min. One solution to that is to lower out_min, and give more room for the stability controllers to work. I think throttle_min might be something like 10-20% by default? Is there a reason we don't recommend going lower, like 5%, or maybe even less? I would think we could go almost as low as possible without having the ESC's actually shut-down?


I bet all of this also has a lot to do with the instability in the quads during descent.


Anyway, so what I'm thinking is something like this. Basically, I'm moving all the yaw controller stuff below the pitch/roll stuff. And I'm constraining the yaw controller PWM to a range which is constrained by how far above the min_throttle we are. If the throttle is low, we cut the yaw controller output to preserve the pitch/roll stability.


// output_armed - sends commands to the motors

void AP_MotorsMatrix::output_armed()


int8_t i;

int16_t out_min = _rc_throttle->radio_min;

int16_t out_max = _rc_throttle->radio_max;

int16_t yaw_contribution = 0;

int16_t lowest_output = 2000;


// Throttle is 0 to 1000 only

_rc_throttle->servo_out = constrain(_rc_throttle->servo_out, 0, _max_throttle);


if(_rc_throttle->servo_out > 0)

out_min = _rc_throttle->radio_min + _min_throttle;


// capture desired roll, pitch, yaw and throttle from receiver






// mix roll, pitch, yaw, throttle into output for each motor

for( i=0; i<AP_MOTORS_MAX_NUM_MOTORS; i++ ) {

if( motor_enabled[i] ) {

motor_out[i] = _rc_throttle->radio_out +

_rc_roll->pwm_out * _roll_factor[i] +

_rc_pitch->pwm_out * _pitch_factor[i];




// stability patch

for( i=0; i<AP_MOTORS_MAX_NUM_MOTORS; i++ ) {

if( motor_enabled[i] && motor_out[i] > out_max ) {

if( opposite_motor[i] != AP_MOTORS_MATRIX_MOTOR_UNDEFINED ) {

motor_out[opposite_motor[i]] -= motor_out[i] - out_max;


motor_out[i] = out_max;




// ensure motors are not below the minimum

for( i=0; i<AP_MOTORS_MAX_NUM_MOTORS; i++ ) {

if( motor_enabled[i] ) {

motor_out[i] = max(motor_out[i], out_min);



if( motor_out[i] < lowest_motor ){

lowest_motor = motor_out[i];




// constrain yaw controller output to priorities roll/pitch control

_rc_yaw->pwm_out = constrain(_rc_yaw->pwm_out, 1500 - lowest_motor, 1500 + lowest_motor);


// add yaw controller contribution

for( i=0; i<AP_MOTORS_MAX_NUM_MOTORS; i++ ) {

if( motor_enabled[i] ) {

yaw_contribution = _rc_yaw->pwm_out*_yaw_factor[i];

if (yaw_contribution > 0 ){

yaw_contribution *= 0.7;


yaw_contribution *= 1.42;


motor_out[i] += _rc_yaw->pwm_out * _yaw_factor[i];





// if we are not sending a throttle output, we cut the motors

if(_rc_throttle->servo_out == 0){

for( i=0; i<AP_MOTORS_MAX_NUM_MOTORS; i++ ) {

if( motor_enabled[i] ) {

motor_out[i] = _rc_throttle->radio_min;






// send output to each motor

for( i=0; i<AP_MOTORS_MAX_NUM_MOTORS; i++ ) {

if( motor_enabled[i] ) {

_rc->OutputCh(_motor_to_channel_map[i], motor_out[i]);




// InstantPWM

if( _speed_hz == AP_MOTORS_SPEED_INSTANT_PWM ) {

if( instant_pwm_force01 )


if( instant_pwm_force23 )


if( instant_pwm_force67 )






Sorry the formatting didn't come through, hopefully you can understand what I'm saying.


Also note this isn't finished working code, just kind of a back-of-the-envelope sketch.




I haven't read through everything thoroughly, but I think you're right Randy.  I would be better to sacrifice a high attitude request (45° pitch) if you have to to keep the copter yawed properly.  But if the request is to hold the quad level, then that should get priority over yaw.



Huge amount of knowledge here. Still analyzing in my head what I've just read.

This all match to my observations with my quad of having "random" yaws when playing with pitch/roll or trying to avoid the ground with max throttle stick for a while. And because of having GoPro attached to my quad and that unpredictable yaw heading it's almost impossible to know where camera is looking at the moment and record what I want. Also, when flying away when I'm unable to recognize white vs red arms to determine front of the quad, only "simple" mode is usable.

I was watching great movies of copters flights and always was curious "what did I wrong" to not be able to fly various paths and head properly.
I'm still learning about all those PIDs in ArduCopter and not ready to add my 3 cents on that subject.
Fingers crossed for some great conclusions.



Hi all, Thanks for taking the time to read all this.

When I look at throttle curves what I see is a general RPM^2 characteristic with a fall off or saturation at the high end. I think that this is probably a combination of efficiency going down and the ESC running out of legs at the top end. It may also have something to do with the drag characteristics of the antenna as well.

But basically my understanding is that ESC's basically control the average voltage being applied to the motor (for the purposes of RPM calculation), using pulse width modulation of the driving fets. RPM is approximately proportional to voltage input. Then we should get an approximate propeller force = (ESC input pwm)^2. At least below the peak efficiency of the motor (assuming the ESC is up to the task).

But then all the real life effects start messing with us........

But lets just assume that the pwm to force is X^2 relationship around hover at least.

We get a curve like this:


This graph is computer by comparing the upper and lower Yaw commands we need to give to maintain hover. The Blue line is the ratio that you are suggesting, 0.7/1.42, while the purple is the ratio required to maintain hover or constant vertical force. So based on this idealised model, the ratio you have currently is about right when we are reducing half the motors to near zero.

Sorry, I have to go to a doctors appointment but I will be back to give the equations for the above curves and add the excel sheet.



Ok, the maths.

x = throttle RPM at hover with no control input

y = the reduction in RPM in the slowing motors

z = the increase in RPM of the increasing motors.

Total Lift = 4*x^2 (for a quad without the lift multiplier)

When yawing Total lift is = 2*(x-y)^2 + 2*(x+z)^2

if we want to maintain the same total lift force during yaw
4*x^2 = 2*(x-y)^2 + 2*(x+z)^2
4*x^2 =2*x^2 + 2*y^2 - 4*x*y + 2*x^2 + 2*z^2 + 4*x*z
2*x^2 =x^2 + y^2 - 2*x*y + x^2 + z^2 + 2*x*z
2*x^2 =2*x^2 + y^2 - 2*x*y + z^2 + 2*x*z
0 = y^2 - 2*x*y + z^2 + 2*x*z

Ok, so we have this equation

z^2 + 2*x*z + y^2 - 2*x*y = 0

and we want to calculate what z needs to be.

z = (-2x + sqrt(4*x^2 - 4*(y^2 + 2*x*y)))/2 (we only need the positive root)

z = -x + sqrt(x^2 - y^2 +2*x*y)

So the long and the short of this is that when making small yaw inputs we need a 1 to 1 ratio of increasing and decreasing throttle. When we are applying the maximum possible yaw toque y = x (half the motors are stopped)

z = -x + sqrt(x^2 - x^2 +2*x*x)

z = -x + sqrt(2*x^2)

z = -x + x*sqrt(2)

z = x*(sqrt(2)-1)

z ~ x*0.414




Is it better (or even possible) to to sacrifice a high attitude request (45° pitch) if you have to to keep the copter yawed properly?

First up, I agree with the sentiment, I just aren't sure if this is what we want to try to do......

If we are ascending or descending (motors near a limit) with no requested attitude change then the PID loops are simply attempting to maintain the current attitude. Therefore Roll, Pitch, and Yaw inputs will be relatively small.

A number of things could disturb this state:

1. Roll, Pitch, or Yaw input. PID's translate this to the equivalent Rate request.

2. Turbulence or some other force cause a rotation in a number of axis. Attitude error feedback is translated again to the equivalent Rate request.

I think both are important but 1 will happen more often and with larger deviations.

My opinions follow, not facts:

1. If a yaw input is applied then I believe it shouldn't be allowed to impact the roll and pitch loops in any way. This is not too bad because the strong control of the copter in the roll and pitch axis means that the motor RPM deviations from average should be small. Ok, that is easy to say but what about the other way round.

2. If a roll or pitch input is applied I want to see that Yaw still has enough authority to maintain a heading but only just. This is because Yaw will very quickly increase the average lifting force of the motors if we want the same authority of a helicopter or tricopter. So this means we need to allow a certain throttle increase if Yaw needs it, but we want to keep it small because we want to come down.

3. What if we are manoeuvring in all axis. Ok, any strong input in Roll, Pitch or Yaw will reduce our rate of decent because of the RPM^2 tendency. However if we are using the above approach then we will get quick solid response from roll and pitch and a mushy yaw response. The important point is to make sure that we allow Yaw access enough pwm output to keep a heading and weakly adjust heading.

4. As soon as the throttle setting is increased to give a bit of room between the throttle setting and the minimum output then Yaw authority will return (at lease return as much as it can in a quad).

Ok so what happens if we are descending with near minimum throttle in Stabilise mode and we want to go from horizontal to a 45 degree pitch forward. Using the rational described above the pitch will change very quickly (less than a second in my quad), we will momentarily increase the total lifting force being applied to the copter de-accelerating the decent during the manurer. During this... lets say second, the output that yaw is allowed to exert is at it's minimum limit. This means that the copter will have very limited ability to accelerate in Yaw during this second but enough to maintain it's current state. Ok, I am happy with the performance the way I describe it so far. What happens after this maneuver though? The copter now has angle boost plus minimum throttle, increasing the headroom that Yaw can use (a 45 degree angle increased the throttle (g.throttle_cruise + 80) / 0.75).

Code Here:


So while a maneuver in roll or pitch away from flat hover, will reduce Yaw control to the minimum needed to maintain a heading for the short period of time, after the maneuver the Yaw authority will be increased (and I don't think people will even notice). However, if the roll or pitch maneuver is back to level there will be less Yaw authority afterwards but who cares, if I let go of the sticks in Stabilise mode I want my copter to go back to level, I don't care if I can't Yaw for a second.

Ok as for point 2.

We are descending and clip a branch. The copter tumbles, we crap ourselves, we don't increase throttle because we don't want to see it accelerate into the ground. Please PID's save me!!!!!

This is a simple one. Get me level then worry about Yaw. We probably have some angle boost helping us for most of the time as the copter attempts to right it's self so that will help but Yaw just isn't on the priority list in this situation at all.

Ok so to answer the question, No I don't think we should reduce roll or pitch authority to get better yaw when near throttle minimum (although I would allow more headroom for Yaw near Throttle maximum). In Stabilise the increased roll and pitch angle will actually increase Yaw authority due to angle boost.



Just a quick note. I hope these replies don't come across as condescending or "know it all" in any way. I am simply trying to put as much detail into my replies as I can to ensure that my thoughts are coming across clearly.

I am also making a real effort to make the most out of the feedback of the DEV team because I realise that you all have been playing with this stuff for a long time now and have a wealth of practical experience with the APM2 on a variety of airframes that I don't have.

As for the post above, I didn't address the (or even possible) part of the question. I was wondering how we would do this quickly (processor clock cycles) without strongly disrupting the roll and pitch PID's. I don't really have an answer to that part of the question......

I will see if I can find some references for where I got the RPM^2 thing.

Read more…


Hi all, it appears that my blog post “Yaw Control, ESC Linearization, and Hover” has been lost. I hope that it will be saveable but I am not holding my breath. If it can’t be saved I will attempt to reconstruct it but while I have most people’s replies on my emails but I don’t have my own. If anybody has a copy of my replies I would be very grateful if you could send them to me.

The discussion that followed that blog post focused on the "stability patch" in AP_MotorsMatrix.cpp.

Both myself and R_Lefebvre attempted to explain this in detail in the blog post above so I won’t do it again now in a hope that we will get that work back (fingers crossed). But I will attempt to summarise the issues that we would like to address.

  1. Near maximum and minimum throttle the control is compromised because we can’t decrease propeller lift much further at minimum throttle or increase it much further maximum throttle.
  2. When multiple Roll, Pitch, and Yaw manoeuvres are happening, how do we combine these with the requested Throttle setting to maintain stability.
  3. Yaw control is very limited in most of the multi rotor geometries and therefore results in large RPM variation in motors compared to Roll and Pitch to create an equivalent Yaw response. The lift force generated tends to be non-linear creating an increase in lifting force when Yaw is applied. How can we correct this behaviour?

While addressing these points we need to ensure that:

  1. We maintain stability and preferably good control over Roll, Pitch, and Yaw.
  2. Throttle response and altitude control is not compromised any more than absolutely necessary.
  3. That we don’t do anything that can prevent an overpowered multi rotor from coming down!


Yaw Curve

Ok, easy bit first.

Yaw is achieved by increasing the RPM of half the motors and decreasing it in the other half of the motors. However, because the lift of a given propeller tends to increase by the square of the change in RPM, this results in an increased total lifting force.

Reference is page 16 here: http://dc-rc.org/pdf/Model%20Propellers%20Article.pdf

So what we want to do is increase the RPM of half the motors less than we decrease the RPM of the other half and keep it the same as when all motors are at the same RPM.

Ok, some maths.

x = RPM of all motors at stationary hover.

y = RPM reduction of half the motors during Yaw.

z = RPM increase of half the motors during Yaw.

Total lifting force at hover for a quad is:

Total Force = 4*x^2

When inducing a Yaw it is:

Total Force = 2*(x - y)^2 + 2*(x + z)^2

We want these two equations to be equal if we don’t want the quad to start accelerating vertically therefore:

4*x^2 = 2*(x - y)^2 + 2*(x + z)^2

2*x^2 = (x - y)^2 + (x + z)^2

2*x^2 = x^2 + y^2 -2*x*y + x^2 + z^2 + 2*x*z

2*x^2 = 2*x^2 + y^2 -2*x*y + z^2 + 2*x*z

0 = y^2 -2*x*y + z^2 + 2*x*z

0 = z^2 + 2*x*z + y^2 -2*x*y

if we solve this for z we get:

z = -x + sqrt(x^2 – y^2 + 2*x*y)

If we plot this we get:


 The excel file I used is here if you would like to play with it.


The current ratio line is the ratio we are currently considering using, ie 0.7 up and 1.42 down. As you can see, the ratio starts off 1:1 then reduces to sqrt(2)-1 or 0.414. We could get pretty close to the ideal line using a straight line approximation:

z = 1 - (2-SQRT(2)) * x/y

This will give us a small increase in lift half way along but it is pretty close. Looking at the added complexity with this approach I think it is probably better to go with the constant ratio approach that is currently commented out in the code. This makes all calculations much quicker and easier.

Stability Patch

Ok, now the difficult bit.

The approach I suggested in the lost blog was

  1. calculate all motor settings for Roll, Pitch and Throttle.
  2. calculate the remaining headroom between these throttle settings and the max_throttle and min_throttle.
  3. if the headroom is not enough to contain the requested Yaw input the we reduce the requested Yaw to fit the available headroom or the minimum reserved yaw headroom.
  4. We then go through and add the Yaw request to each motor output with the throttle offset to ensure the outputs remain between the max_throttle setting and the min_throttle setting.

We do need to be very careful that Pitch or Yaw oscillations can’t make a high powered quad fly away though. I have some ideas on this but it may not be needed.


In the lost post the question was raised by Randy. “For example, I think it's much better to abandon a request from an autopilot for a 45 degree pitch forward in favour of maintaining yaw.” We could do this by:

  1.  reducing the stick input travel at low or high throttle,
  2. reducing the limit on roll and pitch rate outputs at low or high throttle,
  3. or scaling the rate outputs in the MotorMatix function.

I don’t like any of these options because they either directly interfere with the users inputs or change the ability of the Rate_I (or Stab_I) term to do it job and correct for CG and motor output offsets.

The good news is that I don’t think this is a problem if we leave the Roll and Pitch components un touched. At near minimum throttle we are descending and we can get a large Roll or Pitch output from the Rate PID’s from two things:

  1. a large stick input from the user,
  2. a large exterior force.

Point 1. If the user enters a command to change attitude from horizontal to 45 degree pitch for example. With full Pitch control this will happen in less than a second (for my quad anyway). For this short time we may lose almost all our Yaw authority leaving just a little more than is required to maintain a heading. However, as the Pitch angle increases the throttle boost kicks in. This will dramatically increase the throttle setting restoring Yaw authority.

On the other hand, If the airframe is at 45 degrees and I let go of the sticks in stabilise mode. I want to see my copter go level as fast as possible. I don’t care if I lose all Yaw authority for a second provided my copter is level afterwards. Then with the small amount of Yaw authority that we keep in reserve the copter can change the heading as requested.

Point 2. If the copter experiences a large outside force… say clips a branch while descending to land, all I care about is that it gets up the right way again. As before, Throttle boost will help us here for a portion of the rotation, but Yaw is my absolute lowest priority.

Remember I am not advocating removing all Yaw authority, I am suggesting reserving only enough to maintain a heading and apply small Yaw accelerations.

Code Example

To quote R_Lefebvre from the lost blog post, “this isn't finished working code, just kind of a back-of-the-envelope sketch”


    // capture desired roll, pitch, yaw and throttle from receiver






    // mix roll, pitch, throttle into output for each motor

    for( i=0; i<AP_MOTORS_MAX_NUM_MOTORS; i++ ) {

        if( motor_enabled[i] ) {

            motor_out[i] = _rc_throttle->radio_out +

                           _rc_roll->pwm_out * _roll_factor[i] +

                           _rc_pitch->pwm_out * _pitch_factor[i];




    // calulate the minium headroom left for Yaw.

    high_yaw_pos = 1000;

    high_yaw_neg = 1000;

    low_yaw_pos = 1000;

    low_yaw_neg = 1000;

    high_throttle = 0;

    low_throttle = 2000;


    // the signs I have used might be wrong

    for( i=0; i<AP_MOTORS_MAX_NUM_MOTORS; i++ ) {

        if( motor_enabled[i]) {

             if( _yaw_factor[i] > 0 ) {

            if( high_yaw_pos > (out_max - motor_out[i])/ ) {

                    high_yaw_pos = out_max - motor_out[i];


            if( low_yaw_neg > motor_out[i] - out_min ) {

                    low_yaw_neg = motor_out[i] - out_min;


                    } else if( _yaw_factor[i] < 0 ) {

            if( high_yaw_neg > out_max - motor_out[i] ) {

                    high_yaw_neg = out_max - motor_out[i];


            if( low_yaw_pos > motor_out[i] - out_min ) {

                    low_yaw_pos = motor_out[i] - out_min;



            if( high_throttle < motor_out[i] ) {

            high_throttle = motor_out[i];


            if( low_throttle > motor_out[i] ) {

            low_throttle = motor_out[i];





    yaw_ratio = 0.7/1.42;


    high_yaw_pos = max(high_yaw_pos, min_yaw_headroom);

    high_yaw_neg = max(high_yaw_neg, min_yaw_headroom);

    low_yaw_pos = max(low_yaw_pos, min_yaw_headroom);

    low_yaw_neg = max(low_yaw_neg, min_yaw_headroom);


    yaw_pos = min(high_yaw_pos/yaw_ratio, low_yaw_pos);

    yaw_neg = min(high_yaw_neg/yaw_ratio, low_yaw_neg);


       rc_yaw_pwm_out = constrain(_rc_yaw->pwm_out, -yaw_neg, yaw_pos);



       min_required_yaw_headroom = min(reserved_yaw_headroom, rc_yaw->pwm_out);


       if( (out_max-high_throttle)/yaw_ratio < (low_throttle - out_min) ) {

             throttle_change = min((out_max-high_throttle) - min_yaw_headroom*yaw_ratio,0);


             throttle_change = max((out_min-low_throttle) + min_yaw_headroom,0);



    for( i=0; i<AP_MOTORS_MAX_NUM_MOTORS; i++ ) {

        if( motor_enabled[i] ) {

             yaw_contribution = rc_yaw_pwm_out*_yaw_factor[i];

                    if (yaw_contribution > 0 ){

                           yaw_contribution *= yaw_ratio;


            motor_out[i] = motor_out[i] +

                                 throttle_change +





    // ensure motors are not outside alowable region

    for( i=0; i<AP_MOTORS_MAX_NUM_MOTORS; i++ ) {

        if( motor_enabled[i] ) {

            motor_out[i] = constrain(motor_out[i], out_min, out_max);




Read more…

This is a couple of flights from my holiday that I made my first quad copter for. My wife and I (and two kids under 2) were planning a 2 week four wheel drive trip across the Simpson Desert in central Australia. For those not familiar with the Simpson Desert it is 550 km of desert, 1100 sand dunes to cross, and 3000 km round trip. The quad seemed like the perfect way to get a different perspective on the landscape.

I didn't have much time before the trip and only had experience with RC gliders before so I purchased a cheap frame from Hobby King. It didn't take long to realise that it wasn't going to but up to the task so I set about designing and building my own using 3mm ply. My first wasn't going to fit in a fully packed 4WD so I had to design and build a folding version.

In the end it took four full days (over 2 months ish) from start to finish before I left on the trip so I had very little time to learn to fly a quad and optimise the tuning.

I didn’t get to develop my flying skills much before I left and I only started to get comfortable flying FPV near my last flight of the trip. Unfortunately I missed one of my ESC connectors worked its way out and I crashed the quad after approximately 10 flights. I some good footage though. The crash is at the end of the video.

I would like to thank the DIY Drones community and everybody who contributed to the ARM 2 board!

Just for kicks I thought I would put a rendering of my SolidWorks design and what it looked like after it was built.



Post processing I did on the GoPro footage

As you can see from parts of the footage, my piloting was still pretty poor and I didn't get time to balance my propellers before the trip. I also found that the fish eye on the GoPro was pretty hard to watch when set to 720P (170 degree field of view). Before I went I tried to work out what I should be setting the camera to but people didn't post the settings or post processing details. So here is what I did for this trip:

GoPro settings:

720P (170 degree wide)

50 fps (this minimised the rolling shutter I found)

Post processing using Virtual Dub:

1. Resize 1900x1600

2. Deshaker v3.0

3. Barrel Distortion

4. Resize 1280x720

I did this as a mass batch process using DubMan. Here are my processing settings for Virtual dub. There are two because Deshaker takes two passes.



All this is free but then I added 20% saturation in CyberLink PowerDirector 10 Deluxe when I cut the video together.

Read more…

Acro Mode PID Options and "Fly by Wire"

3689475641?profile=originalThanks for taking the time to read another Blog post.

"Not another Blog post" you say, "Get off your *** and code something up I hear you say" :)

Yeh I know, I hope to have some time over xmas. I am using this BLOG to clarify what I want to do, attempt to make notes that I can refer to (when I finally get my finger out), and get feedback from people to better understand how to best achieve my goal.

Just a quick note on the diagram above. I describe it below but I have remove a number of components that we currently use in the code because they unnecessarily complicate the drawing and are not used in my setup. They could be included in the controller if the user desired.

My Goal is to improve the ACRO mode

The Arducopter has been developed with a significant focus on autonomous flight. The hardware and IMU code is working extremely well. However ACRO mode is much simpler than the quality of the majority of this code and hardware deserves.

The unrestricted ROLL_PITCH_ACRO code is found here:


However it is combined with a YAW_HOLD code by default, shown here:


instead of the YAW_ACRO code here:


I understand this has been because it significantly improves when flying a helicopter.

There is also some restricted ACRO code, that is accessed by setting AXIS_ENABLE to 1, here:


The difference between what I refer to as restricted and unrestricted is weather or not the code allows the airframe to rotate through 360 degrees in any direction.

True ACRO mode will allow the pilot to do flips in roll and yaw or any combination there of.

Restricted ACRO mode is basically controlling STABILIZE mode using a rate input rather than an absolute angle input.

Ideal ACRO mode

The idea ACRO mode is "Fly by wire". By that I mean that the airframe is stabilized as it is in STABILIZE mode but controlled by rate inputs like it is and ACRO mode. I have shown a number of PID control loops above that illustrate potential options to implement this.

The first is the rate only control loop that is currently used by default. This PID design suffers from the absence of absolute attitude feedback. This means that noise, sensor drift, and external forces can cause the attitude of the airframe to vary when no variation is commanded.

The second is the rate controlled stabilize loop that can be set by assigning AXIS_ENABLE to 1. This is a very nice option in that it allows small and precise attitude changes to be made by small stick inputs. This makes it possible to precisely control the airframe not only at hover but also in fast forward flight when pitched forward at 30 degrees. This mode could also be combined with the ALT_HOLD throttle mode to make learning to fly ACRO easier. However, this PID design doesn't result in crisp response because the rate is only increased in proportion to the difference between the desired attitude and measured attitude. This difference must build up to achieve full rate. The last option addresses this problem using a feed forward technique.

The third option is what I would like to eventually implement. This is a feed forward PID design. Here the desired rate is directly fed into the rate controller. However unlike the rate only PID design, the rate is also fed into the attitude input via an integrator (or rate times time step sum). The attitude feedback part of this PID controller only attempts to correct the error in attitude, it is not responsible for commanding the desired rate. In this way we are able to achieve full rate without the "wind up" effect of the attitude controller but still achieve a very stable attitude when zero rate is commanded. If the copter is hit by an external force, the attitude feedback part of the PID will reset the attitude to where it should be. This brings me to the attitude error limit. This is there to prevent poor PID coefficient choices from causing the airframe to continue to move far after the rate command has been set to zero.

Gimbal Lock and Ardupilot

This brings me to a very important point that is missing if we want to be able to use an unrestricted and stabilized implementation of ACRO. Currently the roll and pitch controllers assume that the commands to move the airframe in roll, pitch and yaw correspond to the measurements of attitude. While this is not far from the truth during hover it creates a larger and larger error as the pitch or roll angles increase.

This made flying the quad very strange for me initially. I am used to flying aircraft where I could "Bank and Yank" the aircraft through a turn (roll to say 45 degrees and use pitch to turn). Because of this effect we need to "Bank and Yaw" instead.

While rolled 45 degrees to the right, an input in Yaw to the right (measured by the attitude controller as an angle from north around the horizon) will cause an equal rotation rate in both Yaw to the right and Pitch down. This will cause the Pitch controller to add a pitch up once as this error grows but because this pitch up is at 45 degrees from the horizon it will cause both an increase in pitch up and an increase in yaw to the right.

Ideally what we would do is translate the coordinate system of the earth to that of the airframe before commanding a desired pitch, roll and yaw rate. In this case if the airframe is rolled 45 degrees to the right and a yaw command to the right is applied the yaw controller will command both a yaw and pitch rate command that keeps the nose of the airframe on the horizon.

Without this facility we can't implement a stabilized, unlimited ACRO mode.

Stability in ACRO mode

The common perception of perfect ACRO mode is that we command a rate in any axis and the airframe moves in that axis. While this is good, it is what is known as neutrally stable. When we fly an aircraft we like the aircraft to have a tendency to right its self without user input, this is known as positively stable. This can be implemented into the PID controller using a user defined attitude to rate feedback loop. Basically the roll and pitch angle is multiplied by a stability factor and subtracted from the desired roll and pitch rate. This results in the airframe moving back to level when the sticks are released in a similar way to STABILIZE but when full stick is applied the airframe will continue to rotate in what ever direction is commanded.

An ACRO beginner would set the stability factor high resulting in performance very close to STABILIZE while an experienced pilot might set it to zero or very small so that the attitude can be set not move if the sticks are let go.

OK it's over

Well this pretty much sums up my intentions. The reason I have chosen to focus on ACRO is because most of what I describe above can be done without effecting any other of the auto modes (limited stabilized ACRO mode with a stability factor). And this also happens to be what I want to fly with when I do my 55 km/h runs down a valley out the back of a friends farm house.(Video to come, but I want to get lower).

Any way, if you have read all the way to this point I congratulate your patience. Thank you in advance for any feedback, comments, and (especially) corrections, you can give on the ideas expressed above.

You may be happy to know that I think I am out of things I want to put on my BLOG now :) Now I just need to fix my USB port on my ARM2 so that I can program it without holding the USB cable.


Equations for translation between EARTH frame and BODY frame:






Read more…


Thanks for taking the time to read this post. First of all I would like to reassure you that this is in no way a criticism of the code or the Dev team, they have done a fantastic job.

I am working towards making my own contribution to the Arducopter code base to improve the "Fly by Wire" aspects, but it will take time for me to get the environment set up. (two kids under 2 and 2 jobs) So in the mean time I would like to discuss my ideas. If they are supported and still not implemented when I get my finger out then I will start attempting to implement and test them.

I would appreciate any feedback you can give me.

So this is my first idea to address two problems I and others have experienced in using the Arducopter.

The dreaded drop in altitude when transitioning from Alt Hold or any other Auto mode to Stabilize. Ok, it isn't a big deal once you get used to it but it isn't pretty and I think we could do better.

So I see a number of problems to be addressed:

1. Drop or increase in height when changing modes.

2. Throttle hover position in Stabilize is not in a fixed location so it needs to be "found"

3. Alt Hold is implemented such that it changes height rather aggressively.

I was able to address point 2 and even point 1 to a lesser degree setting up my throttle curve in my transmitter to set hover at mid stick.

Point 3 makes using Alt Hold to control altitude while learning or filming quite clumsy or impractical.

Ok so here is the idea. It has three parts to bare with me.

3689475373?profile=originalManual Throttle curve making hover at mid stick

Now I could see in the code where the throttle offset was changed to place throttle_cruise at mid stick but it did this by simply offsetting and limiting the curve. What I suggest above is to add two slopes for > throttle_cruise and < throttle_cruise. This means that no matter what throttle_cruise is set to the pilot will have access to full throttle range in Stabilize. throttle_cruise takes approximately 5 seconds to move 90% to hover. This means that the throttle position during hover for a bad throttle_cruise setting would move quiet slowly even in the worst case.

Alt Hold has progressive rate vs stick input and smaller dead band

The diagrams on the right show the throttle input vs requested climb rate when using Alt Hold. I am suggesting that we should make this progressive with only a small dead band in the middle. This makes it possible to make smooth and slow altitude changes without having to use the Manual Throttle. (great for learning and filming)

Transitioning from Auto mode via Alt Hold mode

When switching from Auto to Stabilize we could pause in Alt Hold mode. How I was thinking we could do this is to spend a maximum of 2 seconds in Alt Hold mode or until we move the throttle to the dead zone in Alt Hold. What ever happens first. The effect of this is to limit the sudden drop or increase in hight to -120cm/s to 180cm/s and give the pilot time to react by moving the throttle to the central position. Once in the dead band the throttle setting should be within 10% of that required for Hover.


Mid stick is always what you need to hover.

Change from Alt Hold to Stabilize should not result in scary moments because the throttle stick position should be within 10% of Hover.

Change from Auto modes, when the throttle has been set to max or min, will give the pilot 2 seconds warning before going to full or no throttle.

Alt Hold is much more "Fly by Wire".


Alt Hold would drift if the throttle is just outside the much small dead band.

There may be times when the 2 second delay moving to Stabilize could prevent the pilot adding full throttle in time to prevent a crash.

I would really appreciate any feedback and insight people have into this idea or these problems in general.



Code for this approach:

As always the code is marching on and there are already changes made in the areas I have been discussing. So I thought I would list the main requirements in the code to make this work the way I describe.

The main requirement is that g.throttle_cruise is only updated when the copter is in a stable stationary hover. The simple testes for this could be

(g.rc_3.control_in > g.throttle_min && abs(climb_rate) < 60&& abs(g.rc_1.control_in) < 1000 && abs(g.rc_2.control_in) < 1000 )

This can happen in all flight modes. Altitude is kept in different flight conditions other than hover using the Rate I term. The Rate I term limit needs to be large enough to compensate for all flight conditions.

The code for the throttle position to manual throttle output is very straight forward.

if(g.rc_3.control_in < (500 - th_deadband/2)){
    g.rc_3.servo_out = g.throttle_cruise * (g.rc_3.control_in / (500 - th_deadband/2));
}else if(g.rc_3.control_in > (500 + th_deadband/2){
    g.rc_3.servo_out = g.throttle_cruise + (1000-g.throttle_cruise) * ((g.rc_3.control_in-500-th_deadband/2) / (500-th_deadband/2));
    g.rc_3.servo_out = g.throttle_cruise;

The code for the throttle position to altitude rate output is something like this:

if(g.rc_3.control_in < (500 - th_deadband/2)){
    th_Rate = -120 * (g.rc_3.control_in / (500 - th_deadband/2));
}else if(g.rc_3.control_in > (500 + th_deadband/2){
    th_Rate = 180 * ((g.rc_3.control_in-500-th_deadband/2) / (500-th_deadband/2));
    th_Rate = 0;

Sorry but I am not familiar enough with C to add the types quickly.

In the latest version of the code the throttle_cruise factor is updated in two places. Here where it was before and what I think works well with this approach.


throttle_avg = throttle_avg * .99 + (float)g.rc_3.control_in * .01;
g.throttle_cruise = throttle_avg;

The new addition here is a problem for this approach. The code is Here:


and here:


The second update prevents this approach from working because it is constantly resetting the Altitude I term and adding it to g.throttle_cruise.

Read more…

Why are the Throttle PID's like this?

I was hoping that someone could explain why the Throttle PID's are designed like this.

3689474587?profile=originalThis is like a feed forward controller design that is then stabilized by the PID feedback loop. That is ok.

Why is the feed forward gain based on to desired rate squared? (propeller static force is proportional to (delta RPM)^2 from what I can find on the net but ESC's aren't very linear anyway)

Why is the limit on the output set to 3200 when the output of the throttle should be only 0 to 1000? (I may be wrong here but I have done my best to check this)

Why didn't we get rid of the rate squared term and just use the PID loop?

Why didn't we get rid of the Throttle Cruze offset and just use the PID loop and not reset the I term? This approach may stop that "my copter dropped out of the sky when I switched to altitude hold mode" problem. Even if the I term is zero to start with at least it can correct it's self while in this flight mode instead of having to fly in Stabilize Mode for 10 to 15 seconds.

I just want to reassure everybody that I am not having a go at all the hard work the developers have done on this project so far. I am just enjoying working towards helping improve the code. Before attempting to improve things I want to understand why things are the way they are.

I would really appreciate any help and discussion that people can contribute.


Ok, I was slack and didn't put the control input into the diagram. Here it is.


It is a bit complicated to work out from the code because the throttle control is very non linear. Navigation control does something similar but it has set THR_ALT_P to 1/4, limited from 100 to 180,if going up and 1/6 if going down, limited from -10 to -100.

Read more…

Head first into the deep end :)

3689469893?profile=originalHi all,

I wanted to ask some questions about my quad implementation but I thought that it would be polite to introduce myself and my quad first.

I started my first quad design because my wife and I (and two kids under 2) were planning a 2 week four wheel drive trip across the Simpson Desert in central Australia. For those not familiar with the Simpson Desert it is 550 km of desert, 1100 sand dunes to cross, and 3000 km round trip. The quad seemed like the perfect way to get a different perspective on the landscape.

I have been following DIY Drones for a while because I supervised a couple of Electrical and Electronic Engineering final year projects to develop an IMU for a basic auto pilot application. So I ordered an ARM 2 and a bunch of parts from Hobby King.

I started with a cheap frame but quickly realised that it wasn’t going to be easy to mount the ARM 2 so I decided to design and build my own, keeping the aluminium arms and motor mounts. I wasn’t overly happy with my first design but it did serve to introduce me to some of the basic tuning and setup required. It also made me realise how much electronics I was going to have to cram into the quad to do what I intended.

I quickly realised that my first frame was going to be very difficult to carry in a fully loaded 4WD so I redesigned the frame to fold up and be stored against the cargo barrier above the rear seats. I also added some room for a pitch gimbal on the GoPro I intended to use.

The final assembly looks like this:


Folded for travel:


And the pitch gimbal and GoPro:


The basic parameters for the quad are:

1.6 kg with GoPro

NTM Prop Drive Series 28-26A 1200kv / 250w

APC 12x3.8 Propellers

Hobbyking X550 Aluminum Spare Booms ( 2pcs red/2pcs black)

ZIPPY Flightmax 4000mAh 3S1P 20C

Fat Shark Predator RTF FPV Headset System w/Camera and 5.8G TX

I broke quiet a few prop’s so I am now using:

Slow Fly Electric Prop 1045 SF

In the end it took four full days from start to finish before I left on the trip so I had very little time to learn to fly a quad and optimise the tuning. I have flown RC gliders since I was 14 so I had some basics but this was the first time I had flown anything with a motor. The most challenging part of the process was the tuning. I have a good understanding of control theory as make use of it from time to time in my day job but the Wiki control loop diagrams don’t seem to be up to date. This made it difficult to understand how some of the parameters interact.

I didn’t get to develop my flying skills too much before I left and I only started to get comfortable flying FPV near my last flight of the trip. Unfortunately I missed one of my ESC connectors worked its way out and I crashed the quad after approximately 10 flights. I some good footage though. I will post a video when I get one cut together.

I would like to thank the DIY Drones community and everybody who contributed to the ARM 2 board!

Read more…