I have been asked a few times now how I got my GCS basics up and running. MAVLink is a rather complicated protocol to implement. The documentation is rather thin and partially outdated... Not an easy thing, if you are no experienced developer...

I'm no pro developer by a long shot. I speak reasonably well C and I did some smaller projects in JAVA. All in all, I can hold my own but can't do nor understand really fancy stuff. Without the help of Pat Hickey, who answered many of my questions on the mailing list, I wouldn't have gotten very far, so first of all, thanks again to him and the others!

Now, how do we get a MAVLink interpreter going?

The first thing to do would be to snatch a copy of the GCS_MAVLink library from the Arducopter project. You will also need AP_Common, AP_Math and FastSerial for dependencies. FastSerial must be the first to be included in your sketch.

Then, go an grab the code of ArduStationII. When you have that, open 2 windows: One with the code of MAVLink.pde from ArduStation2, the other in the GCS_MAVLink library subdir include/mavlink/v1.0/common/

Then, in MAVLink.pde, look at void gcs_handleMessage(mavlink_message_t* msg). This function is called by gcs_update and does the main decoding work. Basically, it's a huge switch-case block which switches on the message id of the received package. Let's have a look at one case block:

// decode
mavlink_attitude_t packet;
mavlink_msg_attitude_decode(msg, &packet);
pitch = toDeg(packet.pitch);
yaw = toDeg(packet.yaw);
roll = toDeg(packet.roll);

That doesn't look so complicated, does it? ArduStationII works mainly with global variables for all the interesting parameters. So what they do is, for everything they want, they knit a case block, fishing for the right message id, then call the respective decode method and assign the values to their global variables.

Let's have a look at something that isn't included in ArduStationII. In the common directory, search for mavlink_msg_vfr_hud.h and open it in an editor.

The very first thing in this file is the definition of what's in a MAVLINK_MSG_VFR_HUD packet:

typedef struct __mavlink_vfr_hud_t
float airspeed; ///< Current airspeed in m/s
float groundspeed; ///< Current ground speed in m/s
float alt; ///< Current altitude (MSL), in meters
float climb; ///< Current climb rate in meters/second
int16_t heading; ///< Current heading in degrees, in compass units (0..360, 0=north)
uint16_t throttle; ///< Current throttle setting in integer percent, 0 to 100
} mavlink_vfr_hud_t;

Let's say, we want the heading... If you scroll down a bit, you find the decode function...

static inline void mavlink_msg_vfr_hud_decode(const mavlink_message_t* msg, mavlink_vfr_hud_t* vfr_hud)

Seems, like we have everything. Now you just need to define a global variable for the heading...

int heading;

and write the respective case block:

mavlink_vfr_hud_t packet;
mavlink_msg_vfr_hud_decode(msg, &packet);
heading = packet.heading;

Now there is only one more thing to do. Normally, the APM sends the VFR_HUD message rather rarely. You have to tell it to do it more often. In MAVLink.pde, scroll down until you find the start_feeds function. VFR_HUD is a stream in the EXTRA2 category ;). You can find out, which message stream is in which category from the GCS_MAVLink.pde in the Arducopter project :).

Have fun coding!

E-mail me when people leave their comments –

You need to be a member of diydrones to add comments!

Join diydrones


  • Sorry about the blooper.
    SO I was saying that I have no idea that weather I should use the complete code and include all the libraries. Plus can I access the values only on the serial port monitor?
    I am a beginner and any help would be appreciated.
  • Hi Stefan,
    I want to read the basic paramters from APM like imu, roll,pitch yaw etc. I want to get this data through an Arduino Uno. I have no idea ho
  • Hi Stefan,
    I want to read the basic paramters from APM like imu, roll,pitch yaw etc. I want to get this data through an Arduino Uno. I have no idea ho
  • That depends what you want to do. Read the code of ArduStation :).

  • Stefan,

    Am I adding this to MAVLink.pde or am I creating a separate sketch that uses the above and calls the correct libraries?

  • @Edit to previous post: The telemetry is attached to APM 2.5 as usual. I am just interfacing RPi for some networking needs and alongside RPi has a small camera attached which also I wish to control via GCS with my custom (say MavLink) commands..

    Eagerly jumping to hear answers :)

  • Hi,

    Good tutorial, thank you. I am interfacing Raspberry PI with APM 2.5. Can someone tell me how do I communicate with MaVLink between these two boards, change some values in real-time (like change mode from Stabilize-> Loiter) and still interact with the Mission Planner (GCS) on my laptop?

    There are so many out there ROS, MavProxy, MavLink. Which is more suitable and why?

    Any help is appreciated.

  • Ignore my last comment, have worked it out :)

  • so close but yet so far... sorry to be a complete noob but how do I get the code from github? All it lets me do is navigate down the file structure?

  • Developer

    Thanks a lot! should help with my RPi GCS

This reply was deleted.