Next Generation Tilt Sensor/ Attitude Monitor

The Rocketry Forum

Help Support The Rocketry Forum:

This site may earn a commission from merchant affiliate links, including eBay, Amazon, and others.
Consequently, my focus on the application of the technology is to try to eliminate as much roll as possible.

Getting rid of the roll is a necessary step if you are trying to do a Vertical Trajectory System without using stupidly fast servos and a higher degree of difficulty in general.

Similarly to a helicopter, when a rocket is spinning there is a phase shift in the rotation from where the fin provides force to where it is applied. In helicopters it can be up to nearly 90 degrees phase lag from the applied blade angle. So to affect pitch, the angle of the blades at the left-right position determines the outcome. Similarly the roll control is achieved by what the blades are set at in the fore-aft position, or thereabouts.

A rolling rocket will not exhibit such a large phase shift, but some roll-pitch coupling will happen. This would likely result in something like a dutch roll flight path. I am working on stopping the roll with my VTS to keep things simple... https://forum.ausrocketry.com/viewtopic.php?f=56&t=5324
 
Will be nice to have an option to separate the booster if the angle is to large to fire the motor, If the booster stay attached the main chute of the sustainer will not be sufficient
 
Will be nice to have an option to separate the booster if the angle is to large to fire the motor, If the booster stay attached the main chute of the sustainer will not be sufficient

I launched a 28 lb two stage rocket that failed to separate the booster from the sustainer (timer was not working properly). Both sections deployed parachutes: the booster on motor eject, and sustainer kicked the drogue out at apogee, and then the main at 300'. I was surprised the whole thing hung together, but we had a completely safe recovery and no damage to the rocket beyond some scraped paint and a ding in the nosecone. But I see your point, and I'll look for a method to provide an option to allow the timer to allow event 1 (stage separation) and disallow event 2 (sustainer ignition). Current code is designed to shut off both events upon a poor trajectory.
 
That's where breakwire support can be handy... if your separation doesn't happen, inhibit the sustainer ignition.
 
But I see your point, and I'll look for a method to provide an option to allow the timer to allow event 1 (stage separation) and disallow event 2 (sustainer ignition). Current code is designed to shut off both events upon a poor trajectory.

IMHO, the staging event does not have to run through the tilt sensor... i.e. whether or not the sustainer motor is allowed to light, the sustainer should be off the booster for recovery. If it doesn't drag separate, one can blow it off with a charge prior to lighting the sustainer's motor (or the decision of the sensor to not light it). The Seahawk flies with a simple timer (two, actually, for redundancy) in the ISC to separate the sections after booster motor burnout, another second or two to get some space between them, then separate circuitry in the sustainer av bay to light its motor (protected with an original Tiltometer).

[video=youtube_share;JWG7-3rVfIg]https://youtu.be/JWG7-3rVfIg[/video]
 
I've updated the Arduino code to use the accelerometers to assign the original tilt to the rocket on the pad, transfer this position information to the gyros upon launch detect, and then use gyros only for the duration of the flight. I've posted the new code, entitled MPU6050_Companion_Gyro_v3.ino at https://github.com/ekchess/PET2_Companionv7/blob/master/MPU6050_Companion_Gyro_v3.ino. The board has not been altered. The code still controls both SSRs together, so if you want to control the stage separation BP charge independently, simply do not wire the charge through the companion board. Take a look at the code, which was based on code written by Joop Brokking for a quad copter, and let me know your thoughts. The code is currently configured to run at 500Hz. I tested higher rates but found the code was not fast enough to do any better than 500Hz on the Arduino Pro Mini (5V version, which runs with a 16MHz crystal).
 
This code makes no sense to me:
Code:
angle_pitch += angle_roll * sin(gyro_z * 0.000000533); //500Hz; If the IMU has yawed transfer the roll angle to the pitch angle
angle_roll -= angle_pitch * sin(gyro_z * 0.000000533);   //500Hz; If the IMU has yawed transfer the pitch angle to the roll angle

I expected to see the pitch and (misnamed) roll corrected using the integrated gyro_z data. Instead it is using the roll rate. How does that work?
 
This code makes no sense to me:
Code:
angle_pitch += angle_roll * sin(gyro_z * 0.000000533); //500Hz; If the IMU has yawed transfer the roll angle to the pitch angle
angle_roll -= angle_pitch * sin(gyro_z * 0.000000533);   //500Hz; If the IMU has yawed transfer the pitch angle to the roll angle

I expected to see the pitch and (misnamed) roll corrected using the integrated gyro_z data. Instead it is using the roll rate. How does that work?

