Navit is an open source navigation system with GPS tracking. It works great with a Raspberry Pi, a GPS module and a small TFT with touch, jut like the official Raspberry Pi Display or PiScreen.
Navit can be installed without a GPS connected to your Raspberry Pi, but you will not be able to use the real-time turn by turn navigation. You will however be able to browse maps. If you are not going to use a GPS, you can skip to the next step.
As we are using the BerryGPS-IMU, we will be following the guide in the link below. As most GPS modules use serial to communication, this guide can be followed for other GPS modules.
The images below shows how we have connected the BerryGPS-IMU to the Raspberry Pi 3 whilst it is in the SmartPi Touch case.
If you plan on testing this out in your car, you need to be mindfully of where you place your BerryGPS. In my setup and I have placed it in the air vent as shown below, and BerryGPS gets a good strong signal.
If you are using an external antenna, then there is no need to worry about where your BerryGPS is placed.
BerryIMU also works great with Windows IoT Core on the Raspberry Pi.
Our Git repository contains the source files needed to get the BerryIMU up and running on Windows IoT.
The code will print out the following values to the screen;
Raw values from the gyroscope, accelerometer and magnetometer.
Accelerometer calculated angles.
Gyro tracked angles.
Fused X and Y angles.
Heading.
Tilt compensated heading.
Connecting BerryIMU to a Raspberry Pi
BrryIMU can connect via the jumper cables to the Raspberry Pi as shown below;
Or BerryIMU can sit right on top of the GPIO pins on a Raspberry Pi. The first 6 GPIOs are used as shown below.
Get the Code
Download the BerryIMU code for Windows IoT from our GIT repository. The files you need are under the WindowsIoT-BerryIMU folder.
You will need to download the entire git repository as GIT doesn’t allow downloading individual folders.
Once downloaded, double-click the file WindowsIoT-BerryIMU.sln to open up the project in Visual Studio.
About the code
The project code outputs all of the needed values to the screen and a complementary filter is used to fuse the accelerometer and gyroscope angles.
We have a number of guides already documented on how to get the BerryIMU working with the Raspberry Pi. https://ozzmaker.com/berryimu/ These are based on Raspbian, however the principals and math are the same for Windows Iot.
The final values which should be used are the fused X &Y angles and the tilt compensated heading.
The sensor on the BerryIMU is the LSM9DS0 and all the I2C registers for this sensor can be found in LSM9DS0.cs
The main code can be found in MainPage.xaml.cs
Complementary Filter
A complementary filter is used to fuse the angles. Is summary, the complementary filter trusts the gyroscope for short periods and trusts the accelerometer for longer periods;
Changing how much trust is given for each of the sensors can be changed by modify the complementary filter constant at the start of the code.
const float AA = 0.03f; // Complementary filter constant
Loop Speed
The loop speed is important as we need to know how much time has past to calculate the rotational degrees per second on the gyroscope. A time delta is set at the start of the code.
const int DT = 100; //DT is the loop delta in milliseconds.
This is then used to specify a new timer method.
periodicTimer = new Timer(this.TimerCallback, null, 0,DT);
Here you can see where DT is used to keep track of the gyroscope angle. You can also see it in the above calculation for the complementary filter.
//Calculate the angles from the gyro
gyroXangle += rate_gyr_x * DT / 1000;
gyroYangle += rate_gyr_y * DT / 1000;
gyroZangle += rate_gyr_z * DT / 1000;
BerryIMU orientation
The calculations in the code are based on how the BerryIMU is orientated. If BerryIMU is upside down, then some of the angles need to be reversed. It is upside down when the skull logo is facing up(or to the sky). If it is upside down, set the below value to true. Otherwise, set it to false.
This post explains how to log GPS data from a BerryGPS or a BerryGPS-IMU and then how to plot this data onto Google Maps and many other maps E.g. OpenStreet, WorldStreet, National Maps, etc..
1. Setup GPS
Follow the instructions on this page to setup your Raspberry Pi for a BerryGPS-IMU. Ensure GPSD is set to automatically start and confirm that you can see the NMEA sentences when using gpsipe;
pi@raspberrypi ~ $ gpspipe -r
2. Automatically Capture Data on Boot.
We will be using gpspipe to capture the NMEA sentence from the BerryGPS and storing these into a file. The command to use is;
-r = Output raw NMEA sentences. -d = Causes gpspipe to run as a daemon. -l = Causes gpspipe to sleep for ten seconds before attempting to connect to gpsd. -o = Output to file.
The date the file is created is also added to the name.
Now we need to force the above command to run at boot. This can be done by editing the rc.local file.
pi@raspberrypi ~ $ sudo nano /etc/rc.local
Just before the last line, which will be ‘exit 0’, paste in the below line;
The Raspberry Pi 3 can now be booted from a USB drive or from over the Network. It is still in beta and somewhat complicated to setup.
However, once the Raspberry Foundation has ironed out some of the bugs and have made it easier to configure, I think these two features will be used more frequently, specifically booting from USB.
uname -a can be used to see what kernel version is running
pi@raspberrypi ~ $ uname -a Linux raspberrypi 3.18.11-v7+ #781 SMP PREEMPT Tue Apr 21 18:07:59 BST 2015 armv7l GNU/Linux
2015-05-05-raspbian-wheezy
pi@raspberrypi ~ $ uname -a Linux raspberrypi 4.1.19-v7+ #858 SMP Tue Mar 15 15:56:00 GMT 2016 armv7l GNU/Linux
2016-02-03-raspbian-jessie
To check the hardware version;
cat /proc/cpuinfo can be used to see what hardware you are using. Take note of the revision number in the second last line and then refer to the table below. The output below is from a Pi 2
pi@raspberrypi ~ $ cat /proc/cpuinfo processor : 0 model name : ARMv7 Processor rev 5 (v7l) BogoMIPS : 38.40 Features : half thumb fastmult vfp edsp neon vfpv3 tls vfpv4 idiva idivt vfpd32 lpae evtstrm CPU implementer : 0x41 CPU architecture: 7 CPU variant : 0x0 CPU part : 0xc07 CPU revision : 5processor : 1 model name : ARMv7 Processor rev 5 (v7l) BogoMIPS : 38.40 Features : half thumb fastmult vfp edsp neon vfpv3 tls vfpv4 idiva idivt vfpd32 lpae evtstrm CPU implementer : 0x41 CPU architecture: 7 CPU variant : 0x0 CPU part : 0xc07 CPU revision : 5processor : 2 model name : ARMv7 Processor rev 5 (v7l) BogoMIPS : 38.40 Features : half thumb fastmult vfp edsp neon vfpv3 tls vfpv4 idiva idivt vfpd32 lpae evtstrm CPU implementer : 0x41 CPU architecture: 7 CPU variant : 0x0 CPU part : 0xc07 CPU revision : 5processor : 3 model name : ARMv7 Processor rev 5 (v7l) BogoMIPS : 38.40 Features : half thumb fastmult vfp edsp neon vfpv3 tls vfpv4 idiva idivt vfpd32 lpae evtstrm CPU implementer : 0x41 CPU architecture: 7 CPU variant : 0x0 CPU part : 0xc07 CPU revision : 5Hardware : BCM2709 Revision : a21041 Serial : 00000000c15e9432 pi@raspberrypi ~ $
Model and Pi Revision
256MB
Hardware Revision Code from cpuinfo
Model B Revision 1.0
256MB
0002
Model B Revision 1.0 + ECN0001 (no fuses, D14 removed)
256MB
0003
Model B Revision 2.0 Mounting holes
256MB
0004 0005 0006
Model A Mounting holes
256MB
0007 0008 0009
Model B Revision 2.0 Mounting holes
512MB
000d 000e 000f
Model B+
512MB
0010
Compute Module
512MB
0011
Model A+
256MB
0012
Pi 2 Model B
1GB
a01041 (Sony, UK) a21041 (Embest, China)
PiZero
512MB
900092(no camera connector) 900093(camera connector)
Any IMU or TFT can be used, however the code would need to be updated to accommodate the different devices. It is best to use a 480×320 TFT as the images are scaled to fit this resolution.
This guide assumes that some basic understanding of an IMU(Accelerometer and Gyroscope) is already known. And you have one already working with your Raspberry Pi.
If you don’t, we do have some guides which covers this.
We have used our existing python code to read the values from the IMU, however we have removed the code related to the magnetometer as it isn’t needed for this project.
Git repository here The code can be pulled down to your Raspberry Pi with;
The IMU can be attached anywhere, however it is best to place it in the same orientation as shown below. If you do change the orientation, you will need to update the code accordingly.
We have updated to the python code in our git repo.
It now includes;
The elusive Kalman filter.
Math needed when the IMU is upside down
Automatically calculate loop period.
A lot more comments.
What is a Kalman filter? In a nutshell; A Kalman filter is, it is an algorithm which uses a series of measurements observed over time, in this context an accelerometer and a gyroscope. These measurements will contain noise that will contribute to the error of the measurement. The Kalman filter will then try to estimate the state of the system, based on the current and previous states, that tend to be more precise that than the measurements alone.
A Kalman filter is more precise than a Complementary filter. This can be seen in the image below, which is the output of a complementary filter (CFangleX) and a Kalman filter (kalmanX) from the X axis plotted in a graph.
The red line (KalmanX) is better at filtering out noisep;
The code can be found here in our Git repository here And can be pulled down to your Raspberry Pi with;