In full disclosure, I'm not really savvy on either the hardware or the programming, I'm just a solderer and test-bed guinea pig, but I will bring up your question with Ed.

In any event, this is a market in need of a product. We fly a lot of staged and/or airstarted motors, and having something capable of making consent decisions based on real-time situations is preferable to running a timer with your fingers crossed. It is a complicated problem and we are a small market, so don't expect any help from Gates or Musk. We are probably as a hobby going to have to forge ahead ourselves with our vastly diverse field of knowledge. i.e. got any suggestions?

I know we are a long way from self-driving cars, but there is some overlap. How does a self-driving car know whether the object that just appeared in its flight path is blowing garbage or a child chasing a ball? The answer would make a huge difference in the outcome of you were on a narrow road with oncoming traffic and no escape path.
 
In any event, this is a market in need of a product..

I realize the code for the altusmetrum altimeters is a bit scary as it's using quaternions to perform the rate gyro integration in a single step. However, that's the solution which avoids the pitfalls inherent in any step-wise "Euler Angle" code (which the above fragment appears to use). Our software and hardware designs are all freely available, so this algorithm could be adapted to other hardware starting with the code that we ship for EasyMega and TeleMega altimeters. I would love to see other systems available which also directly measured tilt angle to help make staging and airstarts safer for everyone.
 
I realize the code for the altusmetrum altimeters is a bit scary as it's using quaternions to perform the rate gyro integration in a single step. However, that's the solution which avoids the pitfalls inherent in any step-wise "Euler Angle" code (which the above fragment appears to use). Our software and hardware designs are all freely available, so this algorithm could be adapted to other hardware starting with the code that we ship for EasyMega and TeleMega altimeters. I would love to see other systems available which also directly measured tilt angle to help make staging and airstarts safer for everyone.

Well, done, Keith. You guys are great.

And having worked around/with people who do this professionally for missions throughout the solar system, I can confirm that quaternions are the way to go for updating the calculated attitude from rate sensors.
 
It took me about 90 minutes of discussion with Keith P at Airfest along with another couple hours perusing the Altus Metrium open source site. That was enough. I am a believer. And voted with $'s since then--smart guys deserve the dough.

From the Ether...
 
Last edited:
I realize the code for the altusmetrum altimeters is a bit scary as it's using quaternions to perform the rate gyro integration in a single step. However, that's the solution which avoids the pitfalls inherent in any step-wise "Euler Angle" code...
Totally agree about the use of quaternions for keeping track of orientation. However, looking at the Altusmetrum code I see it using the common Euler formula to update the quaternion from the gyro readings. However, that formula has a built-in inherent assumption that the Eular angles change in a specific order. That being yaw, then pitch, then roll. (One example reference starting this is the Wiki page at this link.) However, the order of angle changes on a body does not commute. A yaw, pitch, roll maneuver for a body does not yield the same orientation in inertial space as for example, a roll, pitch, yaw sequence. It seems to me this formula will be inducing error into the computed orientation since a rocket will pitch, yaw and roll in an unknown sequence. Unless I missed something, I think a different formulation is needed to properly update the quaternion.
 
I see it using the common Euler formula to update the quaternion from the gyro readings.

Yes, the gyro rotations are converted to a quaternion in a specific order. I don't think there is any other way to perform this conversion. However, because the incremental rotations are small due to the sampling rate, the order-induced error is also small.

For rocketry, a 100Hz sample rate is plenty fast -- typical pitch and yaw rates are on the order of a few degrees per second at the most, yielding a few hundred's of a degree per sample. Of course the roll rate is often much higher, but the order only matters when you have large rotations in more than one axis. If I was building something expected to rotate rapidly in more than one axis, I'd be increasing the sample rate to keep the sampled rotation values small.
 
In any event, this is a market in need of a product. .

Sather/Ed.. will this eventually be something we can buy? I can solder, but I haven't compiled any software in a good 10 years :) And my skills in flashing software on chips are non existent.
 
I don't think you can use the accelerometer in the MPU9250 with the quaternion, it's very likely to be pegged during boost. You'd probably need an external 3-axis 100G (or so) accelerometer like this one... https://www.mouser.com/search/ProductDetail.aspx?R=0virtualkey0virtualkeyH3LIS100DLTR
Apologies in advance to Cris Irving for responding to a nearly 4 year old posts, but I've just started building an Arduino MPU-9250 -- based rocket inertial data logger. On many flights, of the three L2 rockets I'm building RockSim10 says I can keep the maximum force to under 16 g's, but on other flights this is out of the question.

I looked at the specs for the H3LIS100DLTR, and it only has 0.78g of resolution in its 8bit data read. This is only 1/1600th the resolution of the MPU-9250. On the other hand the H3LIS331DL has 0.049g of resolution in its 12bit data read in the 100g range which is still just 1% of the MPU-9250's 16bit data resolution. But this is the cost of needing a 100g acceleration range.

After this analysis, I ordered a SparkFun breakout H3LIS331DL to connect to my Arduino along with a MPU9250 breakout. I also have a BMP280 breakout for measuring atmospheric pressure for calculating altitude. But its still yet to be determined if either the accelerometer data from the MPU-9250 or the H3LIS331DL can be integrated to get a good estimate of velocity after deducting the gravitational offset.

In the meantime, I have several Jolly Logic Altimeter3 data sets from my late Apogee Zephyr that I can analyze with Excel to see how good the 3-axis accelerometer data is for estimating velocity and altitude, or apogee. I'm pretty sure these L1 and L2 flights flights didn't go over the maximum 24G that the Altimeter3 can measure. So I'll be using the Altimeter3 data as a model to see what I can hope to gather with the combined MPU9250, H3LIS331DL and BMP280 on my next rockets.

TE/Meas-Spec MS5637

I have and use Eggtimer Protons and Quantums, and its useful to know that this is the altimeter sensor you use. Are there advantages of using this over the BMP280? At this point I'm open to getting a MS5237 breakout if I can find one.
 
On the other hand the H3LIS331DL has 0.049g of resolution in its 12bit data read in the 100g range which is still just 1% of the MPU-9250's 16bit data resolution. But this is the cost of needing a 100g acceleration range.

I use two accelerometers onboard my units. The LSM9DS1 is an IMU with accelerometer good to 24Gs, 2000dps gyro, and magnetometer. I use the H3LIS331DL for those few flights that go above 24Gs. Ramp the data rate up to 1000sps and use a moving average of the last 15 datapoints. The lag is not noticable and the readings are spot-on with the LSM9DS1 data.

I also have a BMP280 breakout for measuring atmospheric pressure for calculating altitude. But its still yet to be determined if either the accelerometer data from the MPU-9250 or the H3LIS331DL can be integrated to get a good estimate of velocity after deducting the gravitational offset.

The IMU will drift no matter what. With pure IMU integration I get an over-estimate of altitude in the 8-15% range. The BMP280 will help fix this by a lot. I use the IMU to integrate between barometric readings, and when I get a baro reading, I use a weighted average of the integrated (0.95) and barometric (0.05). It really smooths things out and increases accuracy.

My biggest problem right now is the gyros. I'm using quaternion differentials at about 500Hz. It seems to work OK shortly after liftoff, but by apogee I'm off by as much as 30 degrees. I'm not sure what I'm doing wrong.
 
I use two accelerometers onboard my units. The LSM9DS1 is an IMU with accelerometer good to 24Gs, 2000dps gyro, and magnetometer. I use the H3LIS331DL for those few flights that go above 24Gs. Ramp the data rate up to 1000sps and use a moving average of the last 15 datapoints. The lag is not noticable and the readings are spot-on with the LSM9DS1 data.



The IMU will drift no matter what. With pure IMU integration I get an over-estimate of altitude in the 8-15% range. The BMP280 will help fix this by a lot. I use the IMU to integrate between barometric readings, and when I get a baro reading, I use a weighted average of the integrated (0.95) and barometric (0.05). It really smooths things out and increases accuracy.

My biggest problem right now is the gyros. I'm using quaternion differentials at about 500Hz. It seems to work OK shortly after liftoff, but by apogee I'm off by as much as 30 degrees. I'm not sure what I'm doing wrong.
I’m also used to using a moving average for my scientific and engineering firmware and data analysis.

Averaging 15 acceleration 1000sps 12-bit precision data points is almost like using a 16-bit precision accelerometer at 67sps.

Your results from the moving average from the 1000sps H3LIS331DL acceleration data is great to hear. I should be able to collect a continuity of H3LIS331DL acceleration data and match the with the segments of MPU-9250 acceleration data that are below 20g.

I’m also not surprised that quaternion differentials can show large uncertainties at apogee when the rocket’s tilt angle is changing rapidly, the derivative of the composite quaternion vector changes even more rapidly which greatly magnifies its uncertainty.
 
Last edited:
I’m also not surprised that quaternion differentials can show large uncertainties at apogee when the rocket’s tilt angle is changing rapidly, the derivative of the composite quaternion vector changes even more rapidly which greatly magnifies its uncertainty.

I'm still not sure. I'm doing rotation updates at 500Hz which is pretty quick, and the accuracy seems to drop off right when the rocket is flopping over. I'm now wondering if the 30Hz high-pass filter is the issue. I'm going to turn it off and see if it makes a difference.
 
I'm still not sure. I'm doing rotation updates at 500Hz which is pretty quick, and the accuracy seems to drop off right when the rocket is flopping over. I'm now wondering if the 30Hz high-pass filter is the issue. I'm going to turn it off and see if it makes a difference.
What does it do on the bench?
 
I'm going to test that today. I know it used to be very accurate when I first wrote the code. I haven't bench tested it in a while, so its possible I goofed something up.
Make sure you do rotations (rolls) when you simulate on the way up.
 
You absolutely do not want that. You can't even measure the zero offset with that operational.
I was getting some spurious readings and wanted to filter those out. The LSM9DS1 had a setting for a high-pass filter so I turned it on. That eliminated the spurious readings, but I'm not sure if that was the right way to do it. The reality is that the spurious readings are so sparse that they really aren't impacting accuracy.
 
I'm also trying to figure out how to turn the magnetometer readings into 3D orientation readings. Anybody know how to do it?

I've figured out how to do roll, but pitch and yaw I'm still trying to figure out. I'm getting close, but haven't found the winning set of equations yet.
 
I'm also trying to figure out how to turn the magnetometer readings into 3D orientation readings.
The problem with that is that the field strength and direction depend on where you are. (See Mark 14 torpedo.)

The best that you can do is get the starting values, assuming they haven't been corrupted by iron in the launch pad, and use that as a starting point and get deviations from that. But rotations aligned with the field can't be seen.
 
I'm also trying to figure out how to turn the magnetometer readings into 3D orientation readings. Anybody know how to do it?

I've figured out how to do roll, but pitch and yaw I'm still trying to figure out. I'm getting close, but haven't found the winning set of equations yet.
First you need to calibrate your magnetometer. x^2+y^2+z^2 should be equal to a constant. Then the x, y, and z readings are the direction cosines of the earths magnetic field vector.
 
I'm still not sure. I'm doing rotation updates at 500Hz which is pretty quick, and the accuracy seems to drop off right when the rocket is flopping over. I'm now wondering if the 30Hz high-pass filter is the issue. I'm going to turn it off and see if it makes a difference.
My statement:
the derivative of 'X' changes even more rapidly than 'X'
is generally true for all measured variables and not just quaternion vector measurments. The numerical derivative (or slope) of any function is the difference between two data points, each with its associated uncertainties and statistical distributions. The combined variability of this difference is larger than the variability of a single data point. Now if you were averaging two data points instead of needing to know their estimated difference, the variability would be smaller.

If you high-pass filtered any single measurement the statistical variability would be reduced. But if you subtract the difference between two high-pass filtered data points the statistical variability of the difference will be larger than a single high-pass filtered data point. Its almost axiomatic that slopes of measured functions are noisier than the individual data points. This is also one reason why measured acceleration data is nosier than measured velocity data, which is noisier than the statistical variation of altitude data. Derivatives calculations result in increased noise and statistical variation. Integrated data is like averaging, it reduces the statistical noise and variation.
 
The numerical derivative (or slope) of any function is the difference between two data points, each with its associated uncertainties and statistical distributions.

Dan, there is no numerical derivatives being taken in gyro based IMU calculation. The gyros out put rates which can either be integrated into 3 euler angles or used to define a rate quaternion which can be integrated to find the new quaternion. A suitable lpf should be configured for the rate gyro's.
 
Dan, there is no numerical derivatives being taken in gyro based IMU calculation.
This doesn’t matter. I was responding to

My biggest problem right now is the gyros. I'm using quaternion differentials at about 500Hz. It seems to work OK shortly after liftoff, but by apogee I'm off by as much as 30 degrees. I'm not sure what I'm doing wrong.

“Quaternion differentials” are the differences between quaternions, and they don’t need to be calculated within the gyro-based IMU. The differences between quaternion measurements are used to calculate the change in direction that’s off by 30 degrees at apogee.

In general when you’re looking at the statistical variation of data points, the overall statistical variation in a difference between two data points is the root sum square of the statistical variation of each data point. This also applies to parameters calculated from separate reported quaternion vector measurements. And these individual quaternion vector measurements are changing rapidly at apogee.
 
Back
Top