<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>http://wiki.paparazziuav.org/w/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Lethargi</id>
	<title>PaparazziUAV - User contributions [en]</title>
	<link rel="self" type="application/atom+xml" href="http://wiki.paparazziuav.org/w/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Lethargi"/>
	<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/wiki/Special:Contributions/Lethargi"/>
	<updated>2026-04-08T05:18:12Z</updated>
	<subtitle>User contributions</subtitle>
	<generator>MediaWiki 1.37.1</generator>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Load_Screenshots_from_FlightGear&amp;diff=24120</id>
		<title>Load Screenshots from FlightGear</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Load_Screenshots_from_FlightGear&amp;diff=24120"/>
		<updated>2018-11-08T13:09:16Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: Removed the &amp;quot;work in progress&amp;quot; tag&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This page describes the steps required to obtain screenshots from FlightGear into the memory of PaparazziUAV. First the required functions are presented and described. Than the exact details about running the applications are mentioned. This has been tested with PaparazziUAV v5.10 and FlightGear 2017.1.2.&lt;br /&gt;
&lt;br /&gt;
== Required functions and libraries ==&lt;br /&gt;
&lt;br /&gt;
FlightGear can be run with an HTTP server which can be used to obtain screenshots of the current scenery in FlightGear. There is a limit to the rate at which these screenshots (I only tested this with approximately 1 fps) can be obtained thus it cannot be used to simulate high frame rate vision. One requires the libcurl library to download the image from the HTTP server into memory. Following this, the jpeg image data needs to be decompressed to obtain the pixel values using libjpeg. All of this code have been obtained from the reference material of the corresponding libraries and required modifications made for the specific implementation. Note that in order to indicate to the compiler that libcurl and libjpeg &lt;br /&gt;
&lt;br /&gt;
Before doing anything a module needs to be added to PaparazziUAV ([[Modules#Make_your_own|create a module]]). By using the 3 functions below (WriteMemoryCallback, curl2mem, get_bmp) one can download the screenshot from the FlightGear HTTP server and convert the jpeg image into bitmap data. The WriteMemoryCallback is a function that is used by the libcurl function ''curl_easy_setopt'' to write the downloaded data into the memory. The function curl2mem takes the pointer to a MemoryStruct structure as input. This structure contains two elements namely a pointer to memory and the size of the memory. curl2mem basically writes the information from http://localhost:1234/screenshot (this is where FlightGear will have its screenshot) to a predefined memory location.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
struct MemoryStruct&lt;br /&gt;
{&lt;br /&gt;
  char *memory;&lt;br /&gt;
  size_t size;&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
static size_t WriteMemoryCallback(void *contents, size_t size, size_t nmemb, void *userp)&lt;br /&gt;
{&lt;br /&gt;
    /* Helper function for curl2mem. Handles the writing of the data from&lt;br /&gt;
     * the source HTTP into the memory. Needs to follow format provided by&lt;br /&gt;
     * libcurl.&lt;br /&gt;
     */&lt;br /&gt;
  size_t realsize = size * nmemb;&lt;br /&gt;
  struct MemoryStruct *mem = (struct MemoryStruct *)userp;&lt;br /&gt;
&lt;br /&gt;
  mem-&amp;gt;memory = realloc(mem-&amp;gt;memory, mem-&amp;gt;size + realsize + 1);&lt;br /&gt;
  if(mem-&amp;gt;memory == NULL) {&lt;br /&gt;
    /* out of memory! */&lt;br /&gt;
    printf(&amp;quot;not enough memory (realloc returned NULL)\n&amp;quot;);&lt;br /&gt;
    return 0;&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  memcpy(&amp;amp;(mem-&amp;gt;memory[mem-&amp;gt;size]), contents, realsize);&lt;br /&gt;
  mem-&amp;gt;size += realsize;&lt;br /&gt;
  mem-&amp;gt;memory[mem-&amp;gt;size] = 0;&lt;br /&gt;
&lt;br /&gt;
  return realsize;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
void curl2mem(struct MemoryStruct *chunk)&lt;br /&gt;
{&lt;br /&gt;
    /* Uses libcurl functions to load the screenshot from the FlightGear HTTP&lt;br /&gt;
     * server into the programs memory&lt;br /&gt;
     */&lt;br /&gt;
  CURL *curl_handle;&lt;br /&gt;
  CURLcode res;&lt;br /&gt;
&lt;br /&gt;
  curl_global_init(CURL_GLOBAL_ALL);&lt;br /&gt;
&lt;br /&gt;
  /* init the curl session */&lt;br /&gt;
  curl_handle = curl_easy_init();&lt;br /&gt;
&lt;br /&gt;
  /* specify URL to get */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_URL, &amp;quot;http://localhost:1234/screenshot&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
  /* send all data to this function  */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_WRITEFUNCTION, WriteMemoryCallback);&lt;br /&gt;
&lt;br /&gt;
  /* we pass our 'chunk' struct to the callback function */&lt;br /&gt;
  // curl_easy_setopt(curl_handle, CURLOPT_WRITEDATA, (void *)&amp;amp;chunk);&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_WRITEDATA, (void *)chunk);&lt;br /&gt;
&lt;br /&gt;
  /* some servers don't like requests that are made without a user-agent&lt;br /&gt;
     field, so we provide one */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_USERAGENT, &amp;quot;libcurl-agent/1.0&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
  /* get it! */&lt;br /&gt;
  res = curl_easy_perform(curl_handle);&lt;br /&gt;
&lt;br /&gt;
  /* check for errors */&lt;br /&gt;
  if(res != CURLE_OK) {&lt;br /&gt;
    fprintf(stderr, &amp;quot;curl_easy_perform() failed: %s\n&amp;quot;,&lt;br /&gt;
            curl_easy_strerror(res));&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  /* cleanup curl stuff */&lt;br /&gt;
  curl_easy_cleanup(curl_handle);&lt;br /&gt;
&lt;br /&gt;
  /* we're done with libcurl, so clean it up */&lt;br /&gt;
  curl_global_cleanup();&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
After obtaining the jpeg screenshot, it is decompressed to obtain the pixel data. This is done by the get_bmp function which takes 3 input parameters. The first input is a pointer to the chunk of memory containing the jpeg data. The second one is the total length of the memory chunk (i.e. the jpeg data) in bytes. The last input is a pointer to a structure which contains the decompressed pixel data from the jpeg file.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
struct BmpStruct&lt;br /&gt;
{&lt;br /&gt;
    unsigned char *buffer;&lt;br /&gt;
    unsigned long size;&lt;br /&gt;
    uint16_t width;&lt;br /&gt;
    uint16_t height;&lt;br /&gt;
    uint8_t pixel_size;&lt;br /&gt;
    uint16_t row_stride;&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
uint8_t get_bmp(unsigned char *jpg_buffer, unsigned long jpg_size, struct BmpStruct *bmp)&lt;br /&gt;
{&lt;br /&gt;
    // // INTIALIZE&lt;br /&gt;
    uint8_t rc;&lt;br /&gt;
	// Variables for the decompressor itself&lt;br /&gt;
	struct jpeg_decompress_struct cinfo;&lt;br /&gt;
	struct jpeg_error_mgr jerr;&lt;br /&gt;
&lt;br /&gt;
	// Variables for the output buffer, and how long each row is&lt;br /&gt;
	unsigned long bmp_size;&lt;br /&gt;
	unsigned char *bmp_buffer;&lt;br /&gt;
	uint16_t row_stride, width, height, pixel_size;&lt;br /&gt;
&lt;br /&gt;
    // holds the output bmp and its metadata&lt;br /&gt;
&lt;br /&gt;
    // // SETUP AND CHECK&lt;br /&gt;
	cinfo.err = jpeg_std_error(&amp;amp;jerr);&lt;br /&gt;
	jpeg_create_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
	jpeg_mem_src(&amp;amp;cinfo, jpg_buffer, jpg_size);&lt;br /&gt;
&lt;br /&gt;
    // 	skipping error check for now. file should be JPEG&lt;br /&gt;
	rc = jpeg_read_header(&amp;amp;cinfo, TRUE);&lt;br /&gt;
	if (rc != 1) {&lt;br /&gt;
        printf(&amp;quot;File to get_bmp() not JPEG&amp;quot;);&lt;br /&gt;
        return 1;&lt;br /&gt;
	}&lt;br /&gt;
&lt;br /&gt;
	jpeg_start_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
	width = cinfo.output_width;&lt;br /&gt;
	height = cinfo.output_height;&lt;br /&gt;
	pixel_size = cinfo.output_components;&lt;br /&gt;
&lt;br /&gt;
	bmp_size = width * height * pixel_size;&lt;br /&gt;
	bmp_buffer = (unsigned char*) malloc(bmp_size);&lt;br /&gt;
&lt;br /&gt;
	// The row_stride is the total number of bytes it takes to store an&lt;br /&gt;
	// entire scanline (row).&lt;br /&gt;
	row_stride = width * pixel_size;&lt;br /&gt;
&lt;br /&gt;
    // // READ THE LINES&lt;br /&gt;
	while (cinfo.output_scanline &amp;lt; cinfo.output_height) {&lt;br /&gt;
		unsigned char *buffer_array[1];&lt;br /&gt;
		buffer_array[0] = bmp_buffer + (cinfo.output_scanline) * row_stride;&lt;br /&gt;
&lt;br /&gt;
		jpeg_read_scanlines(&amp;amp;cinfo, buffer_array, 1);&lt;br /&gt;
&lt;br /&gt;
	}&lt;br /&gt;
&lt;br /&gt;
    bmp-&amp;gt;buffer = bmp_buffer;&lt;br /&gt;
    bmp-&amp;gt;size = bmp_size;&lt;br /&gt;
    bmp-&amp;gt;width = width;&lt;br /&gt;
    bmp-&amp;gt;height = height;&lt;br /&gt;
    bmp-&amp;gt;pixel_size = pixel_size;&lt;br /&gt;
&lt;br /&gt;
	jpeg_finish_decompress(&amp;amp;cinfo);&lt;br /&gt;
	jpeg_destroy_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
    return 0;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The sum_blues function below is an example of a function that uses the obtained pixel data from the FlightGear screenshot to sum up all the blue pixels. It iterates over all the bytes in the decompressed image which are for the blue channel of each pixel and sums them.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
uint8_t sum_blues(void)&lt;br /&gt;
{&lt;br /&gt;
    struct MemoryStruct chunk; // structure holding download data&lt;br /&gt;
    chunk.memory = malloc(1);&lt;br /&gt;
    chunk.size = 0;&lt;br /&gt;
&lt;br /&gt;
    struct BmpStruct bmp; // structure holding decompressed image&lt;br /&gt;
&lt;br /&gt;
    // download the jpeg into internal memory&lt;br /&gt;
    curl2mem(&amp;amp;chunk);&lt;br /&gt;
&lt;br /&gt;
    // decompress the image and store it in preallocated structure&lt;br /&gt;
    get_bmp((unsigned char*)chunk.memory, chunk.size, &amp;amp;bmp);&lt;br /&gt;
&lt;br /&gt;
    // free up memory of downloaded jpeg&lt;br /&gt;
    free(chunk.memory);&lt;br /&gt;
&lt;br /&gt;
    uint32_t bluesum = 0;&lt;br /&gt;
    unsigned long curinc = 2;&lt;br /&gt;
    unsigned char *curby;&lt;br /&gt;
    while (curinc &amp;lt;= bmp.size) {&lt;br /&gt;
        curby = bmp.buffer + curinc;&lt;br /&gt;
        bluesum += *curby;&lt;br /&gt;
        curinc = curinc + 3;&lt;br /&gt;
    }&lt;br /&gt;
    printf(&amp;quot;BlueSum: %d\n&amp;quot;,bluesum);&lt;br /&gt;
&lt;br /&gt;
    // free up memory of the bmp&lt;br /&gt;
    free(bmp.buffer);&lt;br /&gt;
&lt;br /&gt;
    return 0;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The user needs to make required implementation and plumbing to call these functions. They can be called by the users modules or through blocks in the flight plans.&lt;br /&gt;
&lt;br /&gt;
== Running the application ==&lt;br /&gt;
&lt;br /&gt;
After creating the required modules and functions, one must start FlightGear and the PaparazziUAV with settings that allow them to communicate with each other. I obtained the information for how to do this from [http://lists.paparazziuav.org/Paparazzi-and-Flightgear-td17704.html this] page.&lt;br /&gt;
&lt;br /&gt;
First, FlightGear should be started with the following command:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source&amp;gt;&lt;br /&gt;
fgfs --fdm=null --native-gui=socket,in,30,,5501,udp &lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
There are many other options for FlightGear; refer to [http://wiki.flightgear.org/Command_line_options this] page for details. One may want to include their own 3D models into the environment when trying to simulate computer vision functionalities. The way to do this has been described in this [http://wiki.flightgear.org/Howto:Place_3D_objects_with_the_UFO page] of the FlightGear wiki.&lt;br /&gt;
&lt;br /&gt;
Second, an extra flag needs to be included when running the simulator of PaparazziUAV.&lt;br /&gt;
&amp;lt;source&amp;gt;&lt;br /&gt;
--fg_host 127.0.0.1&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This should be typed in the text box running the simulator in the [https://wiki.paparazziuav.org/wiki/Paparazzi_Center Paparazzi center]. Note that in order to speed up or pause the simulation one has to run it from the terminal as described [https://wiki.paparazziuav.org/wiki/NPS#Pausing_or_running_the_sim_at_a_different_speed here].&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Load_Screenshots_from_FlightGear&amp;diff=24119</id>
		<title>Load Screenshots from FlightGear</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Load_Screenshots_from_FlightGear&amp;diff=24119"/>
		<updated>2018-11-08T13:08:13Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: Filled the &amp;quot;running the application&amp;quot; section of the page&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;'''WORK IN PROGRESS'''&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This page describes the steps required to obtain screenshots from FlightGear into the memory of PaparazziUAV. First the required functions are presented and described. Than the exact details about running the applications are mentioned. This has been tested with PaparazziUAV v5.10 and FlightGear 2017.1.2.&lt;br /&gt;
&lt;br /&gt;
== Required functions and libraries ==&lt;br /&gt;
&lt;br /&gt;
FlightGear can be run with an HTTP server which can be used to obtain screenshots of the current scenery in FlightGear. There is a limit to the rate at which these screenshots (I only tested this with approximately 1 fps) can be obtained thus it cannot be used to simulate high frame rate vision. One requires the libcurl library to download the image from the HTTP server into memory. Following this, the jpeg image data needs to be decompressed to obtain the pixel values using libjpeg. All of this code have been obtained from the reference material of the corresponding libraries and required modifications made for the specific implementation. Note that in order to indicate to the compiler that libcurl and libjpeg &lt;br /&gt;
&lt;br /&gt;
Before doing anything a module needs to be added to PaparazziUAV ([[Modules#Make_your_own|create a module]]). By using the 3 functions below (WriteMemoryCallback, curl2mem, get_bmp) one can download the screenshot from the FlightGear HTTP server and convert the jpeg image into bitmap data. The WriteMemoryCallback is a function that is used by the libcurl function ''curl_easy_setopt'' to write the downloaded data into the memory. The function curl2mem takes the pointer to a MemoryStruct structure as input. This structure contains two elements namely a pointer to memory and the size of the memory. curl2mem basically writes the information from http://localhost:1234/screenshot (this is where FlightGear will have its screenshot) to a predefined memory location.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
struct MemoryStruct&lt;br /&gt;
{&lt;br /&gt;
  char *memory;&lt;br /&gt;
  size_t size;&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
static size_t WriteMemoryCallback(void *contents, size_t size, size_t nmemb, void *userp)&lt;br /&gt;
{&lt;br /&gt;
    /* Helper function for curl2mem. Handles the writing of the data from&lt;br /&gt;
     * the source HTTP into the memory. Needs to follow format provided by&lt;br /&gt;
     * libcurl.&lt;br /&gt;
     */&lt;br /&gt;
  size_t realsize = size * nmemb;&lt;br /&gt;
  struct MemoryStruct *mem = (struct MemoryStruct *)userp;&lt;br /&gt;
&lt;br /&gt;
  mem-&amp;gt;memory = realloc(mem-&amp;gt;memory, mem-&amp;gt;size + realsize + 1);&lt;br /&gt;
  if(mem-&amp;gt;memory == NULL) {&lt;br /&gt;
    /* out of memory! */&lt;br /&gt;
    printf(&amp;quot;not enough memory (realloc returned NULL)\n&amp;quot;);&lt;br /&gt;
    return 0;&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  memcpy(&amp;amp;(mem-&amp;gt;memory[mem-&amp;gt;size]), contents, realsize);&lt;br /&gt;
  mem-&amp;gt;size += realsize;&lt;br /&gt;
  mem-&amp;gt;memory[mem-&amp;gt;size] = 0;&lt;br /&gt;
&lt;br /&gt;
  return realsize;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
void curl2mem(struct MemoryStruct *chunk)&lt;br /&gt;
{&lt;br /&gt;
    /* Uses libcurl functions to load the screenshot from the FlightGear HTTP&lt;br /&gt;
     * server into the programs memory&lt;br /&gt;
     */&lt;br /&gt;
  CURL *curl_handle;&lt;br /&gt;
  CURLcode res;&lt;br /&gt;
&lt;br /&gt;
  curl_global_init(CURL_GLOBAL_ALL);&lt;br /&gt;
&lt;br /&gt;
  /* init the curl session */&lt;br /&gt;
  curl_handle = curl_easy_init();&lt;br /&gt;
&lt;br /&gt;
  /* specify URL to get */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_URL, &amp;quot;http://localhost:1234/screenshot&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
  /* send all data to this function  */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_WRITEFUNCTION, WriteMemoryCallback);&lt;br /&gt;
&lt;br /&gt;
  /* we pass our 'chunk' struct to the callback function */&lt;br /&gt;
  // curl_easy_setopt(curl_handle, CURLOPT_WRITEDATA, (void *)&amp;amp;chunk);&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_WRITEDATA, (void *)chunk);&lt;br /&gt;
&lt;br /&gt;
  /* some servers don't like requests that are made without a user-agent&lt;br /&gt;
     field, so we provide one */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_USERAGENT, &amp;quot;libcurl-agent/1.0&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
  /* get it! */&lt;br /&gt;
  res = curl_easy_perform(curl_handle);&lt;br /&gt;
&lt;br /&gt;
  /* check for errors */&lt;br /&gt;
  if(res != CURLE_OK) {&lt;br /&gt;
    fprintf(stderr, &amp;quot;curl_easy_perform() failed: %s\n&amp;quot;,&lt;br /&gt;
            curl_easy_strerror(res));&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  /* cleanup curl stuff */&lt;br /&gt;
  curl_easy_cleanup(curl_handle);&lt;br /&gt;
&lt;br /&gt;
  /* we're done with libcurl, so clean it up */&lt;br /&gt;
  curl_global_cleanup();&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
After obtaining the jpeg screenshot, it is decompressed to obtain the pixel data. This is done by the get_bmp function which takes 3 input parameters. The first input is a pointer to the chunk of memory containing the jpeg data. The second one is the total length of the memory chunk (i.e. the jpeg data) in bytes. The last input is a pointer to a structure which contains the decompressed pixel data from the jpeg file.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
struct BmpStruct&lt;br /&gt;
{&lt;br /&gt;
    unsigned char *buffer;&lt;br /&gt;
    unsigned long size;&lt;br /&gt;
    uint16_t width;&lt;br /&gt;
    uint16_t height;&lt;br /&gt;
    uint8_t pixel_size;&lt;br /&gt;
    uint16_t row_stride;&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
uint8_t get_bmp(unsigned char *jpg_buffer, unsigned long jpg_size, struct BmpStruct *bmp)&lt;br /&gt;
{&lt;br /&gt;
    // // INTIALIZE&lt;br /&gt;
    uint8_t rc;&lt;br /&gt;
	// Variables for the decompressor itself&lt;br /&gt;
	struct jpeg_decompress_struct cinfo;&lt;br /&gt;
	struct jpeg_error_mgr jerr;&lt;br /&gt;
&lt;br /&gt;
	// Variables for the output buffer, and how long each row is&lt;br /&gt;
	unsigned long bmp_size;&lt;br /&gt;
	unsigned char *bmp_buffer;&lt;br /&gt;
	uint16_t row_stride, width, height, pixel_size;&lt;br /&gt;
&lt;br /&gt;
    // holds the output bmp and its metadata&lt;br /&gt;
&lt;br /&gt;
    // // SETUP AND CHECK&lt;br /&gt;
	cinfo.err = jpeg_std_error(&amp;amp;jerr);&lt;br /&gt;
	jpeg_create_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
	jpeg_mem_src(&amp;amp;cinfo, jpg_buffer, jpg_size);&lt;br /&gt;
&lt;br /&gt;
    // 	skipping error check for now. file should be JPEG&lt;br /&gt;
	rc = jpeg_read_header(&amp;amp;cinfo, TRUE);&lt;br /&gt;
	if (rc != 1) {&lt;br /&gt;
        printf(&amp;quot;File to get_bmp() not JPEG&amp;quot;);&lt;br /&gt;
        return 1;&lt;br /&gt;
	}&lt;br /&gt;
&lt;br /&gt;
	jpeg_start_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
	width = cinfo.output_width;&lt;br /&gt;
	height = cinfo.output_height;&lt;br /&gt;
	pixel_size = cinfo.output_components;&lt;br /&gt;
&lt;br /&gt;
	bmp_size = width * height * pixel_size;&lt;br /&gt;
	bmp_buffer = (unsigned char*) malloc(bmp_size);&lt;br /&gt;
&lt;br /&gt;
	// The row_stride is the total number of bytes it takes to store an&lt;br /&gt;
	// entire scanline (row).&lt;br /&gt;
	row_stride = width * pixel_size;&lt;br /&gt;
&lt;br /&gt;
    // // READ THE LINES&lt;br /&gt;
	while (cinfo.output_scanline &amp;lt; cinfo.output_height) {&lt;br /&gt;
		unsigned char *buffer_array[1];&lt;br /&gt;
		buffer_array[0] = bmp_buffer + (cinfo.output_scanline) * row_stride;&lt;br /&gt;
&lt;br /&gt;
		jpeg_read_scanlines(&amp;amp;cinfo, buffer_array, 1);&lt;br /&gt;
&lt;br /&gt;
	}&lt;br /&gt;
&lt;br /&gt;
    bmp-&amp;gt;buffer = bmp_buffer;&lt;br /&gt;
    bmp-&amp;gt;size = bmp_size;&lt;br /&gt;
    bmp-&amp;gt;width = width;&lt;br /&gt;
    bmp-&amp;gt;height = height;&lt;br /&gt;
    bmp-&amp;gt;pixel_size = pixel_size;&lt;br /&gt;
&lt;br /&gt;
	jpeg_finish_decompress(&amp;amp;cinfo);&lt;br /&gt;
	jpeg_destroy_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
    return 0;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The sum_blues function below is an example of a function that uses the obtained pixel data from the FlightGear screenshot to sum up all the blue pixels. It iterates over all the bytes in the decompressed image which are for the blue channel of each pixel and sums them.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
uint8_t sum_blues(void)&lt;br /&gt;
{&lt;br /&gt;
    struct MemoryStruct chunk; // structure holding download data&lt;br /&gt;
    chunk.memory = malloc(1);&lt;br /&gt;
    chunk.size = 0;&lt;br /&gt;
&lt;br /&gt;
    struct BmpStruct bmp; // structure holding decompressed image&lt;br /&gt;
&lt;br /&gt;
    // download the jpeg into internal memory&lt;br /&gt;
    curl2mem(&amp;amp;chunk);&lt;br /&gt;
&lt;br /&gt;
    // decompress the image and store it in preallocated structure&lt;br /&gt;
    get_bmp((unsigned char*)chunk.memory, chunk.size, &amp;amp;bmp);&lt;br /&gt;
&lt;br /&gt;
    // free up memory of downloaded jpeg&lt;br /&gt;
    free(chunk.memory);&lt;br /&gt;
&lt;br /&gt;
    uint32_t bluesum = 0;&lt;br /&gt;
    unsigned long curinc = 2;&lt;br /&gt;
    unsigned char *curby;&lt;br /&gt;
    while (curinc &amp;lt;= bmp.size) {&lt;br /&gt;
        curby = bmp.buffer + curinc;&lt;br /&gt;
        bluesum += *curby;&lt;br /&gt;
        curinc = curinc + 3;&lt;br /&gt;
    }&lt;br /&gt;
    printf(&amp;quot;BlueSum: %d\n&amp;quot;,bluesum);&lt;br /&gt;
&lt;br /&gt;
    // free up memory of the bmp&lt;br /&gt;
    free(bmp.buffer);&lt;br /&gt;
&lt;br /&gt;
    return 0;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The user needs to make required implementation and plumbing to call these functions. They can be called by the users modules or through blocks in the flight plans.&lt;br /&gt;
&lt;br /&gt;
== Running the application ==&lt;br /&gt;
&lt;br /&gt;
After creating the required modules and functions, one must start FlightGear and the PaparazziUAV with settings that allow them to communicate with each other. I obtained the information for how to do this from [http://lists.paparazziuav.org/Paparazzi-and-Flightgear-td17704.html this] page.&lt;br /&gt;
&lt;br /&gt;
First, FlightGear should be started with the following command:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source&amp;gt;&lt;br /&gt;
fgfs --fdm=null --native-gui=socket,in,30,,5501,udp &lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
There are many other options for FlightGear; refer to [http://wiki.flightgear.org/Command_line_options this] page for details. One may want to include their own 3D models into the environment when trying to simulate computer vision functionalities. The way to do this has been described in this [http://wiki.flightgear.org/Howto:Place_3D_objects_with_the_UFO page] of the FlightGear wiki.&lt;br /&gt;
&lt;br /&gt;
Second, an extra flag needs to be included when running the simulator of PaparazziUAV.&lt;br /&gt;
&amp;lt;source&amp;gt;&lt;br /&gt;
--fg_host 127.0.0.1&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This should be typed in the text box running the simulator in the [https://wiki.paparazziuav.org/wiki/Paparazzi_Center Paparazzi center]. Note that in order to speed up or pause the simulation one has to run it from the terminal as described [https://wiki.paparazziuav.org/wiki/NPS#Pausing_or_running_the_sim_at_a_different_speed here].&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Load_Screenshots_from_FlightGear&amp;diff=24118</id>
		<title>Load Screenshots from FlightGear</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Load_Screenshots_from_FlightGear&amp;diff=24118"/>
		<updated>2018-11-08T12:32:33Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: Adding final information on how the functions should be called&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;'''WORK IN PROGRESS'''&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This page describes the steps required to obtain screenshots from FlightGear into the memory of PaparazziUAV. First the required functions are presented and described. Than the exact details about running the applications are mentioned. This has been tested with PaparazziUAV v5.10 and FlightGear 2017.1.2.&lt;br /&gt;
&lt;br /&gt;
== Required functions and libraries ==&lt;br /&gt;
&lt;br /&gt;
FlightGear can be run with an HTTP server which can be used to obtain screenshots of the current scenery in FlightGear. There is a limit to the rate at which these screenshots (I only tested this with approximately 1 fps) can be obtained thus it cannot be used to simulate high frame rate vision. One requires the libcurl library to download the image from the HTTP server into memory. Following this, the jpeg image data needs to be decompressed to obtain the pixel values using libjpeg. All of this code have been obtained from the reference material of the corresponding libraries and required modifications made for the specific implementation. Note that in order to indicate to the compiler that libcurl and libjpeg &lt;br /&gt;
&lt;br /&gt;
Before doing anything a module needs to be added to PaparazziUAV ([[Modules#Make_your_own|create a module]]). By using the 3 functions below (WriteMemoryCallback, curl2mem, get_bmp) one can download the screenshot from the FlightGear HTTP server and convert the jpeg image into bitmap data. The WriteMemoryCallback is a function that is used by the libcurl function ''curl_easy_setopt'' to write the downloaded data into the memory. The function curl2mem takes the pointer to a MemoryStruct structure as input. This structure contains two elements namely a pointer to memory and the size of the memory. curl2mem basically writes the information from http://localhost:1234/screenshot (this is where FlightGear will have its screenshot) to a predefined memory location.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
struct MemoryStruct&lt;br /&gt;
{&lt;br /&gt;
  char *memory;&lt;br /&gt;
  size_t size;&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
static size_t WriteMemoryCallback(void *contents, size_t size, size_t nmemb, void *userp)&lt;br /&gt;
{&lt;br /&gt;
    /* Helper function for curl2mem. Handles the writing of the data from&lt;br /&gt;
     * the source HTTP into the memory. Needs to follow format provided by&lt;br /&gt;
     * libcurl.&lt;br /&gt;
     */&lt;br /&gt;
  size_t realsize = size * nmemb;&lt;br /&gt;
  struct MemoryStruct *mem = (struct MemoryStruct *)userp;&lt;br /&gt;
&lt;br /&gt;
  mem-&amp;gt;memory = realloc(mem-&amp;gt;memory, mem-&amp;gt;size + realsize + 1);&lt;br /&gt;
  if(mem-&amp;gt;memory == NULL) {&lt;br /&gt;
    /* out of memory! */&lt;br /&gt;
    printf(&amp;quot;not enough memory (realloc returned NULL)\n&amp;quot;);&lt;br /&gt;
    return 0;&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  memcpy(&amp;amp;(mem-&amp;gt;memory[mem-&amp;gt;size]), contents, realsize);&lt;br /&gt;
  mem-&amp;gt;size += realsize;&lt;br /&gt;
  mem-&amp;gt;memory[mem-&amp;gt;size] = 0;&lt;br /&gt;
&lt;br /&gt;
  return realsize;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
void curl2mem(struct MemoryStruct *chunk)&lt;br /&gt;
{&lt;br /&gt;
    /* Uses libcurl functions to load the screenshot from the FlightGear HTTP&lt;br /&gt;
     * server into the programs memory&lt;br /&gt;
     */&lt;br /&gt;
  CURL *curl_handle;&lt;br /&gt;
  CURLcode res;&lt;br /&gt;
&lt;br /&gt;
  curl_global_init(CURL_GLOBAL_ALL);&lt;br /&gt;
&lt;br /&gt;
  /* init the curl session */&lt;br /&gt;
  curl_handle = curl_easy_init();&lt;br /&gt;
&lt;br /&gt;
  /* specify URL to get */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_URL, &amp;quot;http://localhost:1234/screenshot&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
  /* send all data to this function  */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_WRITEFUNCTION, WriteMemoryCallback);&lt;br /&gt;
&lt;br /&gt;
  /* we pass our 'chunk' struct to the callback function */&lt;br /&gt;
  // curl_easy_setopt(curl_handle, CURLOPT_WRITEDATA, (void *)&amp;amp;chunk);&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_WRITEDATA, (void *)chunk);&lt;br /&gt;
&lt;br /&gt;
  /* some servers don't like requests that are made without a user-agent&lt;br /&gt;
     field, so we provide one */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_USERAGENT, &amp;quot;libcurl-agent/1.0&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
  /* get it! */&lt;br /&gt;
  res = curl_easy_perform(curl_handle);&lt;br /&gt;
&lt;br /&gt;
  /* check for errors */&lt;br /&gt;
  if(res != CURLE_OK) {&lt;br /&gt;
    fprintf(stderr, &amp;quot;curl_easy_perform() failed: %s\n&amp;quot;,&lt;br /&gt;
            curl_easy_strerror(res));&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  /* cleanup curl stuff */&lt;br /&gt;
  curl_easy_cleanup(curl_handle);&lt;br /&gt;
&lt;br /&gt;
  /* we're done with libcurl, so clean it up */&lt;br /&gt;
  curl_global_cleanup();&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
After obtaining the jpeg screenshot, it is decompressed to obtain the pixel data. This is done by the get_bmp function which takes 3 input parameters. The first input is a pointer to the chunk of memory containing the jpeg data. The second one is the total length of the memory chunk (i.e. the jpeg data) in bytes. The last input is a pointer to a structure which contains the decompressed pixel data from the jpeg file.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
struct BmpStruct&lt;br /&gt;
{&lt;br /&gt;
    unsigned char *buffer;&lt;br /&gt;
    unsigned long size;&lt;br /&gt;
    uint16_t width;&lt;br /&gt;
    uint16_t height;&lt;br /&gt;
    uint8_t pixel_size;&lt;br /&gt;
    uint16_t row_stride;&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
uint8_t get_bmp(unsigned char *jpg_buffer, unsigned long jpg_size, struct BmpStruct *bmp)&lt;br /&gt;
{&lt;br /&gt;
    // // INTIALIZE&lt;br /&gt;
    uint8_t rc;&lt;br /&gt;
	// Variables for the decompressor itself&lt;br /&gt;
	struct jpeg_decompress_struct cinfo;&lt;br /&gt;
	struct jpeg_error_mgr jerr;&lt;br /&gt;
&lt;br /&gt;
	// Variables for the output buffer, and how long each row is&lt;br /&gt;
	unsigned long bmp_size;&lt;br /&gt;
	unsigned char *bmp_buffer;&lt;br /&gt;
	uint16_t row_stride, width, height, pixel_size;&lt;br /&gt;
&lt;br /&gt;
    // holds the output bmp and its metadata&lt;br /&gt;
&lt;br /&gt;
    // // SETUP AND CHECK&lt;br /&gt;
	cinfo.err = jpeg_std_error(&amp;amp;jerr);&lt;br /&gt;
	jpeg_create_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
	jpeg_mem_src(&amp;amp;cinfo, jpg_buffer, jpg_size);&lt;br /&gt;
&lt;br /&gt;
    // 	skipping error check for now. file should be JPEG&lt;br /&gt;
	rc = jpeg_read_header(&amp;amp;cinfo, TRUE);&lt;br /&gt;
	if (rc != 1) {&lt;br /&gt;
        printf(&amp;quot;File to get_bmp() not JPEG&amp;quot;);&lt;br /&gt;
        return 1;&lt;br /&gt;
	}&lt;br /&gt;
&lt;br /&gt;
	jpeg_start_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
	width = cinfo.output_width;&lt;br /&gt;
	height = cinfo.output_height;&lt;br /&gt;
	pixel_size = cinfo.output_components;&lt;br /&gt;
&lt;br /&gt;
	bmp_size = width * height * pixel_size;&lt;br /&gt;
	bmp_buffer = (unsigned char*) malloc(bmp_size);&lt;br /&gt;
&lt;br /&gt;
	// The row_stride is the total number of bytes it takes to store an&lt;br /&gt;
	// entire scanline (row).&lt;br /&gt;
	row_stride = width * pixel_size;&lt;br /&gt;
&lt;br /&gt;
    // // READ THE LINES&lt;br /&gt;
	while (cinfo.output_scanline &amp;lt; cinfo.output_height) {&lt;br /&gt;
		unsigned char *buffer_array[1];&lt;br /&gt;
		buffer_array[0] = bmp_buffer + (cinfo.output_scanline) * row_stride;&lt;br /&gt;
&lt;br /&gt;
		jpeg_read_scanlines(&amp;amp;cinfo, buffer_array, 1);&lt;br /&gt;
&lt;br /&gt;
	}&lt;br /&gt;
&lt;br /&gt;
    bmp-&amp;gt;buffer = bmp_buffer;&lt;br /&gt;
    bmp-&amp;gt;size = bmp_size;&lt;br /&gt;
    bmp-&amp;gt;width = width;&lt;br /&gt;
    bmp-&amp;gt;height = height;&lt;br /&gt;
    bmp-&amp;gt;pixel_size = pixel_size;&lt;br /&gt;
&lt;br /&gt;
	jpeg_finish_decompress(&amp;amp;cinfo);&lt;br /&gt;
	jpeg_destroy_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
    return 0;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The sum_blues function below is an example of a function that uses the obtained pixel data from the FlightGear screenshot to sum up all the blue pixels. It iterates over all the bytes in the decompressed image which are for the blue channel of each pixel and sums them.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
uint8_t sum_blues(void)&lt;br /&gt;
{&lt;br /&gt;
    struct MemoryStruct chunk; // structure holding download data&lt;br /&gt;
    chunk.memory = malloc(1);&lt;br /&gt;
    chunk.size = 0;&lt;br /&gt;
&lt;br /&gt;
    struct BmpStruct bmp; // structure holding decompressed image&lt;br /&gt;
&lt;br /&gt;
    // download the jpeg into internal memory&lt;br /&gt;
    curl2mem(&amp;amp;chunk);&lt;br /&gt;
&lt;br /&gt;
    // decompress the image and store it in preallocated structure&lt;br /&gt;
    get_bmp((unsigned char*)chunk.memory, chunk.size, &amp;amp;bmp);&lt;br /&gt;
&lt;br /&gt;
    // free up memory of downloaded jpeg&lt;br /&gt;
    free(chunk.memory);&lt;br /&gt;
&lt;br /&gt;
    uint32_t bluesum = 0;&lt;br /&gt;
    unsigned long curinc = 2;&lt;br /&gt;
    unsigned char *curby;&lt;br /&gt;
    while (curinc &amp;lt;= bmp.size) {&lt;br /&gt;
        curby = bmp.buffer + curinc;&lt;br /&gt;
        bluesum += *curby;&lt;br /&gt;
        curinc = curinc + 3;&lt;br /&gt;
    }&lt;br /&gt;
    printf(&amp;quot;BlueSum: %d\n&amp;quot;,bluesum);&lt;br /&gt;
&lt;br /&gt;
    // free up memory of the bmp&lt;br /&gt;
    free(bmp.buffer);&lt;br /&gt;
&lt;br /&gt;
    return 0;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The user needs to make required implementation and plumbing to call these functions. They can be called by the users modules or through blocks in the flight plans.&lt;br /&gt;
&lt;br /&gt;
== Running the application ==&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Telemetry&amp;diff=23847</id>
		<title>Telemetry</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Telemetry&amp;diff=23847"/>
		<updated>2017-09-15T09:19:50Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: /* Step 1 */ changed &amp;quot;conf/messages.xml&amp;quot; to &amp;quot;sw/ext/pprzlink/message_definitions/v1.0/messages.xml&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Messages ==&lt;br /&gt;
&lt;br /&gt;
Telemetry messages (sent from the aircraft to the ground) are defined in the telemetry class of [https://github.com/paparazzi/paparazzi/blob/master/conf/messages.xml conf/messages.xml].&lt;br /&gt;
See also the generated documentation: http://docs.paparazziuav.org/latest/paparazzi_messages.html&lt;br /&gt;
&lt;br /&gt;
== Sending periodic messages ==&lt;br /&gt;
The set of periodic messages sent over the downlink channel by an aircraft to the ground station is configurable&lt;br /&gt;
with the help of one XML file, located in the &amp;lt;tt&amp;gt;conf/telemetry&amp;lt;/tt&amp;gt; directory. This file is referenced by &amp;lt;tt&amp;gt;conf/conf.xml&amp;lt;/tt&amp;gt; and must follow the&lt;br /&gt;
&amp;lt;tt&amp;gt;telemetry.dtd&amp;lt;/tt&amp;gt; syntax. The &amp;lt;tt&amp;gt;fixedwing_default.xml&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;rotorcraft_default.xml&amp;lt;/tt&amp;gt; are provided as an example and should be suitable for most users.&lt;br /&gt;
{{Box Code|default.xml|&lt;br /&gt;
 &amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;!DOCTYPE telemetry SYSTEM &amp;quot;telemetry.dtd&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;telemetry&amp;gt;&lt;br /&gt;
  &amp;lt;process name=&amp;quot;Ap&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;default&amp;quot;&amp;gt;&lt;br /&gt;
     &amp;lt;message name=&amp;quot;ATTITUDE&amp;quot; period=&amp;quot;0.5&amp;quot;/&amp;gt;&lt;br /&gt;
     &amp;lt;message name=&amp;quot;PPRZ_MODE&amp;quot; period=&amp;quot;5&amp;quot;/&amp;gt;&lt;br /&gt;
     &amp;lt;message name=&amp;quot;SOME_MODULE_MSG&amp;quot; period=&amp;quot;2&amp;quot; module=&amp;quot;module_name&amp;quot;/&amp;gt;&lt;br /&gt;
     ...&lt;br /&gt;
    &amp;lt;/mode&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;fast attitude&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;ATTITUDE&amp;quot; period=&amp;quot;0.1&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/mode&amp;gt;&lt;br /&gt;
 &amp;lt;/process&amp;gt;&lt;br /&gt;
  &amp;lt;process name=&amp;quot;Fbw&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;default&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;COMMANDS&amp;quot; period=&amp;quot;1&amp;quot;/&amp;gt;&lt;br /&gt;
      ...&lt;br /&gt;
    &amp;lt;/mode&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;debug&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;PPM&amp;quot; period=&amp;quot;0.5&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/mode&amp;gt;&lt;br /&gt;
  &amp;lt;/process&amp;gt;&lt;br /&gt;
 &amp;lt;/telemetry&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
If a [[Modules|module]] attribute is specified for a message, it will be included in the telemetry only if the corresponding module is loaded.&lt;br /&gt;
&lt;br /&gt;
It is even possible to create your own telemetry XML definition. By the time you need that, it is highly likely you are already an advanced paparazzi user and know why you would and how you will.&lt;br /&gt;
&lt;br /&gt;
===Add Messages===&lt;br /&gt;
&lt;br /&gt;
This section provides instructions of an example case of how one would add a new message to Paparazzi and send the data to the ground station. The example is a little old and considers the addition of the AIRSPEED message, which is already present in newer versions of paparazzi. The user will have to implement her own message objects instead of the AIRSPEED message.&lt;br /&gt;
&lt;br /&gt;
==== Step 1 ====&lt;br /&gt;
&lt;br /&gt;
In sw/ext/pprzlink/message_definitions/v1.0/messages.xml add an airspeed message:&lt;br /&gt;
{{Box Code|sw/ext/pprzlink/message_definitions/v1.0/messages.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
   &amp;lt;message name=&amp;quot;AIRSPEED&amp;quot; id=&amp;quot;54&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;adc_airspeed&amp;quot; type=&amp;quot;uint16&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;estimator_airspeed&amp;quot;   type=&amp;quot;float&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;airspeed_setpoint&amp;quot;    type=&amp;quot;float&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;airspeed_controlled&amp;quot;  type=&amp;quot;float&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;groundspeed_setpoint&amp;quot; type=&amp;quot;float&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/message&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;}}&lt;br /&gt;
Where id=&amp;quot;54&amp;quot; has to be unique. To find an new ID to use there is a script file located at ${PAPARAZZI_HOME}/sw/tools/find_free_msg_id.out (yes it is really a script). &lt;br /&gt;
&lt;br /&gt;
 Type: ${PAPARAZZI_SRC}/sw/tools/find_free_msg_id.out &lt;br /&gt;
&lt;br /&gt;
NOTE: Be sure your Paparazzi source and home environment variables are set correctly in your shell [[Installation#Launching_the_Software]])&lt;br /&gt;
&lt;br /&gt;
Every field in the output is a variable from Paparazzi. The type must be the type of a variable in your code (ie. look in your code). Add your message along with the frequency to be sent over the messaging bus (AKA telemetry messages).&lt;br /&gt;
&lt;br /&gt;
After making the modifications to the messages.xml file, make your paparazzi again (i.e. cd ${PAPARAZZI_HOME} &amp;amp;&amp;amp; make) so that your changes to the messages.xml file are reflected in the paparazzi/var/include/messages.h file. This will create a DOWNLINK_SEND_AIRSPEED macro (in ${PAPARAZZI_HOME}/var/include/messages.h). If you do not make paparazzi, this macro will not be created.&lt;br /&gt;
&lt;br /&gt;
==== Step 2 ====&lt;br /&gt;
&lt;br /&gt;
Add a message to your telemetry file (for example conf/telemetry/default_fixedwing.xml). The message name in telemetry file usually match the message name in messages.xml file, but can be different or even group several messages.&lt;br /&gt;
{{Box Code|conf/telemetry/default.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;telemetry&amp;gt;&lt;br /&gt;
   &amp;lt;process name=&amp;quot;Ap&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;default&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;ALIVE&amp;quot;          period=&amp;quot;5&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;GPS&amp;quot;            period=&amp;quot;0.25&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;AIRSPEED&amp;quot;       period=&amp;quot;1&amp;quot;/&amp;gt;&lt;br /&gt;
      ....&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
The result is a generated file in ${PAPARAZZI_HOME}/var/aircrafts/&amp;lt;AC&amp;gt;/generated/periodic_telemetry.h which consist in a (static) scheduler to that calls specific functions.&lt;br /&gt;
&lt;br /&gt;
==== Step 3 ====&lt;br /&gt;
&lt;br /&gt;
Create a function in your C source file that will send your message(s) (using the generated DOWNLINK_SEND_* macros) and register it to the telemetry system so that it will be send automatically for you. You also need to include the header &amp;lt;tt&amp;gt;subsystems/datalink/telemetry.h&amp;lt;/tt&amp;gt;:&lt;br /&gt;
{{Box Code|firmware/fixedwing/autopilot.c|&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
 ...&lt;br /&gt;
 #include &amp;quot;subsystems/datalink/telemetry.h&amp;quot;&lt;br /&gt;
&lt;br /&gt;
 static void send_airspeed(struct transport_tx *trans, struct link_device *dev)&lt;br /&gt;
 {&lt;br /&gt;
   pprz_msg_send_AIRSPEED(trans, dev, AC_ID,&lt;br /&gt;
                         &amp;amp;airspeed, &amp;amp;v_ctl_auto_airspeed_setpoint,&lt;br /&gt;
                         &amp;amp;v_ctl_auto_airspeed_controlled, &amp;amp;v_ctl_auto_groundspeed_setpoint);&lt;br /&gt;
 }&lt;br /&gt;
&lt;br /&gt;
 ...&lt;br /&gt;
 void autopilot_init(void) {&lt;br /&gt;
 ...&lt;br /&gt;
  register_periodic_telemetry(DefaultPeriodic, PPRZ_MSG_ID_AIRSPEED, send_airspeed);&lt;br /&gt;
 ...&lt;br /&gt;
 }&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
where the second parameter in the register function is the id of the message (use the define &amp;lt;tt&amp;gt;PPRZ_MSG_ID_&amp;lt;MESSAGE_NAME&amp;gt;&amp;lt;/tt&amp;gt;).&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div class=&amp;quot;toccolours mw-collapsible mw-collapsed&amp;quot; style=&amp;quot;width:800px&amp;quot;&amp;gt;&lt;br /&gt;
Prior to '''v5.0''':&lt;br /&gt;
&amp;lt;div class=&amp;quot;mw-collapsible-content&amp;quot;&amp;gt;Past Reference for Paparazzi v5.0 or older:&lt;br /&gt;
Create a PERIODIC_SEND_AIRSPEED with the following code in the firmware specific telemetry header file (In ap_downlink.h/fbw_downlink.h for fixedwing or telemetry.h for rotorcraft) :&lt;br /&gt;
{{Box Code|conf/telemetry/default.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
 #ifdef USE_AIRSPEED&lt;br /&gt;
 #define PERIODIC_SEND_AIRSPEED(_chan) DOWNLINK_SEND_AIRSPEED (_chan, _dev   &amp;amp;adc_airspeed_val,&amp;amp;estimator_airspeed,&amp;amp;v_ctl_auto_airspeed_setpoint,&amp;amp;v_ctl_auto_airspeed_controlled,&amp;amp;v_ctl_auto_groundspeed_setpoint)&lt;br /&gt;
 #else&lt;br /&gt;
 #define PERIODIC_SEND_AIRSPEED(_chan) {}&lt;br /&gt;
 #endif&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&amp;lt;/div&amp;gt;&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Configuring the Downlink Data Rate===&lt;br /&gt;
&lt;br /&gt;
The limited throughput of our RF modems results in a need to carefully choose which data to send, as well as the frequency at which to send it.  A sophisticated set of files and parameters have been developed in order to tailor the data downlink behavior automatically, manually, temporarily, or permanently according to any desired parameter.  This allows the user to create an almost unlimited possibility of downlink configurations.  For example:&lt;br /&gt;
* Tailor the data rate to work with very slow modems (9600 baud or slower)&lt;br /&gt;
* Reduce the data rate of some messages so that others can be increased:&lt;br /&gt;
*: Automatically send GPS data at a very high rate by sacrificing navigation data when not flying (to help GPS/RFI troubleshooting) then automatically reduce the GPS data rate and send normal navigation data when the launch is initiated.&lt;br /&gt;
*: Automatically switch to sending only position data upon landing to conserve power and increase the chance of the operator receiving a position packet when recovering a distant aircraft.&lt;br /&gt;
*: Manually send selected sensor data at very high speeds (60Hz) for real time tuning.&lt;br /&gt;
* Maintain independent telemetry configurations for aircraft with different modems, sensors, or mission profiles.&lt;br /&gt;
&lt;br /&gt;
Any number of configuration files can be created in the &amp;lt;tt&amp;gt;conf/telemetry&amp;lt;/tt&amp;gt; directory and selected from the &amp;lt;tt&amp;gt;conf/conf.xml&amp;lt;/tt&amp;gt; file.  The telemetry downlink is divided into two processes, '''Ap''' and '''Fbw''' each with a possible &amp;lt;tt&amp;gt;mode&amp;lt;/tt&amp;gt; option.  Any number of modes could be created, the default is the first in the sequence. A mode contains the list of messages to be sent as well as the period of each message in seconds. In this example, the '''ATTITUDE''' message will be sent by the '''Ap''' process at 2Hz in the default mode and at 10Hz in the '''fast attitude''' mode. The maximum allowed frequency is 60Hz (0.017s) and the maximum period is 1092s.&lt;br /&gt;
&lt;br /&gt;
The mode can be chosen in the airframe file by setting the '''TELEMETRY_MODE_FBW''' constant:&lt;br /&gt;
 &amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;define name=&amp;quot;TELEMETRY_MODE_FBW&amp;quot; value=&amp;quot;1&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
where the (default) first mode is numbered '''0'''.&lt;br /&gt;
&lt;br /&gt;
This mode can also be changed dynamically with a datalink [[#Settings|setting]] or with a [[Flight_Plans#set|set]] stage in the flight plan.&lt;br /&gt;
&lt;br /&gt;
Note that an (undocumented!) subset of the messages is required to be able to use ground station properly. So it is not advisable to completely remove messages for the '''Ap''' process listed in the default mode.&lt;br /&gt;
&lt;br /&gt;
==Specific Messages==&lt;br /&gt;
&lt;br /&gt;
===GPS_SOL===&lt;br /&gt;
Specification in telemetry file&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;message name=&amp;quot;GPS_SOL&amp;quot;        period=&amp;quot;2.0&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
Example from logfile(.data):&lt;br /&gt;
 6.742 1 GPS_SOL 232 43 198 8&lt;br /&gt;
&lt;br /&gt;
Meaning of tokens:&lt;br /&gt;
 Timestamp, Aircraft-Number, GPS_SOL, Pacc, Sacc, PDOP, numSV&lt;br /&gt;
&lt;br /&gt;
*Pacc = Position accuracy (units: CM)&lt;br /&gt;
*Sacc = Speed accuracy (units: CM/sec ?)&lt;br /&gt;
*PDOP = Position [http://en.wikipedia.org/wiki/Dilution_of_precision_%28GPS%29 Dilution_of_precision_(GPS)] , if this value is high the value of position will be less accurate&lt;br /&gt;
*numSV = number of Space Vehicles (Satellites) used in Nav Solution&lt;br /&gt;
&lt;br /&gt;
===PPRZ_MODE===&lt;br /&gt;
Specification in telemetry file&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;message name=&amp;quot;PPRZ_MODE&amp;quot;      period=&amp;quot;5.&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
Example from logfile(.data):&lt;br /&gt;
 20.433 2 PPRZ_MODE 0 1 2 0 0 1&lt;br /&gt;
&lt;br /&gt;
Meaning of tokens:&lt;br /&gt;
 Timestamp, Aircraft-Number, PPRZ_MODE, ap_mode, ap_gaz, ap_horizontal, if_calib_mode, mcul_status&lt;br /&gt;
*ap_mode = (0 = MANUAL, 1 = AUTO1, 2 = AUTO2, 3 = HOME mode (Circle Home waypoint), 4 = NO_GPS (GPS not working), 5 = NB (?)&lt;br /&gt;
*ap_gaz = ?&lt;br /&gt;
*ap_horizontal = ?&lt;br /&gt;
*if_calib_mode = ?&lt;br /&gt;
*mcul_status = ?&lt;br /&gt;
&lt;br /&gt;
== Audio-based downlink ==&lt;br /&gt;
&lt;br /&gt;
The audio-based downlink has been removed from current hardware designs however using the old designs it is possible to implement. With the current low prices of a simple video transmitter, data over audio may come in as a welcomed addition. Feel free to experiment and revive this classical feature.&lt;br /&gt;
&lt;br /&gt;
[[Category:Software]] [[Category:User_Documentation]] [[Category:Telemetry]]&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Telemetry&amp;diff=23846</id>
		<title>Telemetry</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Telemetry&amp;diff=23846"/>
		<updated>2017-09-15T08:55:57Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: /* Step 1 */ changed &amp;quot;find_msg_id.out&amp;quot; to &amp;quot;find_free_msg_id.out&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Messages ==&lt;br /&gt;
&lt;br /&gt;
Telemetry messages (sent from the aircraft to the ground) are defined in the telemetry class of [https://github.com/paparazzi/paparazzi/blob/master/conf/messages.xml conf/messages.xml].&lt;br /&gt;
See also the generated documentation: http://docs.paparazziuav.org/latest/paparazzi_messages.html&lt;br /&gt;
&lt;br /&gt;
== Sending periodic messages ==&lt;br /&gt;
The set of periodic messages sent over the downlink channel by an aircraft to the ground station is configurable&lt;br /&gt;
with the help of one XML file, located in the &amp;lt;tt&amp;gt;conf/telemetry&amp;lt;/tt&amp;gt; directory. This file is referenced by &amp;lt;tt&amp;gt;conf/conf.xml&amp;lt;/tt&amp;gt; and must follow the&lt;br /&gt;
&amp;lt;tt&amp;gt;telemetry.dtd&amp;lt;/tt&amp;gt; syntax. The &amp;lt;tt&amp;gt;fixedwing_default.xml&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;rotorcraft_default.xml&amp;lt;/tt&amp;gt; are provided as an example and should be suitable for most users.&lt;br /&gt;
{{Box Code|default.xml|&lt;br /&gt;
 &amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;!DOCTYPE telemetry SYSTEM &amp;quot;telemetry.dtd&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;telemetry&amp;gt;&lt;br /&gt;
  &amp;lt;process name=&amp;quot;Ap&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;default&amp;quot;&amp;gt;&lt;br /&gt;
     &amp;lt;message name=&amp;quot;ATTITUDE&amp;quot; period=&amp;quot;0.5&amp;quot;/&amp;gt;&lt;br /&gt;
     &amp;lt;message name=&amp;quot;PPRZ_MODE&amp;quot; period=&amp;quot;5&amp;quot;/&amp;gt;&lt;br /&gt;
     &amp;lt;message name=&amp;quot;SOME_MODULE_MSG&amp;quot; period=&amp;quot;2&amp;quot; module=&amp;quot;module_name&amp;quot;/&amp;gt;&lt;br /&gt;
     ...&lt;br /&gt;
    &amp;lt;/mode&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;fast attitude&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;ATTITUDE&amp;quot; period=&amp;quot;0.1&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/mode&amp;gt;&lt;br /&gt;
 &amp;lt;/process&amp;gt;&lt;br /&gt;
  &amp;lt;process name=&amp;quot;Fbw&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;default&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;COMMANDS&amp;quot; period=&amp;quot;1&amp;quot;/&amp;gt;&lt;br /&gt;
      ...&lt;br /&gt;
    &amp;lt;/mode&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;debug&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;PPM&amp;quot; period=&amp;quot;0.5&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/mode&amp;gt;&lt;br /&gt;
  &amp;lt;/process&amp;gt;&lt;br /&gt;
 &amp;lt;/telemetry&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
If a [[Modules|module]] attribute is specified for a message, it will be included in the telemetry only if the corresponding module is loaded.&lt;br /&gt;
&lt;br /&gt;
It is even possible to create your own telemetry XML definition. By the time you need that, it is highly likely you are already an advanced paparazzi user and know why you would and how you will.&lt;br /&gt;
&lt;br /&gt;
===Add Messages===&lt;br /&gt;
&lt;br /&gt;
This section provides instructions of an example case of how one would add a new message to Paparazzi and send the data to the ground station. The example is a little old and considers the addition of the AIRSPEED message, which is already present in newer versions of paparazzi. The user will have to implement her own message objects instead of the AIRSPEED message.&lt;br /&gt;
&lt;br /&gt;
==== Step 1 ====&lt;br /&gt;
&lt;br /&gt;
In conf/messages.xml add an airspeed message:&lt;br /&gt;
{{Box Code|conf/messages.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
   &amp;lt;message name=&amp;quot;AIRSPEED&amp;quot; id=&amp;quot;54&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;adc_airspeed&amp;quot; type=&amp;quot;uint16&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;estimator_airspeed&amp;quot;   type=&amp;quot;float&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;airspeed_setpoint&amp;quot;    type=&amp;quot;float&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;airspeed_controlled&amp;quot;  type=&amp;quot;float&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;groundspeed_setpoint&amp;quot; type=&amp;quot;float&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/message&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;}}&lt;br /&gt;
Where id=&amp;quot;54&amp;quot; has to be unique. To find an new ID to use there is a script file located at ${PAPARAZZI_HOME}/sw/tools/find_free_msg_id.out (yes it is really a script). &lt;br /&gt;
&lt;br /&gt;
 Type: ${PAPARAZZI_SRC}/sw/tools/find_free_msg_id.out &lt;br /&gt;
&lt;br /&gt;
NOTE: Be sure your Paparazzi source and home environment variables are set correctly in your shell [[Installation#Launching_the_Software]])&lt;br /&gt;
&lt;br /&gt;
Every field in the output is a variable from Paparazzi. The type must be the type of a variable in your code (ie. look in your code). Add your message along with the frequency to be sent over the messaging bus (AKA telemetry messages).&lt;br /&gt;
&lt;br /&gt;
After making the modifications to the messages.xml file, make your paparazzi again (i.e. cd ${PAPARAZZI_HOME} &amp;amp;&amp;amp; make) so that your changes to the messages.xml file are reflected in the paparazzi/var/include/messages.h file. This will create a DOWNLINK_SEND_AIRSPEED macro (in ${PAPARAZZI_HOME}/var/include/messages.h). If you do not make paparazzi, this macro will not be created.&lt;br /&gt;
&lt;br /&gt;
==== Step 2 ====&lt;br /&gt;
&lt;br /&gt;
Add a message to your telemetry file (for example conf/telemetry/default_fixedwing.xml). The message name in telemetry file usually match the message name in messages.xml file, but can be different or even group several messages.&lt;br /&gt;
{{Box Code|conf/telemetry/default.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;telemetry&amp;gt;&lt;br /&gt;
   &amp;lt;process name=&amp;quot;Ap&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;default&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;ALIVE&amp;quot;          period=&amp;quot;5&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;GPS&amp;quot;            period=&amp;quot;0.25&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;AIRSPEED&amp;quot;       period=&amp;quot;1&amp;quot;/&amp;gt;&lt;br /&gt;
      ....&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
The result is a generated file in ${PAPARAZZI_HOME}/var/aircrafts/&amp;lt;AC&amp;gt;/generated/periodic_telemetry.h which consist in a (static) scheduler to that calls specific functions.&lt;br /&gt;
&lt;br /&gt;
==== Step 3 ====&lt;br /&gt;
&lt;br /&gt;
Create a function in your C source file that will send your message(s) (using the generated DOWNLINK_SEND_* macros) and register it to the telemetry system so that it will be send automatically for you. You also need to include the header &amp;lt;tt&amp;gt;subsystems/datalink/telemetry.h&amp;lt;/tt&amp;gt;:&lt;br /&gt;
{{Box Code|firmware/fixedwing/autopilot.c|&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
 ...&lt;br /&gt;
 #include &amp;quot;subsystems/datalink/telemetry.h&amp;quot;&lt;br /&gt;
&lt;br /&gt;
 static void send_airspeed(struct transport_tx *trans, struct link_device *dev)&lt;br /&gt;
 {&lt;br /&gt;
   pprz_msg_send_AIRSPEED(trans, dev, AC_ID,&lt;br /&gt;
                         &amp;amp;airspeed, &amp;amp;v_ctl_auto_airspeed_setpoint,&lt;br /&gt;
                         &amp;amp;v_ctl_auto_airspeed_controlled, &amp;amp;v_ctl_auto_groundspeed_setpoint);&lt;br /&gt;
 }&lt;br /&gt;
&lt;br /&gt;
 ...&lt;br /&gt;
 void autopilot_init(void) {&lt;br /&gt;
 ...&lt;br /&gt;
  register_periodic_telemetry(DefaultPeriodic, PPRZ_MSG_ID_AIRSPEED, send_airspeed);&lt;br /&gt;
 ...&lt;br /&gt;
 }&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
where the second parameter in the register function is the id of the message (use the define &amp;lt;tt&amp;gt;PPRZ_MSG_ID_&amp;lt;MESSAGE_NAME&amp;gt;&amp;lt;/tt&amp;gt;).&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div class=&amp;quot;toccolours mw-collapsible mw-collapsed&amp;quot; style=&amp;quot;width:800px&amp;quot;&amp;gt;&lt;br /&gt;
Prior to '''v5.0''':&lt;br /&gt;
&amp;lt;div class=&amp;quot;mw-collapsible-content&amp;quot;&amp;gt;Past Reference for Paparazzi v5.0 or older:&lt;br /&gt;
Create a PERIODIC_SEND_AIRSPEED with the following code in the firmware specific telemetry header file (In ap_downlink.h/fbw_downlink.h for fixedwing or telemetry.h for rotorcraft) :&lt;br /&gt;
{{Box Code|conf/telemetry/default.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
 #ifdef USE_AIRSPEED&lt;br /&gt;
 #define PERIODIC_SEND_AIRSPEED(_chan) DOWNLINK_SEND_AIRSPEED (_chan, _dev   &amp;amp;adc_airspeed_val,&amp;amp;estimator_airspeed,&amp;amp;v_ctl_auto_airspeed_setpoint,&amp;amp;v_ctl_auto_airspeed_controlled,&amp;amp;v_ctl_auto_groundspeed_setpoint)&lt;br /&gt;
 #else&lt;br /&gt;
 #define PERIODIC_SEND_AIRSPEED(_chan) {}&lt;br /&gt;
 #endif&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&amp;lt;/div&amp;gt;&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Configuring the Downlink Data Rate===&lt;br /&gt;
&lt;br /&gt;
The limited throughput of our RF modems results in a need to carefully choose which data to send, as well as the frequency at which to send it.  A sophisticated set of files and parameters have been developed in order to tailor the data downlink behavior automatically, manually, temporarily, or permanently according to any desired parameter.  This allows the user to create an almost unlimited possibility of downlink configurations.  For example:&lt;br /&gt;
* Tailor the data rate to work with very slow modems (9600 baud or slower)&lt;br /&gt;
* Reduce the data rate of some messages so that others can be increased:&lt;br /&gt;
*: Automatically send GPS data at a very high rate by sacrificing navigation data when not flying (to help GPS/RFI troubleshooting) then automatically reduce the GPS data rate and send normal navigation data when the launch is initiated.&lt;br /&gt;
*: Automatically switch to sending only position data upon landing to conserve power and increase the chance of the operator receiving a position packet when recovering a distant aircraft.&lt;br /&gt;
*: Manually send selected sensor data at very high speeds (60Hz) for real time tuning.&lt;br /&gt;
* Maintain independent telemetry configurations for aircraft with different modems, sensors, or mission profiles.&lt;br /&gt;
&lt;br /&gt;
Any number of configuration files can be created in the &amp;lt;tt&amp;gt;conf/telemetry&amp;lt;/tt&amp;gt; directory and selected from the &amp;lt;tt&amp;gt;conf/conf.xml&amp;lt;/tt&amp;gt; file.  The telemetry downlink is divided into two processes, '''Ap''' and '''Fbw''' each with a possible &amp;lt;tt&amp;gt;mode&amp;lt;/tt&amp;gt; option.  Any number of modes could be created, the default is the first in the sequence. A mode contains the list of messages to be sent as well as the period of each message in seconds. In this example, the '''ATTITUDE''' message will be sent by the '''Ap''' process at 2Hz in the default mode and at 10Hz in the '''fast attitude''' mode. The maximum allowed frequency is 60Hz (0.017s) and the maximum period is 1092s.&lt;br /&gt;
&lt;br /&gt;
The mode can be chosen in the airframe file by setting the '''TELEMETRY_MODE_FBW''' constant:&lt;br /&gt;
 &amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;define name=&amp;quot;TELEMETRY_MODE_FBW&amp;quot; value=&amp;quot;1&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
where the (default) first mode is numbered '''0'''.&lt;br /&gt;
&lt;br /&gt;
This mode can also be changed dynamically with a datalink [[#Settings|setting]] or with a [[Flight_Plans#set|set]] stage in the flight plan.&lt;br /&gt;
&lt;br /&gt;
Note that an (undocumented!) subset of the messages is required to be able to use ground station properly. So it is not advisable to completely remove messages for the '''Ap''' process listed in the default mode.&lt;br /&gt;
&lt;br /&gt;
==Specific Messages==&lt;br /&gt;
&lt;br /&gt;
===GPS_SOL===&lt;br /&gt;
Specification in telemetry file&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;message name=&amp;quot;GPS_SOL&amp;quot;        period=&amp;quot;2.0&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
Example from logfile(.data):&lt;br /&gt;
 6.742 1 GPS_SOL 232 43 198 8&lt;br /&gt;
&lt;br /&gt;
Meaning of tokens:&lt;br /&gt;
 Timestamp, Aircraft-Number, GPS_SOL, Pacc, Sacc, PDOP, numSV&lt;br /&gt;
&lt;br /&gt;
*Pacc = Position accuracy (units: CM)&lt;br /&gt;
*Sacc = Speed accuracy (units: CM/sec ?)&lt;br /&gt;
*PDOP = Position [http://en.wikipedia.org/wiki/Dilution_of_precision_%28GPS%29 Dilution_of_precision_(GPS)] , if this value is high the value of position will be less accurate&lt;br /&gt;
*numSV = number of Space Vehicles (Satellites) used in Nav Solution&lt;br /&gt;
&lt;br /&gt;
===PPRZ_MODE===&lt;br /&gt;
Specification in telemetry file&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;message name=&amp;quot;PPRZ_MODE&amp;quot;      period=&amp;quot;5.&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
Example from logfile(.data):&lt;br /&gt;
 20.433 2 PPRZ_MODE 0 1 2 0 0 1&lt;br /&gt;
&lt;br /&gt;
Meaning of tokens:&lt;br /&gt;
 Timestamp, Aircraft-Number, PPRZ_MODE, ap_mode, ap_gaz, ap_horizontal, if_calib_mode, mcul_status&lt;br /&gt;
*ap_mode = (0 = MANUAL, 1 = AUTO1, 2 = AUTO2, 3 = HOME mode (Circle Home waypoint), 4 = NO_GPS (GPS not working), 5 = NB (?)&lt;br /&gt;
*ap_gaz = ?&lt;br /&gt;
*ap_horizontal = ?&lt;br /&gt;
*if_calib_mode = ?&lt;br /&gt;
*mcul_status = ?&lt;br /&gt;
&lt;br /&gt;
== Audio-based downlink ==&lt;br /&gt;
&lt;br /&gt;
The audio-based downlink has been removed from current hardware designs however using the old designs it is possible to implement. With the current low prices of a simple video transmitter, data over audio may come in as a welcomed addition. Feel free to experiment and revive this classical feature.&lt;br /&gt;
&lt;br /&gt;
[[Category:Software]] [[Category:User_Documentation]] [[Category:Telemetry]]&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Load_Screenshots_from_FlightGear&amp;diff=23749</id>
		<title>Load Screenshots from FlightGear</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Load_Screenshots_from_FlightGear&amp;diff=23749"/>
		<updated>2017-07-24T15:08:59Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: included more of the stuff that it needs; more is on the way&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;'''WORK IN PROGRESS'''&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This page describes the steps required to obtain screenshots from FlightGear into the memory of PaparazziUAV. First the required functions are presented and described. Than the exact details about running the applications are mentioned. This has been tested with PaparazziUAV v5.10 and FlightGear 2017.1.2.&lt;br /&gt;
&lt;br /&gt;
== Required functions and libraries ==&lt;br /&gt;
&lt;br /&gt;
FlightGear can be run with an HTTP server which can be used to obtain screenshots of the current scenery in FlightGear. There is a limit to the rate at which these screenshots (I only tested this with approximately 1 fps) can be obtained thus it cannot be used to simulate high frame rate vision. One requires the libcurl library to download the image from the HTTP server into memory. Following this, the jpeg image data needs to be decompressed to obtain the pixel values using libjpeg. All of this code have been obtained from the reference material of the corresponding libraries and required modifications made for the specific implementation. Note that in order to indicate to the compiler that libcurl and libjpeg &lt;br /&gt;
&lt;br /&gt;
Before doing anything a module needs to be added to PaparazziUAV ([[Modules#Make_your_own|create a module]]). By using the 3 functions below (WriteMemoryCallback, curl2mem, get_bmp) one can download the screenshot from the FlightGear HTTP server and convert the jpeg image into bitmap data. The WriteMemoryCallback is a function that is used by the libcurl function ''curl_easy_setopt'' to write the downloaded data into the memory. The function curl2mem takes the pointer to a MemoryStruct structure as input. This structure contains two elements namely a pointer to memory and the size of the memory. curl2mem basically writes the information from http://localhost:1234/screenshot (this is where FlightGear will have its screenshot) to a predefined memory location.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
struct MemoryStruct&lt;br /&gt;
{&lt;br /&gt;
  char *memory;&lt;br /&gt;
  size_t size;&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
static size_t WriteMemoryCallback(void *contents, size_t size, size_t nmemb, void *userp)&lt;br /&gt;
{&lt;br /&gt;
    /* Helper function for curl2mem. Handles the writing of the data from&lt;br /&gt;
     * the source HTTP into the memory. Needs to follow format provided by&lt;br /&gt;
     * libcurl.&lt;br /&gt;
     */&lt;br /&gt;
  size_t realsize = size * nmemb;&lt;br /&gt;
  struct MemoryStruct *mem = (struct MemoryStruct *)userp;&lt;br /&gt;
&lt;br /&gt;
  mem-&amp;gt;memory = realloc(mem-&amp;gt;memory, mem-&amp;gt;size + realsize + 1);&lt;br /&gt;
  if(mem-&amp;gt;memory == NULL) {&lt;br /&gt;
    /* out of memory! */&lt;br /&gt;
    printf(&amp;quot;not enough memory (realloc returned NULL)\n&amp;quot;);&lt;br /&gt;
    return 0;&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  memcpy(&amp;amp;(mem-&amp;gt;memory[mem-&amp;gt;size]), contents, realsize);&lt;br /&gt;
  mem-&amp;gt;size += realsize;&lt;br /&gt;
  mem-&amp;gt;memory[mem-&amp;gt;size] = 0;&lt;br /&gt;
&lt;br /&gt;
  return realsize;&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
void curl2mem(struct MemoryStruct *chunk)&lt;br /&gt;
{&lt;br /&gt;
    /* Uses libcurl functions to load the screenshot from the FlightGear HTTP&lt;br /&gt;
     * server into the programs memory&lt;br /&gt;
     */&lt;br /&gt;
  CURL *curl_handle;&lt;br /&gt;
  CURLcode res;&lt;br /&gt;
&lt;br /&gt;
  curl_global_init(CURL_GLOBAL_ALL);&lt;br /&gt;
&lt;br /&gt;
  /* init the curl session */&lt;br /&gt;
  curl_handle = curl_easy_init();&lt;br /&gt;
&lt;br /&gt;
  /* specify URL to get */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_URL, &amp;quot;http://localhost:1234/screenshot&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
  /* send all data to this function  */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_WRITEFUNCTION, WriteMemoryCallback);&lt;br /&gt;
&lt;br /&gt;
  /* we pass our 'chunk' struct to the callback function */&lt;br /&gt;
  // curl_easy_setopt(curl_handle, CURLOPT_WRITEDATA, (void *)&amp;amp;chunk);&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_WRITEDATA, (void *)chunk);&lt;br /&gt;
&lt;br /&gt;
  /* some servers don't like requests that are made without a user-agent&lt;br /&gt;
     field, so we provide one */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_USERAGENT, &amp;quot;libcurl-agent/1.0&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
  /* get it! */&lt;br /&gt;
  res = curl_easy_perform(curl_handle);&lt;br /&gt;
&lt;br /&gt;
  /* check for errors */&lt;br /&gt;
  if(res != CURLE_OK) {&lt;br /&gt;
    fprintf(stderr, &amp;quot;curl_easy_perform() failed: %s\n&amp;quot;,&lt;br /&gt;
            curl_easy_strerror(res));&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  /* cleanup curl stuff */&lt;br /&gt;
  curl_easy_cleanup(curl_handle);&lt;br /&gt;
&lt;br /&gt;
  /* we're done with libcurl, so clean it up */&lt;br /&gt;
  curl_global_cleanup();&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
After obtaining the jpeg screenshot, it is decompressed to obtain the pixel data. This is done by the get_bmp function which takes 3 input parameters. The first input is a pointer to the chunk of memory containing the jpeg data. The second one is the total length of the memory chunk (i.e. the jpeg data) in bytes. The last input is a pointer to a structure which contains the decompressed pixel data from the jpeg file.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
struct BmpStruct&lt;br /&gt;
{&lt;br /&gt;
    unsigned char *buffer;&lt;br /&gt;
    unsigned long size;&lt;br /&gt;
    uint16_t width;&lt;br /&gt;
    uint16_t height;&lt;br /&gt;
    uint8_t pixel_size;&lt;br /&gt;
    uint16_t row_stride;&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
uint8_t get_bmp(unsigned char *jpg_buffer, unsigned long jpg_size, struct BmpStruct *bmp)&lt;br /&gt;
{&lt;br /&gt;
    // // INTIALIZE&lt;br /&gt;
    uint8_t rc;&lt;br /&gt;
	// Variables for the decompressor itself&lt;br /&gt;
	struct jpeg_decompress_struct cinfo;&lt;br /&gt;
	struct jpeg_error_mgr jerr;&lt;br /&gt;
&lt;br /&gt;
	// Variables for the output buffer, and how long each row is&lt;br /&gt;
	unsigned long bmp_size;&lt;br /&gt;
	unsigned char *bmp_buffer;&lt;br /&gt;
	uint16_t row_stride, width, height, pixel_size;&lt;br /&gt;
&lt;br /&gt;
    // holds the output bmp and its metadata&lt;br /&gt;
&lt;br /&gt;
    // // SETUP AND CHECK&lt;br /&gt;
	cinfo.err = jpeg_std_error(&amp;amp;jerr);&lt;br /&gt;
	jpeg_create_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
	jpeg_mem_src(&amp;amp;cinfo, jpg_buffer, jpg_size);&lt;br /&gt;
&lt;br /&gt;
    // 	skipping error check for now. file should be JPEG&lt;br /&gt;
	rc = jpeg_read_header(&amp;amp;cinfo, TRUE);&lt;br /&gt;
	if (rc != 1) {&lt;br /&gt;
        printf(&amp;quot;File to get_bmp() not JPEG&amp;quot;);&lt;br /&gt;
        return 1;&lt;br /&gt;
	}&lt;br /&gt;
&lt;br /&gt;
	jpeg_start_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
	width = cinfo.output_width;&lt;br /&gt;
	height = cinfo.output_height;&lt;br /&gt;
	pixel_size = cinfo.output_components;&lt;br /&gt;
&lt;br /&gt;
	bmp_size = width * height * pixel_size;&lt;br /&gt;
	bmp_buffer = (unsigned char*) malloc(bmp_size);&lt;br /&gt;
&lt;br /&gt;
	// The row_stride is the total number of bytes it takes to store an&lt;br /&gt;
	// entire scanline (row).&lt;br /&gt;
	row_stride = width * pixel_size;&lt;br /&gt;
&lt;br /&gt;
    // // READ THE LINES&lt;br /&gt;
	while (cinfo.output_scanline &amp;lt; cinfo.output_height) {&lt;br /&gt;
		unsigned char *buffer_array[1];&lt;br /&gt;
		buffer_array[0] = bmp_buffer + (cinfo.output_scanline) * row_stride;&lt;br /&gt;
&lt;br /&gt;
		jpeg_read_scanlines(&amp;amp;cinfo, buffer_array, 1);&lt;br /&gt;
&lt;br /&gt;
	}&lt;br /&gt;
&lt;br /&gt;
    bmp-&amp;gt;buffer = bmp_buffer;&lt;br /&gt;
    bmp-&amp;gt;size = bmp_size;&lt;br /&gt;
    bmp-&amp;gt;width = width;&lt;br /&gt;
    bmp-&amp;gt;height = height;&lt;br /&gt;
    bmp-&amp;gt;pixel_size = pixel_size;&lt;br /&gt;
&lt;br /&gt;
	jpeg_finish_decompress(&amp;amp;cinfo);&lt;br /&gt;
	jpeg_destroy_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
    return 0;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The sum_blues function below is an example of a function that uses the obtained pixel data from the FlightGear screenshot to sum up all the blue pixels. It iterates over all the bytes in the decompressed image which are for the blue channel of each pixel and sums them.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
uint8_t sum_blues(void)&lt;br /&gt;
{&lt;br /&gt;
    struct MemoryStruct chunk; // structure holding download data&lt;br /&gt;
    chunk.memory = malloc(1);&lt;br /&gt;
    chunk.size = 0;&lt;br /&gt;
&lt;br /&gt;
    struct BmpStruct bmp; // structure holding decompressed image&lt;br /&gt;
&lt;br /&gt;
    // download the jpeg into internal memory&lt;br /&gt;
    curl2mem(&amp;amp;chunk);&lt;br /&gt;
&lt;br /&gt;
    // decompress the image and store it in preallocated structure&lt;br /&gt;
    get_bmp((unsigned char*)chunk.memory, chunk.size, &amp;amp;bmp);&lt;br /&gt;
&lt;br /&gt;
    // free up memory of downloaded jpeg&lt;br /&gt;
    free(chunk.memory);&lt;br /&gt;
&lt;br /&gt;
    uint32_t bluesum = 0;&lt;br /&gt;
    unsigned long curinc = 2;&lt;br /&gt;
    unsigned char *curby;&lt;br /&gt;
    while (curinc &amp;lt;= bmp.size) {&lt;br /&gt;
        curby = bmp.buffer + curinc;&lt;br /&gt;
        bluesum += *curby;&lt;br /&gt;
        curinc = curinc + 3;&lt;br /&gt;
    }&lt;br /&gt;
    printf(&amp;quot;BlueSum: %d\n&amp;quot;,bluesum);&lt;br /&gt;
&lt;br /&gt;
    // free up memory of the bmp&lt;br /&gt;
    free(bmp.buffer);&lt;br /&gt;
&lt;br /&gt;
    return 0;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Running the application ==&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Load_Screenshots_from_FlightGear&amp;diff=23748</id>
		<title>Load Screenshots from FlightGear</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Load_Screenshots_from_FlightGear&amp;diff=23748"/>
		<updated>2017-07-24T09:56:41Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: A page describing how to obtain screenshots from FlightGear into the memory of PaparazziUAV for simple computer vision tasks&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;'''WORK IN PROGRESS'''&lt;br /&gt;
&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
This page describes the steps required to obtain screenshots from FlightGear into the memory of PaparazziUAV. First the required functions are presented and described. Than the exact details about running the applications are mentioned. This has been tested with PaparazziUAV v5.10 and FlightGear 2017.1.2.&lt;br /&gt;
&lt;br /&gt;
== Required modules ==&lt;br /&gt;
&lt;br /&gt;
FlightGear can be run with an HTTP server which can be used to obtain screenshots of the current scenery in FlightGear. There is a limit to the rate at which these screenshots (I only tested this with approximately 1 fps) can be obtained thus it cannot be used to simulate high frame rate vision. One requires the libcurl library to download the image from the HTTP server into memory. Following this, the jpeg image data needs to be decompressed to obtain the pixel values using libjpeg. All of this code have been obtained from the reference material of the corresponding libraries and required modifications made for the specific implementation.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
static size_t WriteMemoryCallback(void *contents, size_t size, size_t nmemb, void *userp)&lt;br /&gt;
{&lt;br /&gt;
    /* Helper function for curl2mem. Handles the writing of the data from&lt;br /&gt;
     * the source HTTP into the memory. Needs to follow format provided by&lt;br /&gt;
     * libcurl.&lt;br /&gt;
     */&lt;br /&gt;
  size_t realsize = size * nmemb;&lt;br /&gt;
  struct MemoryStruct *mem = (struct MemoryStruct *)userp;&lt;br /&gt;
&lt;br /&gt;
  mem-&amp;gt;memory = realloc(mem-&amp;gt;memory, mem-&amp;gt;size + realsize + 1);&lt;br /&gt;
  if(mem-&amp;gt;memory == NULL) {&lt;br /&gt;
    /* out of memory! */&lt;br /&gt;
    printf(&amp;quot;not enough memory (realloc returned NULL)\n&amp;quot;);&lt;br /&gt;
    return 0;&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  memcpy(&amp;amp;(mem-&amp;gt;memory[mem-&amp;gt;size]), contents, realsize);&lt;br /&gt;
  mem-&amp;gt;size += realsize;&lt;br /&gt;
  mem-&amp;gt;memory[mem-&amp;gt;size] = 0;&lt;br /&gt;
&lt;br /&gt;
  return realsize;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
void curl2mem(struct MemoryStruct *chunk)&lt;br /&gt;
{&lt;br /&gt;
    /* Uses libcurl functions to load the screenshot from the FlightGear HTTP&lt;br /&gt;
     * server into the programs memory&lt;br /&gt;
     */&lt;br /&gt;
  CURL *curl_handle;&lt;br /&gt;
  CURLcode res;&lt;br /&gt;
&lt;br /&gt;
  curl_global_init(CURL_GLOBAL_ALL);&lt;br /&gt;
&lt;br /&gt;
  /* init the curl session */&lt;br /&gt;
  curl_handle = curl_easy_init();&lt;br /&gt;
&lt;br /&gt;
  /* specify URL to get */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_URL, &amp;quot;http://localhost:1234/screenshot&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
  /* send all data to this function  */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_WRITEFUNCTION, WriteMemoryCallback);&lt;br /&gt;
&lt;br /&gt;
  /* we pass our 'chunk' struct to the callback function */&lt;br /&gt;
  // curl_easy_setopt(curl_handle, CURLOPT_WRITEDATA, (void *)&amp;amp;chunk);&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_WRITEDATA, (void *)chunk);&lt;br /&gt;
&lt;br /&gt;
  /* some servers don't like requests that are made without a user-agent&lt;br /&gt;
     field, so we provide one */&lt;br /&gt;
  curl_easy_setopt(curl_handle, CURLOPT_USERAGENT, &amp;quot;libcurl-agent/1.0&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
  /* get it! */&lt;br /&gt;
  res = curl_easy_perform(curl_handle);&lt;br /&gt;
&lt;br /&gt;
  /* check for errors */&lt;br /&gt;
  if(res != CURLE_OK) {&lt;br /&gt;
    fprintf(stderr, &amp;quot;curl_easy_perform() failed: %s\n&amp;quot;,&lt;br /&gt;
            curl_easy_strerror(res));&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  /* cleanup curl stuff */&lt;br /&gt;
  curl_easy_cleanup(curl_handle);&lt;br /&gt;
&lt;br /&gt;
  /* we're done with libcurl, so clean it up */&lt;br /&gt;
  curl_global_cleanup();&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
uint8_t get_bmp(unsigned char *jpg_buffer, unsigned long jpg_size, struct BmpStruct *bmp)&lt;br /&gt;
{&lt;br /&gt;
    // // INTIALIZE&lt;br /&gt;
    uint8_t rc;&lt;br /&gt;
	// Variables for the decompressor itself&lt;br /&gt;
	struct jpeg_decompress_struct cinfo;&lt;br /&gt;
	struct jpeg_error_mgr jerr;&lt;br /&gt;
&lt;br /&gt;
	// Variables for the output buffer, and how long each row is&lt;br /&gt;
	unsigned long bmp_size;&lt;br /&gt;
	unsigned char *bmp_buffer;&lt;br /&gt;
	uint16_t row_stride, width, height, pixel_size;&lt;br /&gt;
&lt;br /&gt;
    // holds the output bmp and its metadata&lt;br /&gt;
&lt;br /&gt;
    // // SETUP AND CHECK&lt;br /&gt;
	cinfo.err = jpeg_std_error(&amp;amp;jerr);&lt;br /&gt;
	jpeg_create_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
	jpeg_mem_src(&amp;amp;cinfo, jpg_buffer, jpg_size);&lt;br /&gt;
&lt;br /&gt;
    // 	skipping error check for now. file should be JPEG&lt;br /&gt;
	rc = jpeg_read_header(&amp;amp;cinfo, TRUE);&lt;br /&gt;
	if (rc != 1) {&lt;br /&gt;
        printf(&amp;quot;File to get_bmp() not JPEG&amp;quot;);&lt;br /&gt;
        return 1;&lt;br /&gt;
	}&lt;br /&gt;
&lt;br /&gt;
	jpeg_start_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
	width = cinfo.output_width;&lt;br /&gt;
	height = cinfo.output_height;&lt;br /&gt;
	pixel_size = cinfo.output_components;&lt;br /&gt;
&lt;br /&gt;
	bmp_size = width * height * pixel_size;&lt;br /&gt;
	bmp_buffer = (unsigned char*) malloc(bmp_size);&lt;br /&gt;
&lt;br /&gt;
	// The row_stride is the total number of bytes it takes to store an&lt;br /&gt;
	// entire scanline (row).&lt;br /&gt;
	row_stride = width * pixel_size;&lt;br /&gt;
&lt;br /&gt;
    // // READ THE LINES&lt;br /&gt;
	while (cinfo.output_scanline &amp;lt; cinfo.output_height) {&lt;br /&gt;
		unsigned char *buffer_array[1];&lt;br /&gt;
		buffer_array[0] = bmp_buffer + (cinfo.output_scanline) * row_stride;&lt;br /&gt;
&lt;br /&gt;
		jpeg_read_scanlines(&amp;amp;cinfo, buffer_array, 1);&lt;br /&gt;
&lt;br /&gt;
	}&lt;br /&gt;
&lt;br /&gt;
    bmp-&amp;gt;buffer = bmp_buffer;&lt;br /&gt;
    bmp-&amp;gt;size = bmp_size;&lt;br /&gt;
    bmp-&amp;gt;width = width;&lt;br /&gt;
    bmp-&amp;gt;height = height;&lt;br /&gt;
    bmp-&amp;gt;pixel_size = pixel_size;&lt;br /&gt;
&lt;br /&gt;
	jpeg_finish_decompress(&amp;amp;cinfo);&lt;br /&gt;
	jpeg_destroy_decompress(&amp;amp;cinfo);&lt;br /&gt;
&lt;br /&gt;
    return 0;&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Running the application ==&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Simulation&amp;diff=23747</id>
		<title>Simulation</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Simulation&amp;diff=23747"/>
		<updated>2017-07-24T09:21:36Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: /* View the simulation in Flight Gear */ added a subsection to link to a page which has instructions on how to obtain screenshots from FlightGear&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;categorytree style=&amp;quot;float:right; clear:right; margin-left:1ex; border: 1px solid gray; padding: 0.7ex;&amp;quot; mode=pages&amp;gt;Simulation&amp;lt;/categorytree&amp;gt;&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
This page describes the steps needed to run a simulated flight with an UAS.&lt;br /&gt;
&lt;br /&gt;
== Available Simulators ==&lt;br /&gt;
&lt;br /&gt;
Paparazzi currently has two different simulator targets with different degrees of realism and intended purpose:&lt;br /&gt;
&lt;br /&gt;
# '''sim''': The basic fixedwing simulator written in OCaml without IMU simulation or any sensor models (noise, bias, etc) and mainly intended to test [[Flight_Plans|flight plan]] logic.&lt;br /&gt;
# '''nps''': [[NPS]] is a more advanced rotorcraft and fixedwing simulator with sensor models and commonly uses [[JSBSim]] as FDM ('''F'''light '''D'''ynamic '''M'''odel). Other FDM's can be integrated easily. At the moment CRRCSIM, YASIM and JSBSIM are tried as FDM backend.&lt;br /&gt;
&lt;br /&gt;
A FDM is a set of mathematical equations used to calculate the physical forces acting on a simulated aircraft, such as thrust, lift, and drag.&lt;br /&gt;
&lt;br /&gt;
== Compiling and starting ==&lt;br /&gt;
&lt;br /&gt;
'''This describes the basic fixedwing sim, for rotorcraft or advanced fixedwing simulation, see [[NPS]].'''&lt;br /&gt;
&lt;br /&gt;
From the [[Paparazzi_Center|Paparazzi Center]] select the Microjet aircraft (from the '''A/C''' combo box) which is configured with the &amp;lt;tt&amp;gt;basic.xml&amp;lt;/tt&amp;gt; flight plan. From the '''Target''' combo box, select &amp;lt;tt&amp;gt;sim&amp;lt;/tt&amp;gt; and click the '''Build''' button to compile the airbone code to be run on your Linux box. From the '''Session''' combo box, select &amp;lt;tt&amp;gt;Simulation&amp;lt;/tt&amp;gt; entry and click '''Execute''' to start the simulation. It will start &lt;br /&gt;
three processes which are listed in the window below:&lt;br /&gt;
* '''Microjet''' is the interface of a simulator program. It runs the same code as the one for the autopilot processor plus a rudimentary flight dynamic model. it allows you to test the interactions with the UAV and the flight plan execution.&lt;br /&gt;
* '''GCS''' ([[GCS|Ground Control Station]]) is the main window. It displays the track of the aircraft, as well as informations about the execution of its flight plans. This program provide menus for the datalink functions and is able to edit a flight plan.&lt;br /&gt;
* '''Server''' is a hidden process which won't be described here (see [[Overview|the architecture of the system]])&lt;br /&gt;
&lt;br /&gt;
== Start the Simulation ==&lt;br /&gt;
&lt;br /&gt;
The aircraft has automatically been booted, as if the autopilot board had been powered. Its position and its flight parameters are displayed in the GCS window. If you omit the -boot option of the sim the aircraft is not automatically booted and you can first place the aircraft where you want it to start from and then boot.&lt;br /&gt;
&lt;br /&gt;
If the --norc option is ommited, a window for a virtual remote control (including on/off switch and a mode-switch) is started, see: [https://wiki.paparazziuav.org/wiki/Joystick#Virtual_Joystick_.28only_for_SIM_targets.29  Virtual Joystick]&lt;br /&gt;
&lt;br /&gt;
In the GCS the map widget is able to use many map formats and display them according to many projections. To make things simple, we start by using images from [http://maps.google.com Google]. From the toolbar in the top right corner of the GCS, click the Google Earth icon ('''Google maps fill'''). The program attempts to download the required satellite images from the Google servers. If it succeeds, you should now see the nice countryside of Muret (a city close to Toulouse, France). Navigation and other features of the map are described on the [[GCS#map|GCS]] page.&lt;br /&gt;
&lt;br /&gt;
The lower part of the GCS displays the flight plan in a tree view. You see that the current flight plan is composed of several ''blocks'':&lt;br /&gt;
* '''wait GPS''' and '''geo init''' which are instructions to run this flight plan anywhere in the world, by translating the waypoints around the current location of aircraft as soon as it is reported by the GPS.&lt;br /&gt;
* '''Holding point''' (it  should be the current active block) which instructs the autopilot to wait for launch.  &lt;br /&gt;
* '''Takeoff''' which will instruct the aircraft to climb full throttle to a security altitude&lt;br /&gt;
* '''Standby''' which is a simple circle around the '''STDBY''' waypoint.&lt;br /&gt;
&lt;br /&gt;
Switch to the '''Takeoff''' block by a double click on the line or using the corresponding button (an icon figuring an airway) on the left side of the strip.&lt;br /&gt;
&lt;br /&gt;
== Fly ==&lt;br /&gt;
&lt;br /&gt;
In the Simulator ('''Microjet''' window), press the '''Launch''' button to simulate a hand launch or click the launch button in the GCS (the green aircraft icon). The autopilot detects the launch by monitoring the groundspeed. The flight time (in the aircraft label on the GCS) then starts to count.&lt;br /&gt;
&lt;br /&gt;
Position of the aircraft is displayed on the map: the aircraft goes to the '''CLIMB''' waypoint (to the norht-west) and then around the '''STDBY''' waypoint. Current block also changes accordingly in the flight plan display.&lt;br /&gt;
&lt;br /&gt;
The orange triangle (the carrot) on the map is the point that the aircraft is navigating toward.&lt;br /&gt;
&lt;br /&gt;
== Line ==&lt;br /&gt;
&lt;br /&gt;
Jump to this block with double-click on the &amp;lt;tt&amp;gt;Line 1-2&amp;lt;/tt&amp;gt; line in the flight plan or using the corresponding button in the strip (figuring a blue line between two white points). The aircraft will try to follow a line joining the waypoints '''1''' and '''2''', doing nice U-turns at both ends.&lt;br /&gt;
&lt;br /&gt;
=== Move waypoints ===&lt;br /&gt;
&lt;br /&gt;
While the aircraft is flying (or here while the simulator is integrating differential equations), you can move the waypoints on the GCS interface by cliking and dragging (with the left button). When the mouse button is released, a popup window allows you to change the altitude of the waypoint. After validation, the waypoint changes are sent to the autopilot and the followed track is changed accordingly.&lt;br /&gt;
&lt;br /&gt;
=== Coming back around ===&lt;br /&gt;
&lt;br /&gt;
Select the '''Standby''' block (the ''home'' blue icon) to instruct the aircraft to fly around the '''STDBY''' waypoint.&lt;br /&gt;
&lt;br /&gt;
== Fly too far ==&lt;br /&gt;
&lt;br /&gt;
If you unzoom the map (using the PageDown key or he mouse wheel), you will see a large circle around the waypoints. This circle show the allowed flying zone that the autopilot must not leave or it will enter an emergency navigation mode and circles the '''HOME''' waypoint until the further direction is received.&lt;br /&gt;
&lt;br /&gt;
Move the waypoint '''2''' out of this circle (close to the circle in the north-east corner) and switch back to the 'Line 1-2''' block to force the plane to get out of this safety zone.&lt;br /&gt;
&lt;br /&gt;
The aircraft flies to the '''2''' waypoint, cross the protection enveloppe and switches to ''home'' mode: the AP mode in the aircraft strip switches from '''AUTO2''' to '''HOME'''.&lt;br /&gt;
&lt;br /&gt;
To get out of this mode and switch back to the default '''AUTO2''', click on the '''AUTO2''' button in the aircraft strip. The aircraft then flies again towards '''too far''' and again swithes to '''HOME''' mode.&lt;br /&gt;
&lt;br /&gt;
== Change the environment ==&lt;br /&gt;
&lt;br /&gt;
Launch the '''Environment Simulator''' from the '''Tools' menu in the '''Paparazzi Center'''.&lt;br /&gt;
&lt;br /&gt;
[[file:PPRZ_Environment_settings_Gaia_GUI_up.png]]&lt;br /&gt;
&lt;br /&gt;
This interface, also known as '''Gaia''', allows the user to change:&lt;br /&gt;
&lt;br /&gt;
* The time-scale: This make the simulation of the flight speed up time, good if you have a extensive flightpland and you do not want to wait the real time it would taketo fly the aircraft in a real life flight. It is best not use a times-cale higher than 2x for a first tryout.&lt;br /&gt;
* The Wind speed: Set the wind speed while simulating. Try to set it to e.g. 5m/s and observe the trajectory and the speed evolution in the aircraft strip and in the '''PFD''' page of the notebook&lt;br /&gt;
* The Wind direction: Set the direction the wind comse from. For fun try to take of with stong wind from the side.&lt;br /&gt;
* Wind up: Simulates updraft (e.g. by thermals) or downdraft wind (beside thunderstorms or in mountains), which could e.g. shift the UAS higher than permitted, which can be counteracted by exceptions in the flightplan.&lt;br /&gt;
* A GPS failure: Simulate GPS loss on the aircraft ('''GPS OFF''') and observe the resulting mode ('''NO_GPS''') and trajectory. In this mode, the autopilot can for example use a the failsafe roll, pitch and throttle settings defined in the airframe file. Note that in a real flight, an aircraft without GPS won't be able to send it's position ... The simulation is cheating here! It must, otherwise not possible to show the path in the simulator ofcourse.&lt;br /&gt;
&lt;br /&gt;
Environment Simulator, Gaia can also be started with initial values set by command line option. &lt;br /&gt;
&lt;br /&gt;
   -b Bus Default is 127.255.255.255:2010&lt;br /&gt;
   -t Set time scale (default: 1.0)&lt;br /&gt;
   -w Set wind speed (0-30m/s)&lt;br /&gt;
   -d Set wind direction 0-359 deg&lt;br /&gt;
   -g Turn off GPS&lt;br /&gt;
   -help  Display this list of options&lt;br /&gt;
   --help  Display this list of options&lt;br /&gt;
&lt;br /&gt;
If you are in the testfield and forgot the parameters, just use the &amp;quot;help&amp;quot;&lt;br /&gt;
&lt;br /&gt;
 $ ./gaia --help&lt;br /&gt;
&lt;br /&gt;
This make testing more convienient since on can save a session with this parameters and on restart imidately have the same settings again.&lt;br /&gt;
&lt;br /&gt;
=== Example ===&lt;br /&gt;
&lt;br /&gt;
Starting gaia with the following parameters on the command line:&lt;br /&gt;
&lt;br /&gt;
 $ sw/simulator/gaia -t 3 -d 340 -w 11&lt;br /&gt;
&lt;br /&gt;
This sets a 3x speedup of the time with wind coming from 340 degrees with a windspeed of 11m/s&lt;br /&gt;
&lt;br /&gt;
== Other navigation patterns ==&lt;br /&gt;
&lt;br /&gt;
Using the buttons in the strip, you can play with other navigation patterns: figure of eights, oval, survey of a rectangle (with a north-south sweeping), ''Circle around here'' (which sets a waypoint to the current location of the plane and flies a circle around).&lt;br /&gt;
&lt;br /&gt;
== Landing ==&lt;br /&gt;
&lt;br /&gt;
To automatically land the aircraft:&lt;br /&gt;
* Set the '''TD''' (Touch Down) waypoint where you want to land. Be sure that the waypoint is on the ground (185m in Muret)&lt;br /&gt;
* Set the '''AF''' (Approach Fix) waypoint where you want to start the final descent (the ''glide''). If you have set some wind with Gaia, you probably want to fly '''AF-TD''' upwind (an estimation of the wind experienced by the aircraft is displayed in the left-upper corner of the map).&lt;br /&gt;
* Switch to the '''Land right''' or the '''Land left''' block (icons in the strip) according to the direction of the last turn you want to do (for example, if '''AF''' is on the east side of '''TD''' and you want to maneuvre from the north, choose a '''Land right''') &lt;br /&gt;
&lt;br /&gt;
== Multiple UAV Simulation ==&lt;br /&gt;
&lt;br /&gt;
To simulate multiple aircrafts, you just have to launch a second simulator (tools-&amp;gt;simulator, then -a yourairframe) and the server and the GCS should take care of the rest.&lt;br /&gt;
&lt;br /&gt;
== View the simulation in Flight Gear ==&lt;br /&gt;
&lt;br /&gt;
To view the simulation in [[FlightGear]], do the following:&lt;br /&gt;
* [[FlightGear|install Flight Gear]]&lt;br /&gt;
* In Paparazzi Center, add the option &amp;lt;tt&amp;gt;--fg_host 127.0.0.1&amp;lt;/tt&amp;gt; (replace the IP address if FG is running on another host as appropriate) to the Simulator line and restart it, e.g.:&lt;br /&gt;
 &amp;lt;path_to_paparazzi&amp;gt;/sw/simulator/pprzsim-launch --aircraft &amp;lt;your_ac_name&amp;gt; -t sim --boot --norc --fg_host 127.0.0.1&lt;br /&gt;
&amp;lt;div class=&amp;quot;toccolours mw-collapsible mw-collapsed&amp;quot;&amp;gt;&lt;br /&gt;
Prior to '''v5.0''' launchsitl was used instead of pprzsim-launch. Click expand to see the details.&lt;br /&gt;
&amp;lt;div class=&amp;quot;mw-collapsible-content&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;path_to_paparazzi&amp;gt;/sw/simulator/launchsitl -a &amp;lt;your_ac_name&amp;gt; -boot -norc -fg 127.0.0.1&lt;br /&gt;
&amp;lt;/div&amp;gt;&amp;lt;/div&amp;gt;&lt;br /&gt;
* Launch Flight Gear with the following command:&lt;br /&gt;
 fgfs --fdm=null --native-gui=socket,in,30,,5501,udp&lt;br /&gt;
&lt;br /&gt;
=== Old version ===&lt;br /&gt;
For Flight Gear visualization, version 2.12 or greater with rembrand visualisation options switched on is the nicest. If you wish to use a very old version, Flightgear v2.4 or lower, you must add the following to the firmware section of your airframe file:&lt;br /&gt;
{{Box Code|conf/airframes/myplane.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;firmware name=&amp;quot;fixedwing or rotorcraft&amp;quot;&amp;gt;&lt;br /&gt;
     ...&lt;br /&gt;
     &amp;lt;define name=&amp;quot;FG_2_4&amp;quot; value=&amp;quot;1&amp;quot;/&amp;gt;&lt;br /&gt;
     ...&lt;br /&gt;
  &amp;lt;/firmware&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== Obtain Screenshots from FlightGear into PaparazziUAV ===&lt;br /&gt;
&lt;br /&gt;
One can write a relatively simple module in order to obtain screenshots of the FlightGear world into the PaparazziUAV software. This can be useful to simulate low fidelity computer vision tasks with UAVs. The module requires libcurl and libpng to make the screenshot data available to PaparazziUAV. Detailed instructions are available in [[Load Screenshots from FlightGear]].&lt;br /&gt;
&lt;br /&gt;
[[Category:Simulation]] [[Category:Software]] [[Category:User_Documentation]]&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Flight_Plans&amp;diff=23654</id>
		<title>Flight Plans</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Flight_Plans&amp;diff=23654"/>
		<updated>2017-04-05T16:25:29Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: /* Loops */  Put in a suggested maximum range for for loops&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;A '''flight plan''' is a XML document which one can create and store aboard an autopilot. The flight plan will describe how you want your aircraft to travel if released into into the wild blue yonder.&lt;br /&gt;
&lt;br /&gt;
== DTD and Structure ==&lt;br /&gt;
&lt;br /&gt;
The formal description of the flight plan file is given in the [http://en.wikipedia.org/wiki/Document_Type_Definition '''DTD'''] (located in &amp;lt;tt&amp;gt;conf/flight_plans/flight_plan.dtd&amp;lt;/tt&amp;gt;). This&lt;br /&gt;
DTD must be referenced in the header of your flight plan XML document using the following line:&amp;lt;br&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;!DOCTYPE flight_plan SYSTEM &amp;quot;flight_plan.dtd&amp;quot;&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The flight plans are stored in the &amp;lt;tt&amp;gt;conf/flight_plans&amp;lt;/tt&amp;gt; directory. The [[Flight_Plan_Editor|flight plan editor]] can be used to create basic flight plans via the GUI.&lt;br /&gt;
&lt;br /&gt;
Extract from the [http://en.wikipedia.org/wiki/Document_Type_Definition DTD]:&lt;br /&gt;
 &amp;lt;tt&amp;gt;&amp;lt;!ELEMENT flight_plan (header?,waypoints,sectors?,variables?,includes?,exceptions?,blocks)&amp;gt;&amp;lt;/tt&amp;gt;&lt;br /&gt;
&lt;br /&gt;
'''A flight plan is composed of two mandatory elements: [[#waypoints|waypoints]] and [[#blocks|blocks]]'''&lt;br /&gt;
&lt;br /&gt;
The root &amp;lt;tt&amp;gt;flight_plan&amp;lt;/tt&amp;gt; element is specified with several attributes:&lt;br /&gt;
 &amp;lt;tt&amp;gt;'''&amp;lt;flight_plan name lat0 lon0 ground_alt security_height home_mode_height qfu alt max_dist_from_home&amp;gt;'''&amp;lt;/tt&amp;gt;&lt;br /&gt;
; &amp;lt;tt&amp;gt;'''name'''&amp;lt;/tt&amp;gt;: The name of the mission (a text string)&lt;br /&gt;
; &amp;lt;tt&amp;gt;'''lat0, lon0'''&amp;lt;/tt&amp;gt;: Defines the latitude and longitude coordinates of the reference point {0,0} in WGS84 degree coordinates&lt;br /&gt;
; &amp;lt;tt&amp;gt;'''ground_alt'''&amp;lt;/tt&amp;gt;: The ground altitude (in meters), Above Sea Level where you are flying. It defines the &amp;lt;tt&amp;gt;GROUND_ALT&amp;lt;/tt&amp;gt; constant value which can be used in combination with a waypoint &amp;lt;height&amp;gt; parameter to define a waypoint height&lt;br /&gt;
; &amp;lt;tt&amp;gt;'''security_height'''&amp;lt;/tt&amp;gt;:  The height (over &amp;lt;tt&amp;gt;'''ground_alt'''&amp;lt;/tt&amp;gt;) used by the circle-home failsafe procedure and in other flight procedures such as formation flight and anti-collision avoidance. Warnings are produced if you place a waypoint lower than &amp;lt;tt&amp;gt;'''security_height'''&amp;lt;/tt&amp;gt; (usually the case for the landing point)&lt;br /&gt;
; &amp;lt;tt&amp;gt;'''home_mode_height'''&amp;lt;/tt&amp;gt; (optional): This optional attribute available since v4.2 allows to override &amp;lt;tt&amp;gt;'''security_height'''&amp;lt;/tt&amp;gt; as failsafe height in home mode. If &amp;lt;tt&amp;gt;'''home_mode_height'''&amp;lt;/tt&amp;gt; Is set lower than &amp;lt;tt&amp;gt;'''security_height'''&amp;lt;/tt&amp;gt;, the later is used. This attribute is useful if you need to return home at a high altitude rather than a low altitude.&lt;br /&gt;
; &amp;lt;tt&amp;gt;'''qfu'''&amp;lt;/tt&amp;gt; (optional): defines the global constant &amp;lt;tt&amp;gt;QFU&amp;lt;/tt&amp;gt;. It usually is the magnetic heading in degrees (north=0, east=90) of the runway, the opposite of wind direction. This constant may be used in the mission description. It is also used by the simulator as the original course of the aircraft. So if you want to take off and climb to the West you would use qfu=270. &lt;br /&gt;
; &amp;lt;tt&amp;gt;'''alt'''&amp;lt;/tt&amp;gt;: The default altitude of waypoints ([[Altitude_definitions|Above Sea Level]]). So if your ground altitude is 400 then alt needs to be a value greater than ground altitude and above any obstructions in the flight plan. &lt;br /&gt;
; &amp;lt;tt&amp;gt;'''max_dist_from_home'''&amp;lt;/tt&amp;gt;: A radius representing the maximum allowed distance (in meters) from the HOME waypoint. Exceeding this value (ie flying outside the circle with this radius) will trigger an exception. It is up to you to define the block to be executed (ie what to do) for the exception.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
''Here is an '''example''' of such a line in the top of a flight plan:''&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;flight_plan alt=&amp;quot;250&amp;quot; ground_alt=&amp;quot;185&amp;quot; lat0=&amp;quot;43.46223&amp;quot; lon0=&amp;quot;1.27289&amp;quot; name=&amp;quot;Example Muret&amp;quot; max_dist_from_home=&amp;quot;300&amp;quot; qfu=&amp;quot;270&amp;quot; security_height=&amp;quot;25&amp;quot; &amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Note that a flight plan could also contain optional &amp;lt;tt&amp;gt;include&amp;lt;/tt&amp;gt;'s and &amp;lt;tt&amp;gt;exceptions&amp;lt;/tt&amp;gt; cases.&lt;br /&gt;
&lt;br /&gt;
In English the above flight plan says the name is Example Muret. The reference coordinates for the 0,0 point is: 43.46223 (lat) and 1.27289 (long). The flying site 0,0 location is 185m above sea level. The security height is 25m above 0,0 point or 210m above sea level. The default (ie if not defined in a waypoint this alt is used) altitude is 250m (above sea level). The home mode block altitude is defined to be 150m above sea level. Also, for security, a circle is defined with a radius that's 300m from 0,0 position. This is the max_dist_from_home value. Fly 301m from 0,0 and an exception is triggered. A useful block is to trigger/go to the home mode block and return to home when the aircraft flies outside the safety circle. Example flight plans are helpful for study before you build your own from scratch.&lt;br /&gt;
&lt;br /&gt;
== Waypoints ==&lt;br /&gt;
&lt;br /&gt;
The waypoints are the geographic locations used to specify the trajectories. A waypoint is specified by it's name and coordinates:&lt;br /&gt;
 &amp;lt;tt&amp;gt;''' &amp;lt;waypoint name wpx wpy [alt] [height]/&amp;gt; '''&amp;lt;/tt&amp;gt;&lt;br /&gt;
where wpx and wpy are real positional coordinates ( &amp;lt;tt&amp;gt;'''lat/lon'''&amp;lt;/tt&amp;gt; )  '''or''' UTM coordinates ( &amp;lt;tt&amp;gt;'''utm_x0/utm_y0'''&amp;lt;/tt&amp;gt; ) '''or''' relative coordinates ( &amp;lt;tt&amp;gt;'''x/y'''&amp;lt;/tt&amp;gt; ) in meters from your reference point {0,0} .  &amp;lt;tt&amp;gt;alt&amp;lt;/tt&amp;gt; is an optional parameter and can be used to assign an altitude to a particular waypoint that is different from the globally defined &amp;lt;tt&amp;gt;alt&amp;lt;/tt&amp;gt; parameter of the flightplan. The &amp;lt;tt&amp;gt;height&amp;lt;/tt&amp;gt; attribute can be used to set the waypoint height relative to the [[Altitude_definitions|ground altitude]] (&amp;lt;tt&amp;gt;ground_alt&amp;lt;/tt&amp;gt;) of the flight plan for this waypoint.&lt;br /&gt;
&lt;br /&gt;
An example:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;waypoints&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;HOME&amp;quot; x=&amp;quot;0.0&amp;quot; y=&amp;quot;30.0&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;BRIDGEOVERRIVER&amp;quot; x=&amp;quot;-100.0&amp;quot; y=&amp;quot;60.0&amp;quot; alt=&amp;quot;270.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;MyBarn&amp;quot; x=&amp;quot;-130.0&amp;quot; y=&amp;quot;217.5&amp;quot; alt=&amp;quot;3000.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;3&amp;quot; x=&amp;quot;-30.0&amp;quot; y=&amp;quot;50&amp;quot; height=&amp;quot;50.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;4&amp;quot; x=&amp;quot;-30.0&amp;quot; y=&amp;quot;50.&amp;quot; alt=&amp;quot;ground_alt + 50&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;_MYHELPERSPOT&amp;quot; x=&amp;quot;-30.0&amp;quot; y=&amp;quot;60&amp;quot; height=&amp;quot;50.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;_MYOTHERHELPERSPOT&amp;quot; x=&amp;quot;-70.0&amp;quot; y=&amp;quot;90&amp;quot; height=&amp;quot;70.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;TOWER&amp;quot; lat=&amp;quot;48.858249&amp;quot; lon=&amp;quot;2.294494&amp;quot; height=&amp;quot;324.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;MountainCAFE&amp;quot; utm_x0=&amp;quot;360284.8&amp;quot; utm_y0=&amp;quot;4813595.5&amp;quot; alt=&amp;quot;1965.&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/waypoints&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
'''Tips'''&lt;br /&gt;
* Waypoints are easily adjusted with the [[Flight_Plan_Editor|flight plan editor]].&lt;br /&gt;
* If a waypoint name starts with an underscore ( _ ), the waypoint is '''not displayed''' in the GCS, except in editor mode.&lt;br /&gt;
* The maximum number of waypoints is 254.&lt;br /&gt;
* A waypoint named &amp;lt;tt&amp;gt;HOME&amp;lt;/tt&amp;gt; is required if the failsafe HOME mode procedure is used.&lt;br /&gt;
* A waypoints index/reference pointer is derived by prefixing the waypoint name with &amp;quot;WP_&amp;quot;. Useful when a [[#Call |call function]] uses the waypoints reference index vs. it's name.&lt;br /&gt;
&lt;br /&gt;
== Sectors ==&lt;br /&gt;
&lt;br /&gt;
=== Static sectors (default) ===&lt;br /&gt;
&lt;br /&gt;
Flat ''Sectors'' can be described as an area defined by list of waypoint corners. Such an area will be displayed in the Ground Control Station (GCS) by colored lines connecting the cornerpoints.&lt;br /&gt;
A function is generated to check if a point, usually the aircraft itself, is ''inside'' this sector. Currently, this feature requires that the polygon is &amp;lt;b&amp;gt;convex&amp;lt;/b&amp;gt; and described in a &amp;lt;b&amp;gt;clockwise&amp;lt;/b&amp;gt; order. For a sector named &amp;lt;tt&amp;gt;MyBigGarden&amp;lt;/tt&amp;gt; the generated function for the example here would be &amp;lt;tt&amp;gt;bool_t InsideMyBigGarden(float x, float y);&amp;lt;/tt&amp;gt; where &amp;lt;tt&amp;gt;x&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;y&amp;lt;/tt&amp;gt; are east and north coordinated, in meters, relative to the geographic reference of the flight plan. If the flight plan is dynamically relocated, such a sector will be relocated but the display is currently not updated on the GCS. It would be great if one would help improving that part of the source code. Note that sector names are not allowed to contain spaces.&lt;br /&gt;
&lt;br /&gt;
For example, with the following element in a flight plan.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;sectors&amp;gt;&lt;br /&gt;
    &amp;lt;sector name=&amp;quot;MyBigGarden&amp;quot; color=&amp;quot;red&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;_1&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;_2&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;_3&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;_4&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/sector&amp;gt;&lt;br /&gt;
  &amp;lt;/sectors&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
It is then possible to add an exception clause to your flightplan. For example if the aircraft for some reason flies outside this, defined by us, sector the airframe will fly to a standby waypoint. The exclamation mark (!) means the boolean operator &amp;lt;tt&amp;gt;NOT&amp;lt;/tt&amp;gt; in this example. In regular language one would describe &amp;quot;If my airframe is NOT inside the MyBigGarden sector anymore then deroute it to the standby waypoint. In Flightplan &amp;quot;Speak&amp;quot; this is written like: &lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;exception cond=&amp;quot;! InsideMyBigGarden(GetPosX(), GetPosY())&amp;quot; deroute=&amp;quot;standby&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
NOTE: editing of the waypoints of the sector during the flight will not dynamically update the inside function. It will always check if the position is inside the original sector.&lt;br /&gt;
&lt;br /&gt;
'''Tips'''&lt;br /&gt;
* A nice option in the corner notation is that one can add an underscore ( _ ) in front of the name; a corner or waypoint name that starts with an underscore is not displayed in the GCS. Only in editor mode it is visible. It is visible in editor mode, because if you the could not see it, it also would be not possible to edit or drag the corner or waypoint to another position.&lt;br /&gt;
* The color indicating the sector borders is not fixed but can be defined by oneself if wished for via the color attribute.&lt;br /&gt;
&lt;br /&gt;
=== Dynamic sectors ===&lt;br /&gt;
&lt;br /&gt;
With the latest version (v5.5-devel-628), it is possible to create dynamic sectors. The procedure to create the sector is the same than for the static version with an extra attribute '''type=&amp;quot;dynamic&amp;quot;''':&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;sectors&amp;gt;&lt;br /&gt;
    &amp;lt;sector name=&amp;quot;MyBigGarden&amp;quot; color=&amp;quot;red&amp;quot; type=&amp;quot;dynamic&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;C1&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;C2&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;C3&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;C4&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/sector&amp;gt;&lt;br /&gt;
  &amp;lt;/sectors&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
It is also recommended to avoid using hidden waypoints (no _ prefix), so you can move the corner of your sector from the GCS. The polygon is updated on the 2D map to reflect the new waypoints positions.&lt;br /&gt;
Beside the possibility to change the shape of the area in flight, one of the main benefit is that the algorithm behind allows concave hulls. The only restriction is that the edges of the polygon should not cross each other.&lt;br /&gt;
&lt;br /&gt;
The generated function is the same than the static version and can be used the same way.&lt;br /&gt;
&lt;br /&gt;
== Variables ==&lt;br /&gt;
&lt;br /&gt;
'''Available since v5.9'''&lt;br /&gt;
&lt;br /&gt;
It is possible to declare a list of variables that will be automatically created during the flight plan generation and available for the rest of the system from the generated flight plan header and of course inside the flight plan itself. With appropriate attributes, it is also possible to make the variables accessible from the telemetry as a [[Settings|setting]].&lt;br /&gt;
&lt;br /&gt;
The following code will produce a '''float''' variable initialized to 0:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;variables&amp;gt;&lt;br /&gt;
    &amp;lt;variable var=&amp;quot;my_var&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/variables&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The type and the initial value can be changed with the '''type''' and '''init''' attributes:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;variables&amp;gt;&lt;br /&gt;
    &amp;lt;variable var=&amp;quot;my_var&amp;quot; init=&amp;quot;10&amp;quot; type=&amp;quot;int&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/variables&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
To produce an automatic setting for a variable, at least '''min''', '''max''' and '''step''' attributes need to be specified:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;variables&amp;gt;&lt;br /&gt;
    &amp;lt;variable var=&amp;quot;my_var&amp;quot; min=&amp;quot;0.&amp;quot; max=&amp;quot;10.&amp;quot; step=&amp;quot;0.1&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/variables&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
They will appear under the '''Flight Plan''' settings tab in the GCS. So more attributes can be specified: '''shortname''', '''unit''', '''alt_unit''', '''alt_unit_coef''', '''values'''. See [[Settings]] page for more information about these options.&lt;br /&gt;
&lt;br /&gt;
== Includes ==&lt;br /&gt;
&lt;br /&gt;
&amp;lt;tt&amp;gt;include&amp;lt;/tt&amp;gt; is used to add some flight plan elements defined in an external procedure. It’s useful to include pre-written procedures with only few arguments and then clarify the flight plan.&lt;br /&gt;
Here is the structure:&lt;br /&gt;
 &amp;lt;tt&amp;gt;&amp;lt;include name procedure&amp;gt; [&amp;lt;arg name value /&amp;gt;]*[&amp;lt;with from to /&amp;gt;]*&amp;lt;/include&amp;gt;&amp;lt;/tt&amp;gt;&lt;br /&gt;
where &amp;lt;tt&amp;gt;name&amp;lt;/tt&amp;gt; attribute of the include element will be used in this flight plan to prefix the blocks of the &amp;lt;tt&amp;gt;procedure&amp;lt;/tt&amp;gt;, the XML referenced file.&lt;br /&gt;
Named arguments may be given with their value in the &amp;lt;tt&amp;gt;arg&amp;lt;/tt&amp;gt; elements. The &amp;lt;tt&amp;gt;with&amp;lt;/tt&amp;gt; tag allows to link labels (e.g. attribute of a deroute instruction or of an exception) from the procedure to blocks of the main flight plan.&lt;br /&gt;
Then, each block of the procedure is like any block of the flight plan and is designated with a dotted identifier: block &amp;lt;tt&amp;gt;b&amp;lt;/tt&amp;gt; of a procedure named &amp;lt;tt&amp;gt;p&amp;lt;/tt&amp;gt; is named &amp;lt;tt&amp;gt;b.p&amp;lt;/tt&amp;gt; .&lt;br /&gt;
&lt;br /&gt;
Here is an example:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;includes&amp;gt;&lt;br /&gt;
    &amp;lt;include name=&amp;quot;landing&amp;quot; procedure=&amp;quot;landing.xml&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/includes&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Blocks ==&lt;br /&gt;
&lt;br /&gt;
Block elements are the main part of a flight plan: they describe each unit of the mission.&lt;br /&gt;
They are made of various primitives, called stages and exceptions, you can put one after the other. When a&lt;br /&gt;
stage (or a block) is finished, the autopilot goes to the next one. The behaviour after the last stage of the last block is undefined. &lt;br /&gt;
&lt;br /&gt;
As described in the DTD, the &amp;lt;tt&amp;gt;blocks&amp;lt;/tt&amp;gt; element is composed of &amp;lt;tt&amp;gt;block&amp;lt;/tt&amp;gt; elements which are sequence of ''stages'':&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;!ELEMENT blocks (block+)&amp;gt;&lt;br /&gt;
  &amp;lt;!ELEMENT block  (exception|while|heading|attitude|go|xyz|set|call|circle|deroute|stay|follow|survey_rectangle|for|return|eight|oval|home|path)*&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Example:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;block name=&amp;quot;circlehome&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;circle radius=&amp;quot;75&amp;quot; wp=&amp;quot;HOME&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
You can add a button in the [[GCS#Strips|strip of the aircraft]] with the attribute &amp;lt;tt&amp;gt;strip_button&amp;lt;/tt&amp;gt;:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;block name=&amp;quot;descent&amp;quot; strip_button=&amp;quot;Descent&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;circle wp=&amp;quot;HOME&amp;quot; throttle=&amp;quot;0.0&amp;quot; pitch=&amp;quot;-15&amp;quot; vmode=&amp;quot;throttle&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
This button will activate the block. If the attribute &amp;lt;tt&amp;gt;group&amp;lt;/tt&amp;gt; is specified, all strip buttons of the same group will be placed vertically on top of each other.&lt;br /&gt;
&lt;br /&gt;
In the same way, a key shortcut can be specified:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;block key=&amp;quot;D&amp;quot; name=&amp;quot;descent&amp;quot; strip_button=&amp;quot;Descent&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;circle wp=&amp;quot;HOME&amp;quot; throttle=&amp;quot;0.0&amp;quot; pitch=&amp;quot;-15&amp;quot; vmode=&amp;quot;throttle&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
Modifiers are allowed, using the syntax of [http://library.gnome.org/devel/gtk/2.15/gtk-Keyboard-Accelerators.html#gtk-accelerator-parse GTK accelerators].&lt;br /&gt;
&lt;br /&gt;
An icon can be specified to display the button. The &amp;lt;tt&amp;gt;strip_button&amp;lt;/tt&amp;gt; label then is a tooltip for the icon. The icon must be an image file available in the directory &amp;lt;tt&amp;gt;data/pictures/gcs_icons&amp;lt;/tt&amp;gt;:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;block name=&amp;quot;Takeoff&amp;quot; strip_icon=&amp;quot;takeoff.png&amp;quot; strip_button=&amp;quot;Takeoff&amp;quot;&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
You can call functions before or after each execution of the block:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;block name=&amp;quot;circlehome&amp;quot; pre_call=&amp;quot;function_to_call_before_circle()&amp;quot; post_call=&amp;quot;function_to_call_after_circle()&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;circle wp=&amp;quot;HOME&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Expressions ====&lt;br /&gt;
&lt;br /&gt;
Most of the numeric attributes in stages are analyzed as C expressions. The syntax of this C expression is restricted to &lt;br /&gt;
* numeric constants&lt;br /&gt;
* some internal autopilot variables (not fully documented, see [[Flight_Plans#Internal_Variables_in_Flight_Plans|internal variables section]] below and other examples)&lt;br /&gt;
* Some binary operators: &amp;lt;, &amp;gt;, &amp;lt;=, &amp;gt;=, &amp;lt;&amp;gt;, ==, +, -, /, *&lt;br /&gt;
* Some utility functions&lt;br /&gt;
&lt;br /&gt;
Some examples of usable expressions are given in the next sections.&lt;br /&gt;
=== Initialization  Blocks ===&lt;br /&gt;
Most flight plans will have three blocks of flight plan initialization blocks. It is good practice to follow this example below if you first start learning to create flightplans&lt;br /&gt;
&lt;br /&gt;
The first block waits until the GPS fix has been established, as shown below.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;blocks&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Wait GPS&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;set value=&amp;quot;1&amp;quot; var=&amp;quot;kill_throttle&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;while cond=&amp;quot;!GpsFixValid()&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
The second block updates the local waypoints with respect to the UAV.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Geo init&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;while cond=&amp;quot;LessThan(NavBlockTime(), 10)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;NavSetGroundReferenceHere()&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
This next block prevents the UAV from starting the engine and taking off. &lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Holding point&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;!--set var=&amp;quot;nav_mode&amp;quot; value=&amp;quot;NAV_MODE_ROLL&amp;quot;/--&amp;gt;&lt;br /&gt;
      &amp;lt;set value=&amp;quot;1&amp;quot; var=&amp;quot;kill_throttle&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;attitude roll=&amp;quot;0&amp;quot; throttle=&amp;quot;0&amp;quot; vmode=&amp;quot;throttle&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Exceptions ===&lt;br /&gt;
&lt;br /&gt;
The flight manager can handle exceptions. They consist in conditions checked periodically (at the same pace as the navigation control), allowing the control to jump to a given block. Here is the syntax of exceptions:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;exception cond=&amp;quot;...&amp;quot; deroute=&amp;quot;...&amp;quot;&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
where &amp;lt;tt&amp;gt;cond&amp;lt;/tt&amp;gt; is an expression and &amp;lt;tt&amp;gt;deroute&amp;lt;/tt&amp;gt; is the name of the block we want to switch to as soon as the condition is true.&lt;br /&gt;
&lt;br /&gt;
Here are some example of exceptions:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;exception cond=&amp;quot;10 &amp;gt; PowerVoltage()&amp;quot; deroute=&amp;quot;go_down&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;exception cond=&amp;quot;(ground_alt+10 &amp;gt; GetPosAlt())&amp;quot; deroute=&amp;quot;go_up&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;exception cond=&amp;quot;(autopilot_flight_time &amp;gt; 840)&amp;quot; deroute=&amp;quot;quick_land&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Exceptions can be local to a block or global to the flight plan, in the &amp;lt;tt&amp;gt;&amp;lt;exceptions&amp;gt;&amp;lt;/tt&amp;gt; element. In the following example, time since last reception of a message from the ground station is monitored and the navigation is switched to the &amp;lt;tt&amp;gt;Standby&amp;lt;/tt&amp;gt; block if no message have been received for 22s. This exception is valid for '''all''' the blocks.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;flight_plan ...&amp;gt;&lt;br /&gt;
    &amp;lt;waypoints&amp;gt; ... &amp;lt;/waypoints&amp;gt;&lt;br /&gt;
    &amp;lt;exceptions&amp;gt;&lt;br /&gt;
      &amp;lt;exception cond=&amp;quot;datalink_time &amp;gt; 22&amp;quot; deroute=&amp;quot;Standby&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/exceptions&amp;gt;&lt;br /&gt;
  &amp;lt;blocks&amp;gt; ...&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Deroute ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;deroute&amp;lt;/tt&amp;gt; is the ''goto'' directive of the flight plan; it switches the navigation to the given block:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;deroute block=&amp;quot;landing&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Note that this primitive should not be used to execute loops which are provided by the following elements.&lt;br /&gt;
&lt;br /&gt;
=== Return ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;return&amp;lt;/tt&amp;gt; is also a ''goto'' directive that brings you back to the last block (and last stage). It has no argument.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;return/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Loops ===&lt;br /&gt;
&lt;br /&gt;
Unbounded loops are written with &amp;lt;tt&amp;gt;while&amp;lt;/tt&amp;gt; elements whose &amp;lt;tt&amp;gt;cond&amp;lt;/tt&amp;gt; attribute is a boolean expression.&lt;br /&gt;
Children  of &amp;lt;tt&amp;gt;while&amp;lt;/tt&amp;gt; are stages:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;while cond=&amp;quot;TRUE&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;go wp=&amp;quot;A&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;go wp=&amp;quot;B&amp;quot;/&amp;gt; &lt;br /&gt;
    &amp;lt;go wp=&amp;quot;C&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;while cond=&amp;quot;5 &amp;gt; stage_time&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;/while&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
In this example, we run an infinite loop, letting the aircraft try to go via waypoints &amp;lt;tt&amp;gt;A&amp;lt;/tt&amp;gt;, &amp;lt;tt&amp;gt;B&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;C&amp;lt;/tt&amp;gt; and waiting for 5 seconds before repeating.&lt;br /&gt;
&lt;br /&gt;
Bounded loops are written with the &amp;lt;tt&amp;gt;for&amp;lt;/tt&amp;gt; tag:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;for var=&amp;quot;i&amp;quot; from=&amp;quot;0&amp;quot; to=&amp;quot;3&amp;quot;&amp;gt;&lt;br /&gt;
    ...&lt;br /&gt;
  &amp;lt;/for&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
where the body of the loop will be run four times.&lt;br /&gt;
&lt;br /&gt;
The variable of a &amp;lt;tt&amp;gt;for&amp;lt;/tt&amp;gt; loop can be used inside expressions appearing as attributes of the stages:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;for var=&amp;quot;i&amp;quot; from=&amp;quot;1&amp;quot; to=&amp;quot;5&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;circle wp=&amp;quot;HOME&amp;quot; radius=&amp;quot;75&amp;quot; alt=&amp;quot;ground_alt+50*$i&amp;quot; until=&amp;quot;stage_time&amp;gt;10&amp;quot; /&amp;gt;&lt;br /&gt;
  &amp;lt;/for&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
In this example, the aircraft will circle around waypoint '''HOME''' for 10 seconds at an altitude above ground of 50m (1x50), 10 seconds at an altitude of 100m (2x50), ... until 250m (5x50).&lt;br /&gt;
&lt;br /&gt;
Note: Two bounded loops using the same control variable are not allowed in the same block. Further, I tested a specific implementation installation of PaparazziUAV v5.10 and I found the maximum range of the looping variable to be -128 to 126.&lt;br /&gt;
&lt;br /&gt;
=== Navigation modes ===&lt;br /&gt;
&lt;br /&gt;
Navigation modes give the description of the desired trajectory in 3D. While the horizontal mode is specified through&lt;br /&gt;
''stages'', the vertical control is specified with various attributes of these stages. The current available navigation stages are&lt;br /&gt;
* attitude : just keep a fixed attitude;&lt;br /&gt;
* heading : keep a given course;&lt;br /&gt;
* go : go to a given waypoint;&lt;br /&gt;
* path : list of waypoints linked by ''go''&lt;br /&gt;
* circle : circle around a waypoint;&lt;br /&gt;
* oval : two half circles with a straight between two nav points&lt;br /&gt;
* eight : fly a figure of eight through a waypoint and around another&lt;br /&gt;
* stay : hold the position (hard to realize for a fixed-wing aircraft);&lt;br /&gt;
* follow : follow another aircraft;&lt;br /&gt;
* xyz : circle around a point moveable with the RC transmitter stick (obsolete with the datalink).&lt;br /&gt;
&lt;br /&gt;
The vertical control is achieved using the &amp;lt;tt&amp;gt;vmode&amp;lt;/tt&amp;gt; attribute of these stages. The possible values are &lt;br /&gt;
* '''alt''' (the default) : the autopilot keeps the desired altitude which is the altitude of the waypoint (if any) or the altitude specified with the &amp;lt;tt&amp;gt;alt&amp;lt;/tt&amp;gt; attribute;&lt;br /&gt;
* '''climb''' : the autopilot keeps the desired vertical speed specified with the &amp;lt;tt&amp;gt;climb&amp;lt;/tt&amp;gt; attribute (in m/s);&lt;br /&gt;
* '''throttle''' : the autopilots sets the desired throttle specified with the &amp;lt;tt&amp;gt;throttle&amp;lt;/tt&amp;gt; attribute (between 0 and 1);&lt;br /&gt;
* '''glide''' : the autopilot keeps the desired slope between two waypoints&lt;br /&gt;
&lt;br /&gt;
The default control is done with the throttle. However, setting the &amp;lt;tt&amp;gt;pitch&amp;lt;/tt&amp;gt; attribute to '''auto''' and the &amp;lt;tt&amp;gt;throttle&amp;lt;/tt&amp;gt; attribute to a constant allows a vertical control only by controlling the attitude of the A/C.&lt;br /&gt;
The &amp;lt;tt&amp;gt;pitch&amp;lt;/tt&amp;gt; attribute also can be set to any value (in degrees) while the throttle control is in use: it usually affects the airspeed of the aircraft.  &lt;br /&gt;
&lt;br /&gt;
The different navigation modes are detailed in the next sections.&lt;br /&gt;
&lt;br /&gt;
=== Attitude ===&lt;br /&gt;
&lt;br /&gt;
Element &amp;lt;tt&amp;gt;attitude&amp;lt;/tt&amp;gt; is the navigation mode which corresponds to the current lowest control loop for horizontal mode.&lt;br /&gt;
The autopilot then keeps a constant attitude. The &amp;lt;tt&amp;gt;roll&amp;lt;/tt&amp;gt; attribute is required (in degrees, positive to put right wing low).&lt;br /&gt;
&lt;br /&gt;
To fly away, at constant airspeed:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;attitude roll=&amp;quot;0&amp;quot; vmode=&amp;quot;throttle&amp;quot;, throttle=&amp;quot;0.5&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
To fly around, holding a given altitude:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;attitude roll=&amp;quot;30&amp;quot; alt=&amp;quot;ground_alt+50&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Note that it is not a ''safe'' navigation mode since the geographic position of the plane is not controlled. However, this mode is useful to tune the roll attitude control loop.&lt;br /&gt;
&lt;br /&gt;
=== Heading ===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;tt&amp;gt;heading&amp;lt;/tt&amp;gt; primitive is relative to the second level loop for horizontal mode in the autopilot which will keep the given &amp;lt;tt&amp;gt;course&amp;lt;/tt&amp;gt;, a required attribute (in degrees, clockwise, north=0, east=90).&lt;br /&gt;
&lt;br /&gt;
One example to takeoff, following the QFU, 80% throttle, nose up (15 degrees) until height of 30m is reached:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;heading course=&amp;quot;QFU&amp;quot; vmode=&amp;quot;throttle&amp;quot; throttle=&amp;quot;0.8&amp;quot; pitch=&amp;quot;15&amp;quot; until=&amp;quot;(GetPosAlt() &amp;gt; ground_alt+30)&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Go ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;go&amp;lt;/tt&amp;gt; primitive is probably the most useful one. Basically, the autopilot will try to join a given waypoint (&amp;lt;tt&amp;gt;wp&amp;lt;/tt&amp;gt;, the only required attribute). So the simplest thing you can ask for is&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;go wp=&amp;quot;HOME&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
which will set the '''HOME''' waypoint as the desired target position. Note than since &amp;lt;tt&amp;gt;vmode=&amp;quot;alt&amp;quot;&amp;lt;/tt&amp;gt; is the default, the altitude of the target waypoint is also taken into account. The navigation will switch to the next stage as soon as the target is reached.&lt;br /&gt;
&lt;br /&gt;
It is usually not a good idea to try to join a waypoint without asking for a precise trajectory, i.e. a given line.&lt;br /&gt;
Setting the &amp;lt;tt&amp;gt;hmode&amp;lt;/tt&amp;gt; attribute to '''route''', the navigation will go over a segment joining two waypoints:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;go from=&amp;quot;wp1&amp;quot; wp=&amp;quot;wp2&amp;quot; hmode=&amp;quot;route&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The target altitude is the altitude of the target waypoint; it can also be set with the &amp;lt;tt&amp;gt;alt&amp;lt;/tt&amp;gt; attribute. The following example keeps an altitude with fixed throttle:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;go from=&amp;quot;wp2&amp;quot; wp=&amp;quot;wp3&amp;quot; hmode=&amp;quot;route&amp;quot; pitch=&amp;quot;auto&amp;quot; throttle=&amp;quot;0.75&amp;quot; alt=&amp;quot;ground_alt+100&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The attributes related to the vertical control can also be set to replace the default altitude mode:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;go from=&amp;quot;wp1&amp;quot; wp=&amp;quot;wp2&amp;quot; hmode=&amp;quot;route&amp;quot; vmode=&amp;quot;climb&amp;quot; climb=&amp;quot;1.5&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Finally, the &amp;lt;tt&amp;gt;approaching_time&amp;lt;/tt&amp;gt; (in seconds) attribute helps to decide when the target is ''reached''. It can be set&lt;br /&gt;
to '''0''' to go over the target waypoint (default value is the '''CARROT''' time, set in the airframe configuration file).&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;go from=&amp;quot;wp1&amp;quot; wp=&amp;quot;wp2&amp;quot; hmode=&amp;quot;route&amp;quot; approaching_time=&amp;quot;1&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Path ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;path&amp;lt;/tt&amp;gt; primitive is just a shorthand expression for a set of &amp;lt;tt&amp;gt;go&amp;lt;/tt&amp;gt; primitives. A list of waypoints defined with the &amp;lt;tt&amp;gt;wpts&amp;lt;/tt&amp;gt; attribute is pre-processed into a set of &amp;lt;tt&amp;gt;go&amp;lt;/tt&amp;gt; primitives with the &amp;lt;tt&amp;gt;hmode&amp;lt;/tt&amp;gt; attribute. For example:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;path wpts=&amp;quot;wp1, wp2, wp3&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Other attributes are optional:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;path wpts=&amp;quot;wp3, wp1, wp2&amp;quot; approaching_time=&amp;quot;1&amp;quot; pitch=&amp;quot;auto&amp;quot; throttle=&amp;quot;0.5&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Circle ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;circle&amp;lt;/tt&amp;gt; primitive is the second main navigation mode: the trajectory is defined as a circle around a given waypoint with a given radius:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;circle wp=&amp;quot;HOME&amp;quot; radius=&amp;quot;75&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
A positive radius makes the UAS move clockwise, a negative counter-clockwise.&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;until&amp;lt;/tt&amp;gt; attribute may be used to control the end of the stage. The following example defines an ascending trajectory at constant throttle, nose up (15 degrees), over growing circles, until the battery level is low:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;circle wp=&amp;quot;wp1&amp;quot; radius=&amp;quot;50+(GetPosAlt()-ground_alt)/2&amp;quot; vmode=&amp;quot;throttle&amp;quot; throttle=&amp;quot;0.75&amp;quot; pitch=&amp;quot;15&amp;quot; until=&amp;quot;10&amp;gt;PowerVoltage()&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Oval ===&lt;br /&gt;
The oval consists of two half circles that are connected with two straight lines. This flight path is usefull when a IMU is used because the straights allow for level flight. &lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt; &amp;lt;oval p1=&amp;quot;1&amp;quot; p2=&amp;quot;2&amp;quot; radius=&amp;quot;nav_radius&amp;quot;/&amp;gt; &amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Eight ===&lt;br /&gt;
'''Works only for Fixed-wing!''' Fly a figure of eight that consists of two straight legs that pass though the center and the center of the half circle at the end of the two legs is in the turn around  waypoint. The altitude of the center waypoint is used for the entire figure. The turn around waypoint is moved to match radius given. &lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;  &amp;lt;eight center=&amp;quot;1&amp;quot; radius=&amp;quot;nav_radius&amp;quot; turn_around=&amp;quot;2&amp;quot;/&amp;gt; &amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Survey rectangle ===&lt;br /&gt;
Fly a survey rectangle defined by two waypoints. The distance between the legs of the grid (in meter) and the orientation of the grid (NS or WE) can be set by the operator. The plane will turn outside of the border of the rectangle before starting a new leg.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;  &amp;lt;survey_rectangle wp1=&amp;quot;1&amp;quot; wp2=&amp;quot;2&amp;quot; grid=&amp;quot;200&amp;quot; orientation=&amp;quot;NS&amp;quot;/&amp;gt; &amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Follow ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;follow&amp;lt;/tt&amp;gt; is a special primitive which makes the UAS follow another UAS (real or simulated, named with its &amp;lt;tt&amp;gt;ac_id&amp;lt;/tt&amp;gt;) at a given &amp;lt;tt&amp;gt;distance&amp;lt;/tt&amp;gt; (in meters) behind and at a given &amp;lt;tt&amp;gt;height&amp;lt;/tt&amp;gt; (in meters) above.&lt;br /&gt;
&lt;br /&gt;
In this example, the autopilot will try to follow A/C number '''4''', staying '''50'''m behind and '''20'''m above.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;follow ac_id=&amp;quot;4&amp;quot; distance=&amp;quot;50&amp;quot; height=&amp;quot;20&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Stay ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;stay&amp;lt;/tt&amp;gt; Here the UAS with try to stay at the waypoint as best as it can. For an aircraft capable of hovering it will just hang above the waypoint. For a fixedwing type UAV,&amp;lt;tt&amp;gt;stay&amp;lt;/tt&amp;gt; will mean the aircraft will constantly fly straight through the waypoint in a flower like pattern with the smallest turn radius it can manage.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;stay wp=&amp;quot;HOME&amp;quot; alt=&amp;quot;10&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== XYZ ===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;tt&amp;gt;xyz&amp;lt;/tt&amp;gt; is a special mode where the UAS circles around a user moveable waypoint. This waypoint is moved with the RC sticks:&lt;br /&gt;
* YAW channel controls the point over the west-east axis;&lt;br /&gt;
* PITCH channel controls the point over the south-north axis;&lt;br /&gt;
* ROLL channel controls the altitude.&lt;br /&gt;
&lt;br /&gt;
Example (default radius is '''100'''):&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;xyz radius=&amp;quot;40&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Set ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;set&amp;lt;/tt&amp;gt; element is a dangerous one which should be used only by expert users: it is used to directly set an internal variable of the autopilot. For example, you can change the value of the default ground altitude, a variable used by the home mode failsafe procedure (and maybe by your own flight plan):&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;set var=&amp;quot;ground_alt&amp;quot; value=&amp;quot;ground_alt+50&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
This directive is extremely powerful and has great potential for error - use with caution.&lt;br /&gt;
&lt;br /&gt;
=== Call ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;call&amp;lt;/tt&amp;gt; allows the user to define its own navigation procedures in C. The &amp;lt;tt&amp;gt;value&amp;lt;/tt&amp;gt; must be a call to a boolean function which must return TRUE as long as the stage is not completed (a function which should be called only once would then return immediately FALSE).&lt;br /&gt;
This feature is illustrated with the '''line''' pattern:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;call fun=&amp;quot;nav_line_setup()&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;call fun=&amp;quot;nav_line_run(WP_1, WP_2, nav_radius)&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
where &amp;lt;tt&amp;gt;nav_line_setup()&amp;lt;/tt&amp;gt; returns FALSE and &amp;lt;tt&amp;gt;nav_line_run()&amp;lt;/tt&amp;gt; always returns TRUE (this stage never ends). '''Note''' that a waypoints index is derived/denoted by prefixing the waypoint name with &amp;lt;tt&amp;gt;WP_&amp;lt;/tt&amp;gt;(i.e.: 1 --&amp;gt; WP_1, 2 --&amp;gt; WP_2)&lt;br /&gt;
&amp;lt;br /&amp;gt;&lt;br /&gt;
&lt;br /&gt;
To call ''any'' function exactly once regardless of the return value (e.g. call a void function), add &amp;lt;tt&amp;gt;loop=&amp;quot;FALSE&amp;quot;&amp;lt;/tt&amp;gt;&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;call fun=&amp;quot;viewvideo_take_shot(TRUE)&amp;quot; loop=&amp;quot;FALSE&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
or use the &amp;lt;tt&amp;gt;call_once&amp;lt;/tt&amp;gt; alias:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;call_once fun=&amp;quot;viewvideo_take_shot(TRUE)&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Such extra navigation functions are usually written as a [[Modules|Module]] and the header files are included automatically.&lt;br /&gt;
&lt;br /&gt;
If you want to call functions that are not part of a module, you need to include the header file which contains the function declaration:or supplementary C file which must be specified in the &lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;header&amp;gt;&lt;br /&gt;
#include &amp;quot;path/to/header.h&amp;quot;&lt;br /&gt;
  &amp;lt;/header&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
where the path is relative to the &amp;lt;tt&amp;gt;sw/airborne&amp;lt;/tt&amp;gt; directory.&lt;br /&gt;
&lt;br /&gt;
You can also call functions before or after each execution of the block (this means continuously on each iteration of each stage of the block, not just when entering o exiting the block).&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;block name=&amp;quot;circlehome&amp;quot; pre_call=&amp;quot;function_to_call_before_circle()&amp;quot; post_call=&amp;quot;function_to_call_after_circle()&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;circle wp=&amp;quot;HOME&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Pre Call ===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;block name=&amp;quot;Standby&amp;quot; strip_button=&amp;quot;Standby&amp;quot; strip_icon=&amp;quot;home.png&amp;quot; pre_call=&amp;quot;if(!InsideKill(GetPosX(), GetPosY())) NavKillThrottle();&amp;quot;&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Post Call ===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;block name=&amp;quot;traj&amp;quot; pre_call=&amp;quot;formation_pre_call()&amp;quot; post_call=&amp;quot;formation_flight()&amp;quot;&amp;gt; &amp;lt;!-- formation flight is call after all other navigation tasks --&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Procedures ==&lt;br /&gt;
&lt;br /&gt;
Procedures are libraries which can be included in flight plans. They are composed of waypoints, sectors and blocks. The header of a procedure may contain some parameters which are replaced by arguments when the procedure is included.&lt;br /&gt;
&lt;br /&gt;
Extract of the DTD: a procedure is a sequence of parameters, waypoints, ...:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;!ELEMENT procedure (param*,header?,waypoints?,sectors?,exceptions?,blocks?)&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
A &amp;lt;tt&amp;gt;param&amp;lt;/tt&amp;gt;eter is just a name. A parameter is optional if it is declared with a default value.&lt;br /&gt;
An example with a required and an optional parameter:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;param name=&amp;quot;alt&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;param name=&amp;quot;radius&amp;quot; default_value=&amp;quot;75&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Procedures are called with the &amp;lt;tt&amp;gt;include&amp;lt;/tt&amp;gt; element in a flight plan. A procedure cannot be included twice or by another procedure. A procedure call requires:&lt;br /&gt;
&lt;br /&gt;
* the name of the procedure file, the name given to this inclusion; &lt;br /&gt;
* values for the parameters;&lt;br /&gt;
* backlinks for block name exits of the procedure.&lt;br /&gt;
&lt;br /&gt;
For example:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;include name=&amp;quot;landing&amp;quot; procedure=&amp;quot;landing.xml&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Here is the corresponding procedure '''landing.xml''':&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
&amp;lt;!DOCTYPE procedure SYSTEM &amp;quot;flight_plan.dtd&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;procedure&amp;gt;&lt;br /&gt;
    &amp;lt;waypoints&amp;gt;&lt;br /&gt;
      &amp;lt;waypoint name=&amp;quot;AF&amp;quot; x=&amp;quot;177.4&amp;quot; y=&amp;quot;45.1&amp;quot; alt=&amp;quot;30&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;waypoint name=&amp;quot;TD&amp;quot; x=&amp;quot;28.8&amp;quot; y=&amp;quot;57.0&amp;quot; alt=&amp;quot;0&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;waypoint name=&amp;quot;_BASELEG&amp;quot; x=&amp;quot;168.8&amp;quot; y=&amp;quot;-13.8&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/waypoints&amp;gt;&lt;br /&gt;
    &amp;lt;blocks&amp;gt;&lt;br /&gt;
      ...&lt;br /&gt;
      &amp;lt;block name=&amp;quot;land&amp;quot;&amp;gt;&lt;br /&gt;
        &amp;lt;call fun=&amp;quot;nav_compute_baseleg(WP_AF, WP_TD, WP__BASELEG, nav_radius)&amp;quot;/&amp;gt;&lt;br /&gt;
        &amp;lt;circle radius=&amp;quot;nav_radius&amp;quot; until=&amp;quot;NavCircleCount() &amp;gt; 0.5&amp;quot; wp=&amp;quot;_BASELEG&amp;quot;/&amp;gt;&lt;br /&gt;
        &amp;lt;circle radius=&amp;quot;nav_radius&amp;quot; until=&amp;quot;And(NavQdrCloseTo(DegOfRad(baseleg_out_qdr)-10), 10 &amp;gt; fabs(GetPosAlt()- WaypointAlt(WP__BASELEG)))&amp;quot; wp=&amp;quot;_BASELEG&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;/block&amp;gt;&lt;br /&gt;
      ...&lt;br /&gt;
    &amp;lt;/blocks&amp;gt;&lt;br /&gt;
  &amp;lt;/procedure&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Note that the name of procedure '''land''' block will be renamed into '''landing.land''':&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;deroute block=&amp;quot;landing.land&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
will jump to this procedure block.&lt;br /&gt;
&lt;br /&gt;
Suppose you have a go-around condition in your landing procedure. You would write it&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;exception cond=&amp;quot;...&amp;quot; deroute=&amp;quot;go-around&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
then you must link this block exit with one of your block (e.g. &amp;lt;tt&amp;gt;Standby&amp;lt;/tt&amp;gt;). So you would include the procedure as follows:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;include name=&amp;quot;landing&amp;quot; procedure=&amp;quot;landing.xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;with from=&amp;quot;go-around&amp;quot; to=&amp;quot;Standby&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/include&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Internal Variables in Flight Plans ==&lt;br /&gt;
&lt;br /&gt;
The flight plan can use several internal variables, macros and functions coming from the rest of the system or the flight plan API itself. The following list present some of the most commonly used variables, but much more are actually available:&lt;br /&gt;
&lt;br /&gt;
* '''autopilot_flight_time''': time in seconds since autopilot was booted (integer)&lt;br /&gt;
* '''datalink_time''': time in seconds since last connection of telemetry to ground control station (including ''subsystems/datalink/datallink.h'' in the '''header''' section is required) (integer)&lt;br /&gt;
* '''GetPosAlt()''': returns the current altitude above ground level in meter (float)&lt;br /&gt;
* '''GetPosX()''': returns x (easting) of current position relative to reference in meter (float)&lt;br /&gt;
* '''GetPosY()''': returns y (northing) of current position relative to reference in meter (float)&lt;br /&gt;
* &amp;lt;s&amp;gt;'''ground_alt''': altitude above ground level in meter (float)&amp;lt;/s&amp;gt; (v5.8 and higher - use '''GetAltRef()''' instead)&lt;br /&gt;
* '''GetAltRef()''': returns reference altitude, usually ground_alt&lt;br /&gt;
* '''NavSetGroundReferenceHere()''': reset position and altitude reference point to current position&lt;br /&gt;
* '''NavSetAltitudeReferenceHere()''': reset altitude reference to current alt but keep previous horizontal position reference&lt;br /&gt;
* '''NavSetWaypointHere(_wp)''': set position of a waypoint given as argument to the current position&lt;br /&gt;
* '''WaypointX(_wp)''': returns x (easting) of waypoint position relative to reference in meter (float)&lt;br /&gt;
* '''WaypointY(_wp)''': returns y (northing) of waypoint position relative to reference in meter (float)&lt;br /&gt;
* '''WaypointAlt(_wp)''': returns waypoint altitude in meter (float)&lt;br /&gt;
* '''nav_radius''': free variable usually used to set circle radius in flight plan&lt;br /&gt;
* '''NavKillThrottle()''': function to switch off throttle&lt;br /&gt;
* '''PowerVoltage()''': returns current voltage of the battery&lt;br /&gt;
* all functions from the [http://docs.paparazziuav.org/latest/group__state__interface.html state interface API]&lt;br /&gt;
* all functions from the [http://docs.paparazziuav.org/latest/subsystems_2navigation_2waypoints_8h.html waypoint API]&lt;br /&gt;
* all variables declared in [[modules]] headers&lt;br /&gt;
&lt;br /&gt;
== Advanced Examples ==&lt;br /&gt;
&lt;br /&gt;
Parameters used in a flight plan can be computed expressions. In this example, the plane is asked to perform 5 circles at progressively increasing altitudes for exactly one minute at each altitude:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;for var=&amp;quot;i&amp;quot; from=&amp;quot;1&amp;quot; to=&amp;quot;5&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;circle wp=&amp;quot;HOME&amp;quot; radius=&amp;quot;75&amp;quot;&lt;br /&gt;
          alt=&amp;quot;ground_alt + 50*$i&amp;quot;&lt;br /&gt;
          until=&amp;quot;stage_time &amp;gt; 60&amp;quot; /&amp;gt;&lt;br /&gt;
  &amp;lt;/for&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Below you find some random examples of the posibilities. This is only the tip of the iceberg, use your imagination and go wild with new creative ideas for your flightplan&lt;br /&gt;
&lt;br /&gt;
=== Gains on the fly ===&lt;br /&gt;
&lt;br /&gt;
It is very well possible to set specific gain for an airframe if it reaches e.g a certain block.&lt;br /&gt;
&lt;br /&gt;
=== Dynacmically adjustable maximum speed ===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
&amp;lt;call_once fun=&amp;quot;gh_set_max_speed(2.0)&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Immobilize Actuators === &lt;br /&gt;
&lt;br /&gt;
h_ctl setpoints variable are set by the h_ctl_attitude_loop() (from fw_h_ctl.c) loop) which can be disabled with the h_ctl_disabled flag:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;set var=&amp;quot;h_ctl_disabled&amp;quot; value=&amp;quot;TRUE&amp;quot;/&amp;gt;&lt;br /&gt;
 &amp;lt;set var=&amp;quot;h_ctl_aileron_setpoint&amp;quot; value=&amp;quot;0&amp;quot;/&amp;gt;&lt;br /&gt;
 &amp;lt;set var=&amp;quot;h_ctl_elevator_setpoint&amp;quot; value=&amp;quot;MAX_PPRZ/2&amp;quot;/&amp;gt;&lt;br /&gt;
 .... waiting for a condition ...&lt;br /&gt;
 &amp;lt;set var=&amp;quot;h_ctl_disabled&amp;quot; value=&amp;quot;FALSE&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Tips and Tricks ==&lt;br /&gt;
&lt;br /&gt;
There are many ways to skin a cat just as there are many ways to craft your flight plan. Following the best practices tips can save you from a lot of frustration and mishap.&lt;br /&gt;
&lt;br /&gt;
* Simulate your flight plan before taking it to the sky. Flight plans should always be carefully tested prior to flight, take a look at the [[Simulation|simulation]] page for details on how to simulate your plan.&lt;br /&gt;
* Make an subdirectory in the Flight_plan directory with your own name and add your flight plans there. Make sure that the location of the DTD is correct, e.g by using relative directory double dots as in &amp;lt;tt&amp;gt;&amp;lt;!DOCTYPE flight_plan SYSTEM &amp;quot;../flight_plan.dtd&amp;quot;&amp;gt;&amp;lt;/tt&amp;gt;&lt;br /&gt;
&lt;br /&gt;
* Take a good look at other flight plans included with Paparazzi. To learn from example flight plans please visit the [[Flight_Plan_Examples|flight plan examples]] page&lt;br /&gt;
* There are several option to build failsafe features into you flightplan, [[Failsafe|for some examples visit the Failsafe page]].&lt;br /&gt;
* Some flight plan examples define waypoint locations using relative coordinates. These are relative positions from the fixed lat and lon in the header of the flight plan. When simulating your flight plan the aircraft always use the lat/lon as defined in the flight plan since a regular simulation has no notion of you current position of you local PC where you simulate on. This is something to keep in mind if you test your flight plan in real flights.&lt;br /&gt;
&lt;br /&gt;
=== V5.8+ ===&lt;br /&gt;
* If you don't like the '''No SRTM data found to check altitude''' warning, either in your flight plan editor or in GCS itself click on the '''Nav-&amp;gt;display SRTM'''. It will ask you whether you want to download SRTM data. Say yes, and it will save the data in ''data/srtm'' directory, so you don't get the warning any more and check the ground altitude even without GPS.&lt;br /&gt;
&lt;br /&gt;
[[Category:Software]] [[Category:User_Documentation]]&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=NPS&amp;diff=23650</id>
		<title>NPS</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=NPS&amp;diff=23650"/>
		<updated>2017-04-04T18:04:59Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: /* Running the Simulation */  Added a line linking about setting up environment variables before trying to run from terminal&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;categorytree style=&amp;quot;float:right; clear:right; margin-left:1ex; border: 1px solid gray; padding: 0.7ex;&amp;quot; mode=pages&amp;gt;Simulation&amp;lt;/categorytree&amp;gt;&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
== Introduction ==&lt;br /&gt;
&lt;br /&gt;
NPS ('''N'''ew '''P'''aparazzi '''S'''imulator) is a more advanced simulator with sensor models and can use different FDM backends. By default [[JSBSim]] is used as FDM (FlightDynamicModel) backend, this allow fairly complex airframes.&lt;br /&gt;
JSBSim can be replaced by the FDM of your choice, e.g. YASim or a interconnection with MATLAB simulink&lt;br /&gt;
&lt;br /&gt;
NPS is capable of simulating rotorcraft and fixedwing airframes, with the possibility to add more complex aircrafts/hybrids if a proper model is built using one of the FDM backends.&lt;br /&gt;
&lt;br /&gt;
== Usage ==&lt;br /&gt;
&lt;br /&gt;
See [[Installation|installation of Paparazzi]], [[JSBSim]] and optionally [[FlightGear]] (for visualization).&lt;br /&gt;
&lt;br /&gt;
=== Configuration/Build ===&lt;br /&gt;
Add the '''nps''' target to your [[Airframe_Configuration|airframe]] with the fdm you want to use:&lt;br /&gt;
{{Box Code|conf/airframes/myaircraft.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;firmware name=&amp;quot;rotorcraft or fixedwing&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;target name=&amp;quot;nps&amp;quot; board=&amp;quot;pc&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;subsystem name=&amp;quot;fdm&amp;quot;   type=&amp;quot;jsbsim&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/target&amp;gt;&lt;br /&gt;
    ...&lt;br /&gt;
  &amp;lt;/firmware&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
then depending on the aircraft you want to simulate add a NPS simulator section which defines the model, actuators and sensor parameters used:&lt;br /&gt;
&lt;br /&gt;
E.g for a simple quadrotor:&lt;br /&gt;
{{Box Code|conf/airframes/myaircraft.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;section name=&amp;quot;SIMULATOR&amp;quot; prefix=&amp;quot;NPS_&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;ACTUATOR_NAMES&amp;quot;  value=&amp;quot;front_motor, right_motor, back_motor, left_motor&amp;quot; type=&amp;quot;string[]&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;JSBSIM_MODEL&amp;quot; value=&amp;quot;simple_quad&amp;quot; type=&amp;quot;string&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;SENSORS_PARAMS&amp;quot; value=&amp;quot;nps_sensors_params_default.h&amp;quot; type=&amp;quot;string&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/section&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
You can also take a look at the example airframe [https://github.com/paparazzi/paparazzi/blob/master/conf/airframes/examples/quadrotor_lisa_m_2_pwm_spektrum.xml conf/airframes/examples/quadrotor_lisa_m_2_pwm_spektrum.xml] or use it for your first tests.&lt;br /&gt;
&lt;br /&gt;
E.g for a fixedwing like a Bixler,Easystar, etc:&lt;br /&gt;
{{Box Code|conf/airframes/myaircraft.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;section name=&amp;quot;SIMULATOR&amp;quot; prefix=&amp;quot;NPS_&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;JSBSIM_LAUNCHSPEED&amp;quot; value=&amp;quot;15&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;JSBSIM_MODEL&amp;quot; value=&amp;quot;easystar&amp;quot; type=&amp;quot;string&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;SENSORS_PARAMS&amp;quot; value=&amp;quot;nps_sensors_params_default.h&amp;quot; type=&amp;quot;string&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/section&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
* NPS_ACTUATOR_NAMES: mapping of the motors defined in the [[Rotorcraft_Configuration#Motor_Mixing|MOTOR_MIXING section]] to the actuators in the JSBSim model (the order is important, also make sure that your motors in JSBSim spin in the same direction as your real ones)&lt;br /&gt;
* NPS_SENSORS_PARAMS: the parameter file for the sensor simulation (noise/delay) under ''conf/simulator/nps/'' (e.g. [https://github.com/paparazzi/paparazzi/blob/master/conf/simulator/nps/nps_sensors_params_default.h nps_sensors_params_default.h])&lt;br /&gt;
* NPS_JSBSIM_MODEL: name of the JSBSim model in ''conf/simulator/jsbsim/aircraft/'' (e.g. [https://github.com/paparazzi/paparazzi/blob/master/conf/simulator/jsbsim/aircraft/simple_quad.xml simple_quad]), if not defined it defaults to AIRCRAFT_NAME&lt;br /&gt;
* NPS_JSBSIM_INIT: the xml file containing the initial conditions (location, attitude, wind) for JSBSim in ''conf/simulator/jsbsim/aircraft/'' (e.g. [https://github.com/paparazzi/paparazzi/blob/master/conf/simulator/jsbsim/aircraft/reset00.xml reset00])&amp;lt;br&amp;gt;This define is optional and if not specified the initial position of the aircraft will be set to the flight plan location. Prior to v5.1 this was called INITIAL_CONDITITONS.&lt;br /&gt;
* NPS_JSBSIM_LAUNCHSPEED: if defined this sets an initial launchspeed in m/s for fixedwings, available since v5.1.0_testing-54-g2ac094f&lt;br /&gt;
* NPS_JS_*: Joystick mappings, see [http://docs.paparazziuav.org/latest/nps__radio__control__joystick_8c.html]&lt;br /&gt;
Then build the nps target...&lt;br /&gt;
&lt;br /&gt;
== Running the Simulation ==&lt;br /&gt;
&lt;br /&gt;
The most convenient way to start the simulation is via the ''Simulation'' session from the [[Paparazzi Center]].&lt;br /&gt;
Just select e.g. the Quad_LisaM_2 example airframe and start the ''Simulation'' session with the simulator, GCS and server.&lt;br /&gt;
&lt;br /&gt;
If you have added PAPARAZZI_HOME AND PAPARAZZI_SRC to the environmental variables of your terminal (See [[Installation#Environment_Variables|Setting up environment variables]]), you can also start it via the generic simulation launcher:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;bash&amp;quot;&amp;gt;sw/simulator/pprzsim-launch --aircraft Quad_LisaM_2 --type nps&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div class=&amp;quot;toccolours mw-collapsible mw-collapsed&amp;quot;&amp;gt;&lt;br /&gt;
Prior to '''v5.0''' pprzsim-launch was not available. Click expand to see the details.&lt;br /&gt;
&amp;lt;div class=&amp;quot;mw-collapsible-content&amp;quot;&amp;gt;&lt;br /&gt;
In earlier versions, start your tools (e.g. [[GCS]], [[server]] and messages) separately, then launch the nps simulator for your aircraft directly:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;bash&amp;quot;&amp;gt;./var/Quad_LisaM_2/nps/simsitl&amp;lt;/source&amp;gt;&lt;br /&gt;
&amp;lt;/div&amp;gt;&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Options ===&lt;br /&gt;
Start the simulator with the ''--help'' option to list them all.&lt;br /&gt;
&lt;br /&gt;
* ''--ivy_bus'': Set ivy bus broadcast address to use (default 127.255.255.255, 224.255.255.255 on OSX)&lt;br /&gt;
* ''--rc_script'': Execute script with specified number to emulate RC input.&lt;br /&gt;
* ''--js_dev'': Use joystick for radio control (specify index, normally 0), also see [[NPS#Use_a_Joystick]].&lt;br /&gt;
* ''--spektrum_dev'': Spektrum device to use for radio control (e.g. /dev/ttyUSB0)&lt;br /&gt;
* ''--fg_host'': Host for FlightGear visualization (e.g. 127.0.0.1)&lt;br /&gt;
* ''--fg_port'': Port on FlightGear host to connect to (Default: 5501)&lt;br /&gt;
* ''--fg_time_offset'': FlightGear time offset in seconds (e.g. 21600 for 6h), this is useful if it is currently night at the location you are flying and you want to add an offset to fly in daylight. (Since ''v4.9_devel_413-g9d55d6f)&lt;br /&gt;
&lt;br /&gt;
=== Typical Simulation ===&lt;br /&gt;
In general you go through the same steps as with the real aircraft:&lt;br /&gt;
* It should start on the ground and you have to wait a few seconds until the AHRS is aligned.&lt;br /&gt;
* If you have a (simulated) RC, you can now arm the motors and fly around in manual.&lt;br /&gt;
* To fly autonomously, make sure your ''AUTO2'' mode is ''NAV'', you can change it in the GCS-&amp;gt;settings-&amp;gt;system-&amp;gt;auto2.&lt;br /&gt;
** Switch to it if you are using an RC, otherwise you should already be in this mode.&lt;br /&gt;
** Arm your motors: either via the resurrect button or by going to the ''Start Motors'' block of the [[Flight Plans|Flight Plan]].&lt;br /&gt;
** Takeoff: via the takeoff button or the corresponding flight plan block.&lt;br /&gt;
* Do your stuff... :-)&lt;br /&gt;
&lt;br /&gt;
=== Pausing or running the sim at a different speed ===&lt;br /&gt;
If you start the simulation from a terminal, hit ''CTRL-z'' to pause it. You can then enter a different time factor (default 1.0) to make the simulation run slower or faster than real-time. Hit enter to resume the simulation or ''CTRL-z'' again to suspend it like any normal Unix process (use the ''fg'' (foreground) command to un-suspend it again).&lt;br /&gt;
&lt;br /&gt;
This simulation speed parameter ?can be edited? in a configuration file : FIXME&lt;br /&gt;
&lt;br /&gt;
=== Use a Joystick ===&lt;br /&gt;
You can use a [[joystick]] (or connect your RC transmitter as a joystick) to control the quad in the simulator.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;bash&amp;quot;&amp;gt;sw/simulator/pprzsim-launch --aircraft Quad_LisaM_2 --type nps --js_dev 0&amp;lt;/source&amp;gt;&lt;br /&gt;
or directly calling the nps simsitl binary:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;bash&amp;quot;&amp;gt;./var/Quad_LisaM_2/nps/simsitl --js_dev 0&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Joystick support uses the Simple DirectMedia Layer (SDL) library. Rather than specifying an input device name as one normally does on Linux, you just supply an index value (0, 1, 2,...) of the device you wish to use. Typically, the order of devices is the order in which you plugged them into your computer. The sim will display the name of the device being used to double check. If the &amp;lt;tt&amp;gt;-j&amp;lt;/tt&amp;gt; option is used with no argument, the sim defaults to using device on index 0 (which is usually correct if you have only one joystick attached).&lt;br /&gt;
&lt;br /&gt;
Also see [[Joystick#Calibration]].&lt;br /&gt;
&lt;br /&gt;
=== Visualization in [[FlightGear]] ===&lt;br /&gt;
[[FlightGear#Installation|Install]] and [[FlightGear#Using_FlightGear_for_Visualization|start flightgear]], e.g. with a quadrotor model:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;bash&amp;quot;&amp;gt;fgfs --fdm=null --native-gui=socket,in,30,,5501,udp --prop:/sim/model/path=Models/Aircraft/paparazzi/mikrokopter.xml&amp;lt;/source&amp;gt;&lt;br /&gt;
restart your simulator with the ''--fg_host'' option:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;bash&amp;quot;&amp;gt;sw/simulator/pprzsim-launch --aircraft Quad_LisaM_2 --type nps --fg_host 127.0.0.1&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Troubleshooting ===&lt;br /&gt;
* If you get an error like &amp;quot;JSBSim failed to open the configuration file: (null)/conf/simulator/jsbsim/aircraft/BOOZ2_A1.xml&amp;quot;, you need to set your $PAPARAZZI_SRC and $PAPARAZZI_HOME environment variables. Add the following to your .bashrc, change paths according to where you put Paparazzi. Open a new terminal and launch the sim again.&lt;br /&gt;
 export PAPARAZZI_SRC=~/paparazzi&lt;br /&gt;
 export PAPARAZZI_HOME=~/paparazzi&lt;br /&gt;
&lt;br /&gt;
* If you did not install the jsbsim package your JSBSim installation under /opt/jsbsim will be used and you will have to set your library path (either in your shell startup file or when running the sim on the command line), e.g.:&lt;br /&gt;
 LD_LIBRARY_PATH=/opt/jsbsim/lib ./var/Quad_LisaM_2/nps/simsitl --fg_host 127.0.0.1&lt;br /&gt;
&lt;br /&gt;
* If you get an error like &amp;quot;fatal error: gsl/gsl_rng.h: No such file or directory&amp;quot;, you need to install the GNU Scientific Library and corresponding development packages (libgsl).&lt;br /&gt;
&lt;br /&gt;
* If you get an error like &amp;quot;undefined reference to `pcre_compile'&amp;quot;, edit file conf/Makefile.nps, look for the line that begins with LDFLAGS and add -lpcre, e.g.:&lt;br /&gt;
 LDFLAGS += $($(TARGET).LDFLAGS) -lpcre&lt;br /&gt;
&lt;br /&gt;
==== Simulating Multiple Aircraft ====&lt;br /&gt;
When simulating multiple aircraft, the ''-udp_broadcast'' argument needs to be specified as part of the datalink invocation:&lt;br /&gt;
 $PAPARAZZI_HOME/sw/ground_segment/tmtc/link -udp -udp_broadcast&lt;br /&gt;
&lt;br /&gt;
In the case of Mac OS X, the IP ADDR must also be specified:&lt;br /&gt;
 $PAPARAZZI_HOME/sw/ground_segment/tmtc/link -udp -udp_broadcast -udp_broadcast_addr &amp;lt;your_network_broadcast_ip_addr&amp;gt;&lt;br /&gt;
&lt;br /&gt;
You can determine the IP ADDR for your network using '''ifconfig''' command:&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
$ ifconfig&lt;br /&gt;
 ...&lt;br /&gt;
en0: flags=8863&amp;lt;UP,BROADCAST,SMART,RUNNING,SIMPLEX,MULTICAST&amp;gt; mtu 1500&lt;br /&gt;
	ether 60:03:08:8e:14:9e &lt;br /&gt;
	inet6 fe80::6203:8ff:fe8e:149e%en0 prefixlen 64 scopeid 0x4 &lt;br /&gt;
	inet 192.168.1.59 netmask 0xffffff00 broadcast 192.168.1.255&lt;br /&gt;
	nd6 options=1&amp;lt;PERFORMNUD&amp;gt;&lt;br /&gt;
	media: autoselect&lt;br /&gt;
	status: active&lt;br /&gt;
 ...&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Based on the above sample output, the invocation would look like the following:&lt;br /&gt;
 $PAPARAZZI_HOME/sw/ground_segment/tmtc/link -udp -udp_broadcast -udp_broadcast_addr 192.168.1.255&lt;br /&gt;
&lt;br /&gt;
== Usage Examples ==&lt;br /&gt;
&lt;br /&gt;
=== Plot the value of a message field ===&lt;br /&gt;
Start the [[RTPlotter|real-time plotter]] tool menu of [[Paparazzi Center]] or with&lt;br /&gt;
&amp;lt;source lang=&amp;quot;bash&amp;quot;&amp;gt;./sw/logalizer/plotter&amp;lt;/source&amp;gt;&lt;br /&gt;
for example drag the label 'int32 phi' from the ROTORCRAFT_FP message to the drawing area of the plotter&lt;br /&gt;
&lt;br /&gt;
* Use the datalink to change the telemetry mode&lt;br /&gt;
start 'settings' ( from the tool menu of paparazzi center) or with&lt;br /&gt;
  ./sw/ground_segment/tmtc/settings -ac Quad_LisaM_2&lt;br /&gt;
start 'server' to dispatch datalink messages ( from the tool menu of paparazzi center) or with&lt;br /&gt;
 ./sw/ground_segment/tmtc/server &lt;br /&gt;
change the field &amp;quot;telemetry&amp;quot; on the first page to &amp;quot;Att loop&amp;quot; and send by pressing the green check button. The label on the left or the drop box should change to &amp;quot;Att loop&amp;quot; confirming your message has been received. &amp;quot;message&amp;quot; should now show that the message &amp;quot;STAB_ATTITUDE_INT&amp;quot; is received&lt;br /&gt;
&lt;br /&gt;
=== Tuning the attitude control loop ===&lt;br /&gt;
Here we are going to use the simulator to demonstrate a way of tuning the attitude control loop for a multicopter (rotorcraft firmware only).&lt;br /&gt;
&lt;br /&gt;
* Restart your previous session&lt;br /&gt;
* Set telemetry mode to &amp;quot;attitude_loop&amp;quot;&lt;br /&gt;
* Display two real time plotter windows&lt;br /&gt;
&lt;br /&gt;
In the first one, plot the field &amp;quot;m_phi&amp;quot; from the &amp;quot;STAB_ATTITUDE_int&amp;quot; message. This is our estimation of roll angle.&lt;br /&gt;
On top of that, plot the field &amp;quot;phi&amp;quot; from the &amp;quot;STAB_ATTITUDE_REF_INT&amp;quot; message. This is our reference roll angle, that is, the roll value we are trying to achieve.&lt;br /&gt;
&lt;br /&gt;
In the second plotter, plot the fields &amp;quot;delta_a_fb&amp;quot; and &amp;quot;delta_a_ff&amp;quot;. Those are respectively the feedback and feedforward part of our roll command. The sum of those two terms is what is used as roll command.The feedforward part is the part used to follow our trajectory and the feedback part is the part used to reject perturbations.&lt;br /&gt;
&lt;br /&gt;
* In &amp;quot;Settings&amp;quot;, go to the &amp;quot;Att Loop&amp;quot; tab&lt;br /&gt;
We notice that the vehicle doesn't follow the step trajectory we are trying to make him do accurately.&lt;br /&gt;
 &lt;br /&gt;
Start by setting the value of the proportional gain ('pgain_phi') to 1000 instead of 400. The vehicle now follows the trajectory faster but overshoots. To prevent that, increase the value of the derivative gain ('dgain p') from 300 to 700.&lt;br /&gt;
&lt;br /&gt;
If you look at the plotter where you're plotting the commands, you'll notice that during steps, the feedback command has to work hard. This means that our feedforward command is badly tuned, and namely not working hard enough. Increase the value of the feedforward gain ('ddgain p') from 300 to 540. You'll notice that now the feedback command has become marginal during the steps. This is the right value for the gain. Anything bigger will make the feedback command fight against the feedforward command during steps, anything smaller will make the feedback command have to complement the feedforward command.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[Category:Simulation]] [[Category:Software]] [[Category:User_Documentation]]&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=GCS_Configuration&amp;diff=23645</id>
		<title>GCS Configuration</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=GCS_Configuration&amp;diff=23645"/>
		<updated>2017-03-31T18:25:35Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: /* Video plugin */  Made some grammatical changes near the ending. changed the last line to direct people to the discussion if all else fails&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&amp;lt;categorytree style=&amp;quot;float:right; clear:right; margin-left:1ex; border: 1px solid gray; padding: 0.7ex;&amp;quot; mode=pages&amp;gt;GCS&amp;lt;/categorytree&amp;gt;&lt;br /&gt;
__TOC__&lt;br /&gt;
&lt;br /&gt;
== Paparazzi Center ==&lt;br /&gt;
The paparazzi center is launched with the following command:&lt;br /&gt;
 &amp;lt;tt&amp;gt;./sw/supervision/paparazzicenter&amp;lt;/tt&amp;gt;&lt;br /&gt;
and is used to launch individual portions of the GCS (''Programs'') or the entire GCS (''Sessions'') with the modem and map settings defined in &amp;lt;tt&amp;gt;&amp;lt;b&amp;gt;/conf/control_panel.xml&amp;lt;/b&amp;gt;&amp;lt;/tt&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Configuration Options===&lt;br /&gt;
&lt;br /&gt;
Here all the commandline parameter to set specific option(s) while launching the GCS. To use these edit the file conf/control_panel.xml in the line that says &amp;lt;program name=&amp;quot;GCS&amp;quot; command=&amp;quot;sw/ground_segment/cockpit/gcs&amp;quot;&amp;gt; add the options, for example:  &amp;lt;br&amp;gt;&lt;br /&gt;
&amp;lt;program name=&amp;quot;GCS&amp;quot; command=&amp;quot;sw/ground_segment/cockpit/gcs -fullscreen&amp;quot;&amp;gt;&amp;lt;br&amp;gt;&lt;br /&gt;
&lt;br /&gt;
 '''-auto_ortho''', IGN tiles path&lt;br /&gt;
 '''-b''', &amp;lt;ivy bus&amp;gt; Default is 127.255.255.255:2010&lt;br /&gt;
 '''-center''', Initial map center (e.g. 'WGS84 43.605 1.443')&lt;br /&gt;
 '''-center_ac''', Centers the map on any new A/C&lt;br /&gt;
 '''-edit''', Flight plan editor&lt;br /&gt;
 '''-fullscreen''', Fullscreen window&lt;br /&gt;
 '''-maps_fill''', Automatically start loading background maps&lt;br /&gt;
 '''-maps_zoom''', Background maps zoomlevel (default: 18, max: 22)&lt;br /&gt;
 '''-ign''', IGN tiles path&lt;br /&gt;
 '''-lambertIIe''', Switch to LambertIIe projection&lt;br /&gt;
 '''-layout''', &amp;lt;XML layout specification&amp;gt; GUI layout. Default: horizontal.xml&lt;br /&gt;
 '''-m''', Map XML description file&lt;br /&gt;
 '''-maximize''', Maximize window&lt;br /&gt;
 '''-mercator''', Switch to (Google Maps) Mercator projection, default&lt;br /&gt;
 '''-mplayer''', Launch mplayer with the given argument as X plugin&lt;br /&gt;
 '''-no_alarm''', Disables alarm page&lt;br /&gt;
 '''-no_confirm_kill''', Disable the additional kill conformation dialog&lt;br /&gt;
 '''-maps_no_http''', Switch off downloading of maps, always use cached maps&lt;br /&gt;
 '''-ortho''', IGN tiles path&lt;br /&gt;
 '''-osm''', Use OpenStreetMap database (default is Google)&lt;br /&gt;
 '''-ms''', Use Microsoft maps database (default is Google)&lt;br /&gt;
 '''-particules''', Display particules&lt;br /&gt;
 '''-plugin''', External X application (launched with the id of the plugin window as argument)&lt;br /&gt;
 '''-ref ''',Geographic ref (e.g. 'WGS84 43.605 1.443')&lt;br /&gt;
 '''-speech''', Enable vocal messages&lt;br /&gt;
 '''-srtm''', Enable SRTM elevation display&lt;br /&gt;
 '''-track_size''', Default track length (500)&lt;br /&gt;
 '''-utm''', Switch to UTM local projection&lt;br /&gt;
 '''-wid''', &amp;lt;window id&amp;gt; Id of an existing window to be attached to&lt;br /&gt;
 '''-zoom''', Initial zoom&lt;br /&gt;
 '''-auto_hide_fp''', Automatically hide flight plans of unselected aircraft&lt;br /&gt;
 '''-help''', Display a list of options&lt;br /&gt;
&lt;br /&gt;
=== Video plugin ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;-mplayer&amp;lt;/tt&amp;gt; option of GCS allows to the user to display a video stream in a window of the GCS.  The video window can also be exchanged with the map by clicking anywhere inside the frame.&lt;br /&gt;
Use the following line in your &amp;lt;tt&amp;gt;/conf/control_panel.xml&amp;lt;/tt&amp;gt; to enable the video window.&lt;br /&gt;
 &amp;lt;tt&amp;gt;path_to_ground_segment/cockpit/gcs -mplayer rtsp://localhost:7070/video&amp;lt;/tt&amp;gt;&lt;br /&gt;
A useful example follows:&lt;br /&gt;
If you have an Avermedia DVB-T usb tuner like the Aver-Tv Hybrid Volar HX (Avermedia finally released Ubuntu Linux drivers)&lt;br /&gt;
then in order to use the usb tuner as video input to the GCS you have to complete the following steps:&lt;br /&gt;
&lt;br /&gt;
First download and install the drivers and check that the Usb tuner works well by opening a console window&lt;br /&gt;
and typing: &lt;br /&gt;
&lt;br /&gt;
'''mplayer tv:// -tv driver=v4l2:width=320:height=240:norm=NTSC:input=1:device=/dev/video1:noaudio'''&lt;br /&gt;
&lt;br /&gt;
Of course you must connect a video signal to the composite input first.&lt;br /&gt;
Then close the console and remove the Usb tuner.&lt;br /&gt;
Now it is time to configure the control_panel.xml file by editing the GCS command line.&lt;br /&gt;
Locate the line in the &amp;quot;control_panel.xml&amp;quot; usually located in /Your Paparazzi directory/conf/ (mine is in &amp;quot;/paparazzi/conf/&amp;quot;)&lt;br /&gt;
that looks similar to the below line:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
&amp;lt;program name=&amp;quot;GCS&amp;quot; command=&amp;quot;sw/ground_segment/cockpit/gcs -layout horizontal.xml&amp;quot;&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Then edit it so it looks like this:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
&amp;lt;program name=&amp;quot;GCS&amp;quot; command=&amp;quot;sw/ground_segment/cockpit/gcs -layout horizontal.xml -mplayer 'tv:// -tv driver=v4l2:width=320:height=240:norm=NTSC:input=1:device=/dev/video1:alsa:adevice=hw.2,0:amode=1:audiorate=48000:forceaudio:volume=100:immediatemode=0'&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;arg flag=&amp;quot;-b&amp;quot; variable=&amp;quot;ivy_bus&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/program&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The above line is one complete and uninterrupted line but it is just too long to show it in one line here.&lt;br /&gt;
(There is a space after the&amp;quot;-tv&amp;quot; like this &amp;quot;-mplayer 'tv:// -tv driver=v4l2:....&amp;quot; but nowhere else after that).&lt;br /&gt;
This will load the mplayer, select the composite video input of the tuner and enable the sound input.&lt;br /&gt;
Please remember to change the &amp;quot;NTSC&amp;quot; with &amp;quot;PAL&amp;quot; if you do not use the NTSC video system (if your airborne camera is PAL for example). &lt;br /&gt;
Read the mplayer documentation so you can tweak the resolution etc. later to suit your particular setup.&lt;br /&gt;
The resolution above is set to 320x240 here but you can set it to 640x480 by replacing the numbers in the command line above.&lt;br /&gt;
If You forget to set the arg parameter, then GCS will not meet through window handlers with mplayer and the video will not appear! This time you see an mplayer &amp;lt;defunct&amp;gt; on the process list.&lt;br /&gt;
&lt;br /&gt;
Finally you have to add the plugin widget to your GCS layout configuration file.&lt;br /&gt;
If you noticed the GCS command line in the &amp;quot;control_panel.xml&amp;quot; file, a part of it reads &amp;quot;-layout horizontal.xml&amp;quot; &lt;br /&gt;
so our configuration file is the &amp;quot;horizontal.xml&amp;quot; which is located always in &amp;quot;/Your Paparazzi directory/conf/gcs/&amp;quot;.&lt;br /&gt;
Open the file and add or uncomment the line below (in &amp;quot;horizontal.xml&amp;quot; the plugin widget is there but commented out):&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
&amp;lt;widget NAME=&amp;quot;plugin&amp;quot; SIZE=&amp;quot;300&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Now the file should look like this:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;rows&amp;gt;&lt;br /&gt;
  &amp;lt;widget size=&amp;quot;500&amp;quot; name=&amp;quot;map2d&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;columns&amp;gt;&lt;br /&gt;
   &amp;lt;rows size=&amp;quot;375&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;widget size=&amp;quot;200&amp;quot; name=&amp;quot;strips&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;/rows&amp;gt;&lt;br /&gt;
   &amp;lt;widget size=&amp;quot;400&amp;quot; name=&amp;quot;aircraft&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;widget name=&amp;quot;alarms&amp;quot;/&amp;gt;  &lt;br /&gt;
   &amp;lt;widget NAME=&amp;quot;plugin&amp;quot; SIZE=&amp;quot;300&amp;quot;/&amp;gt; &lt;br /&gt;
  &amp;lt;/columns&amp;gt;&lt;br /&gt;
 &amp;lt;/rows&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
All the above works fine in Ubuntu 10.04 LTS. It should work fine on different versions of Ubuntu too. If it does not, look for solution in other wiki pages and the PaparazziUAV documentations. If all else fails discuss your issue in the [https://gitter.im/paparazzi/discuss PaparazziUAV Gitter discussion].&lt;br /&gt;
&lt;br /&gt;
== Layout ==&lt;br /&gt;
The layout of the different components (map, strips, ...) of the gcs is configurable through a ''style'' XML file located in &amp;lt;tt&amp;gt;conf/gcs/&amp;lt;/tt&amp;gt;. The specification is done via a combination of rows and columns. The default layout is given in the &amp;lt;tt&amp;gt;horizontal.xml&amp;lt;/tt&amp;gt; file:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt; &lt;br /&gt;
 &amp;lt;!DOCTYPE layout SYSTEM &amp;quot;layout.dtd&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;layout width=&amp;quot;1024&amp;quot; height=&amp;quot;768&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;rows&amp;gt;&lt;br /&gt;
  &amp;lt;widget size=&amp;quot;500&amp;quot; name=&amp;quot;map2d&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;columns&amp;gt;&lt;br /&gt;
   &amp;lt;rows size=&amp;quot;350&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;widget size=&amp;quot;120&amp;quot; name=&amp;quot;strips&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;widget name=&amp;quot;alarms&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;/rows&amp;gt;&lt;br /&gt;
   &amp;lt;widget size=&amp;quot;400&amp;quot; name=&amp;quot;aircraft&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;widget size=&amp;quot;00&amp;quot; name=&amp;quot;plugin&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/columns&amp;gt;&lt;br /&gt;
 &amp;lt;/rows&amp;gt;&lt;br /&gt;
 &amp;lt;/layout&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Default size ('''1024x768''') of the whole window is specified in the root of the tree. The window is then divided in two rows: &lt;br /&gt;
* the &amp;lt;tt&amp;gt;map2d&amp;lt;/tt&amp;gt; with a requested height of '''500'''&lt;br /&gt;
* a set of columns containing&lt;br /&gt;
** a set of rows of width '''350''' divided into&lt;br /&gt;
**: the '''strips''' frame of height '''120'''&lt;br /&gt;
**: the '''alarms''' frame&lt;br /&gt;
** the notebook frame ('''aircraft''') of width '''400'''&lt;br /&gt;
** the video plugin frame&lt;br /&gt;
&lt;br /&gt;
This second example (&amp;lt;tt&amp;gt;left_col.xml&amp;lt;/tt&amp;gt;) sets the map and the notebook on the right and the other frames in a left column:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt; &lt;br /&gt;
 &amp;lt;!DOCTYPE layout SYSTEM &amp;quot;layout.dtd&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;layout width=&amp;quot;1024&amp;quot; height=&amp;quot;768&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;columns&amp;gt;&lt;br /&gt;
   &amp;lt;rows size=&amp;quot;360&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;widget size=&amp;quot;120&amp;quot; name=&amp;quot;strips&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;widget size=&amp;quot;300&amp;quot; name=&amp;quot;plugin&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;widget name=&amp;quot;alarms&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;/rows&amp;gt;&lt;br /&gt;
   &amp;lt;rows&amp;gt;&lt;br /&gt;
     &amp;lt;widget name=&amp;quot;map2d&amp;quot;/&amp;gt;&lt;br /&gt;
     &amp;lt;widget name=&amp;quot;aircraft&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;/rows&amp;gt;&lt;br /&gt;
 &amp;lt;/columns&amp;gt;&lt;br /&gt;
 &amp;lt;/layout&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
This layout file is chosen with the &amp;lt;tt&amp;gt;-layout&amp;lt;/tt&amp;gt; option:&lt;br /&gt;
 &amp;lt;tt&amp;gt;path_to_ground_segment/cockpit/gcs -layout left_col.xml&amp;lt;/tt&amp;gt;&lt;br /&gt;
&lt;br /&gt;
[[Category:GCS]] [[Category:User_Documentation]]&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Flight_Plans&amp;diff=23642</id>
		<title>Flight Plans</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Flight_Plans&amp;diff=23642"/>
		<updated>2017-03-29T19:37:18Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: /* Loops */  fixed some typos and grammar at the last bit&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;A '''flight plan''' is a XML document which one can create and store aboard an autopilot. The flight plan will describe how you want your aircraft to travel if released into into the wild blue yonder.&lt;br /&gt;
&lt;br /&gt;
== DTD and Structure ==&lt;br /&gt;
&lt;br /&gt;
The formal description of the flight plan file is given in the [http://en.wikipedia.org/wiki/Document_Type_Definition '''DTD'''] (located in &amp;lt;tt&amp;gt;conf/flight_plans/flight_plan.dtd&amp;lt;/tt&amp;gt;). This&lt;br /&gt;
DTD must be referenced in the header of your flight plan XML document using the following line:&amp;lt;br&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;!DOCTYPE flight_plan SYSTEM &amp;quot;flight_plan.dtd&amp;quot;&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The flight plans are stored in the &amp;lt;tt&amp;gt;conf/flight_plans&amp;lt;/tt&amp;gt; directory. The [[Flight_Plan_Editor|flight plan editor]] can be used to create basic flight plans via the GUI.&lt;br /&gt;
&lt;br /&gt;
Extract from the [http://en.wikipedia.org/wiki/Document_Type_Definition DTD]:&lt;br /&gt;
 &amp;lt;tt&amp;gt;&amp;lt;!ELEMENT flight_plan (header?,waypoints,sectors?,variables?,includes?,exceptions?,blocks)&amp;gt;&amp;lt;/tt&amp;gt;&lt;br /&gt;
&lt;br /&gt;
'''A flight plan is composed of two mandatory elements: [[#waypoints|waypoints]] and [[#blocks|blocks]]'''&lt;br /&gt;
&lt;br /&gt;
The root &amp;lt;tt&amp;gt;flight_plan&amp;lt;/tt&amp;gt; element is specified with several attributes:&lt;br /&gt;
 &amp;lt;tt&amp;gt;'''&amp;lt;flight_plan name lat0 lon0 ground_alt security_height home_mode_height qfu alt max_dist_from_home&amp;gt;'''&amp;lt;/tt&amp;gt;&lt;br /&gt;
; &amp;lt;tt&amp;gt;'''name'''&amp;lt;/tt&amp;gt;: The name of the mission (a text string)&lt;br /&gt;
; &amp;lt;tt&amp;gt;'''lat0, lon0'''&amp;lt;/tt&amp;gt;: Defines the latitude and longitude coordinates of the reference point {0,0} in WGS84 degree coordinates&lt;br /&gt;
; &amp;lt;tt&amp;gt;'''ground_alt'''&amp;lt;/tt&amp;gt;: The ground altitude (in meters), Above Sea Level where you are flying. It defines the &amp;lt;tt&amp;gt;GROUND_ALT&amp;lt;/tt&amp;gt; constant value which can be used in combination with a waypoint &amp;lt;height&amp;gt; parameter to define a waypoint height&lt;br /&gt;
; &amp;lt;tt&amp;gt;'''security_height'''&amp;lt;/tt&amp;gt;:  The height (over &amp;lt;tt&amp;gt;'''ground_alt'''&amp;lt;/tt&amp;gt;) used by the circle-home failsafe procedure and in other flight procedures such as formation flight and anti-collision avoidance. Warnings are produced if you place a waypoint lower than &amp;lt;tt&amp;gt;'''security_height'''&amp;lt;/tt&amp;gt; (usually the case for the landing point)&lt;br /&gt;
; &amp;lt;tt&amp;gt;'''home_mode_height'''&amp;lt;/tt&amp;gt; (optional): This optional attribute available since v4.2 allows to override &amp;lt;tt&amp;gt;'''security_height'''&amp;lt;/tt&amp;gt; as failsafe height in home mode. If &amp;lt;tt&amp;gt;'''home_mode_height'''&amp;lt;/tt&amp;gt; Is set lower than &amp;lt;tt&amp;gt;'''security_height'''&amp;lt;/tt&amp;gt;, the later is used. This attribute is useful if you need to return home at a high altitude rather than a low altitude.&lt;br /&gt;
; &amp;lt;tt&amp;gt;'''qfu'''&amp;lt;/tt&amp;gt; (optional): defines the global constant &amp;lt;tt&amp;gt;QFU&amp;lt;/tt&amp;gt;. It usually is the magnetic heading in degrees (north=0, east=90) of the runway, the opposite of wind direction. This constant may be used in the mission description. It is also used by the simulator as the original course of the aircraft. So if you want to take off and climb to the West you would use qfu=270. &lt;br /&gt;
; &amp;lt;tt&amp;gt;'''alt'''&amp;lt;/tt&amp;gt;: The default altitude of waypoints ([[Altitude_definitions|Above Sea Level]]). So if your ground altitude is 400 then alt needs to be a value greater than ground altitude and above any obstructions in the flight plan. &lt;br /&gt;
; &amp;lt;tt&amp;gt;'''max_dist_from_home'''&amp;lt;/tt&amp;gt;: A radius representing the maximum allowed distance (in meters) from the HOME waypoint. Exceeding this value (ie flying outside the circle with this radius) will trigger an exception. It is up to you to define the block to be executed (ie what to do) for the exception.&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
''Here is an '''example''' of such a line in the top of a flight plan:''&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;flight_plan alt=&amp;quot;250&amp;quot; ground_alt=&amp;quot;185&amp;quot; lat0=&amp;quot;43.46223&amp;quot; lon0=&amp;quot;1.27289&amp;quot; name=&amp;quot;Example Muret&amp;quot; max_dist_from_home=&amp;quot;300&amp;quot; qfu=&amp;quot;270&amp;quot; security_height=&amp;quot;25&amp;quot; &amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Note that a flight plan could also contain optional &amp;lt;tt&amp;gt;include&amp;lt;/tt&amp;gt;'s and &amp;lt;tt&amp;gt;exceptions&amp;lt;/tt&amp;gt; cases.&lt;br /&gt;
&lt;br /&gt;
In English the above flight plan says the name is Example Muret. The reference coordinates for the 0,0 point is: 43.46223 (lat) and 1.27289 (long). The flying site 0,0 location is 185m above sea level. The security height is 25m above 0,0 point or 210m above sea level. The default (ie if not defined in a waypoint this alt is used) altitude is 250m (above sea level). The home mode block altitude is defined to be 150m above sea level. Also, for security, a circle is defined with a radius that's 300m from 0,0 position. This is the max_dist_from_home value. Fly 301m from 0,0 and an exception is triggered. A useful block is to trigger/go to the home mode block and return to home when the aircraft flies outside the safety circle. Example flight plans are helpful for study before you build your own from scratch.&lt;br /&gt;
&lt;br /&gt;
== Waypoints ==&lt;br /&gt;
&lt;br /&gt;
The waypoints are the geographic locations used to specify the trajectories. A waypoint is specified by it's name and coordinates:&lt;br /&gt;
 &amp;lt;tt&amp;gt;''' &amp;lt;waypoint name wpx wpy [alt] [height]/&amp;gt; '''&amp;lt;/tt&amp;gt;&lt;br /&gt;
where wpx and wpy are real positional coordinates ( &amp;lt;tt&amp;gt;'''lat/lon'''&amp;lt;/tt&amp;gt; )  '''or''' UTM coordinates ( &amp;lt;tt&amp;gt;'''utm_x0/utm_y0'''&amp;lt;/tt&amp;gt; ) '''or''' relative coordinates ( &amp;lt;tt&amp;gt;'''x/y'''&amp;lt;/tt&amp;gt; ) in meters from your reference point {0,0} .  &amp;lt;tt&amp;gt;alt&amp;lt;/tt&amp;gt; is an optional parameter and can be used to assign an altitude to a particular waypoint that is different from the globally defined &amp;lt;tt&amp;gt;alt&amp;lt;/tt&amp;gt; parameter of the flightplan. The &amp;lt;tt&amp;gt;height&amp;lt;/tt&amp;gt; attribute can be used to set the waypoint height relative to the [[Altitude_definitions|ground altitude]] (&amp;lt;tt&amp;gt;ground_alt&amp;lt;/tt&amp;gt;) of the flight plan for this waypoint.&lt;br /&gt;
&lt;br /&gt;
An example:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;waypoints&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;HOME&amp;quot; x=&amp;quot;0.0&amp;quot; y=&amp;quot;30.0&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;BRIDGEOVERRIVER&amp;quot; x=&amp;quot;-100.0&amp;quot; y=&amp;quot;60.0&amp;quot; alt=&amp;quot;270.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;MyBarn&amp;quot; x=&amp;quot;-130.0&amp;quot; y=&amp;quot;217.5&amp;quot; alt=&amp;quot;3000.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;3&amp;quot; x=&amp;quot;-30.0&amp;quot; y=&amp;quot;50&amp;quot; height=&amp;quot;50.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;4&amp;quot; x=&amp;quot;-30.0&amp;quot; y=&amp;quot;50.&amp;quot; alt=&amp;quot;ground_alt + 50&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;_MYHELPERSPOT&amp;quot; x=&amp;quot;-30.0&amp;quot; y=&amp;quot;60&amp;quot; height=&amp;quot;50.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;_MYOTHERHELPERSPOT&amp;quot; x=&amp;quot;-70.0&amp;quot; y=&amp;quot;90&amp;quot; height=&amp;quot;70.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;TOWER&amp;quot; lat=&amp;quot;48.858249&amp;quot; lon=&amp;quot;2.294494&amp;quot; height=&amp;quot;324.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;MountainCAFE&amp;quot; utm_x0=&amp;quot;360284.8&amp;quot; utm_y0=&amp;quot;4813595.5&amp;quot; alt=&amp;quot;1965.&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/waypoints&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
'''Tips'''&lt;br /&gt;
* Waypoints are easily adjusted with the [[Flight_Plan_Editor|flight plan editor]].&lt;br /&gt;
* If a waypoint name starts with an underscore ( _ ), the waypoint is '''not displayed''' in the GCS, except in editor mode.&lt;br /&gt;
* The maximum number of waypoints is 254.&lt;br /&gt;
* A waypoint named &amp;lt;tt&amp;gt;HOME&amp;lt;/tt&amp;gt; is required if the failsafe HOME mode procedure is used.&lt;br /&gt;
* A waypoints index/reference pointer is derived by prefixing the waypoint name with &amp;quot;WP_&amp;quot;. Useful when a [[#Call |call function]] uses the waypoints reference index vs. it's name.&lt;br /&gt;
&lt;br /&gt;
== Sectors ==&lt;br /&gt;
&lt;br /&gt;
=== Static sectors (default) ===&lt;br /&gt;
&lt;br /&gt;
Flat ''Sectors'' can be described as an area defined by list of waypoint corners. Such an area will be displayed in the Ground Control Station (GCS) by colored lines connecting the cornerpoints.&lt;br /&gt;
A function is generated to check if a point, usually the aircraft itself, is ''inside'' this sector. Currently, this feature requires that the polygon is &amp;lt;b&amp;gt;convex&amp;lt;/b&amp;gt; and described in a &amp;lt;b&amp;gt;clockwise&amp;lt;/b&amp;gt; order. For a sector named &amp;lt;tt&amp;gt;MyBigGarden&amp;lt;/tt&amp;gt; the generated function for the example here would be &amp;lt;tt&amp;gt;bool_t InsideMyBigGarden(float x, float y);&amp;lt;/tt&amp;gt; where &amp;lt;tt&amp;gt;x&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;y&amp;lt;/tt&amp;gt; are east and north coordinated, in meters, relative to the geographic reference of the flight plan. If the flight plan is dynamically relocated, such a sector will be relocated but the display is currently not updated on the GCS. It would be great if one would help improving that part of the source code. Note that sector names are not allowed to contain spaces.&lt;br /&gt;
&lt;br /&gt;
For example, with the following element in a flight plan.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;sectors&amp;gt;&lt;br /&gt;
    &amp;lt;sector name=&amp;quot;MyBigGarden&amp;quot; color=&amp;quot;red&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;_1&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;_2&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;_3&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;_4&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/sector&amp;gt;&lt;br /&gt;
  &amp;lt;/sectors&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
It is then possible to add an exception clause to your flightplan. For example if the aircraft for some reason flies outside this, defined by us, sector the airframe will fly to a standby waypoint. The exclamation mark (!) means the boolean operator &amp;lt;tt&amp;gt;NOT&amp;lt;/tt&amp;gt; in this example. In regular language one would describe &amp;quot;If my airframe is NOT inside the MyBigGarden sector anymore then deroute it to the standby waypoint. In Flightplan &amp;quot;Speak&amp;quot; this is written like: &lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;exception cond=&amp;quot;! InsideMyBigGarden(GetPosX(), GetPosY())&amp;quot; deroute=&amp;quot;standby&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
NOTE: editing of the waypoints of the sector during the flight will not dynamically update the inside function. It will always check if the position is inside the original sector.&lt;br /&gt;
&lt;br /&gt;
'''Tips'''&lt;br /&gt;
* A nice option in the corner notation is that one can add an underscore ( _ ) in front of the name; a corner or waypoint name that starts with an underscore is not displayed in the GCS. Only in editor mode it is visible. It is visible in editor mode, because if you the could not see it, it also would be not possible to edit or drag the corner or waypoint to another position.&lt;br /&gt;
* The color indicating the sector borders is not fixed but can be defined by oneself if wished for via the color attribute.&lt;br /&gt;
&lt;br /&gt;
=== Dynamic sectors ===&lt;br /&gt;
&lt;br /&gt;
With the latest version (v5.5-devel-628), it is possible to create dynamic sectors. The procedure to create the sector is the same than for the static version with an extra attribute '''type=&amp;quot;dynamic&amp;quot;''':&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;sectors&amp;gt;&lt;br /&gt;
    &amp;lt;sector name=&amp;quot;MyBigGarden&amp;quot; color=&amp;quot;red&amp;quot; type=&amp;quot;dynamic&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;C1&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;C2&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;C3&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;C4&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/sector&amp;gt;&lt;br /&gt;
  &amp;lt;/sectors&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
It is also recommended to avoid using hidden waypoints (no _ prefix), so you can move the corner of your sector from the GCS. The polygon is updated on the 2D map to reflect the new waypoints positions.&lt;br /&gt;
Beside the possibility to change the shape of the area in flight, one of the main benefit is that the algorithm behind allows concave hulls. The only restriction is that the edges of the polygon should not cross each other.&lt;br /&gt;
&lt;br /&gt;
The generated function is the same than the static version and can be used the same way.&lt;br /&gt;
&lt;br /&gt;
== Variables ==&lt;br /&gt;
&lt;br /&gt;
'''Available since v5.9'''&lt;br /&gt;
&lt;br /&gt;
It is possible to declare a list of variables that will be automatically created during the flight plan generation and available for the rest of the system from the generated flight plan header and of course inside the flight plan itself. With appropriate attributes, it is also possible to make the variables accessible from the telemetry as a [[Settings|setting]].&lt;br /&gt;
&lt;br /&gt;
The following code will produce a '''float''' variable initialized to 0:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;variables&amp;gt;&lt;br /&gt;
    &amp;lt;variable var=&amp;quot;my_var&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/variables&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The type and the initial value can be changed with the '''type''' and '''init''' attributes:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;variables&amp;gt;&lt;br /&gt;
    &amp;lt;variable var=&amp;quot;my_var&amp;quot; init=&amp;quot;10&amp;quot; type=&amp;quot;int&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/variables&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
To produce an automatic setting for a variable, at least '''min''', '''max''' and '''step''' attributes need to be specified:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;variables&amp;gt;&lt;br /&gt;
    &amp;lt;variable var=&amp;quot;my_var&amp;quot; min=&amp;quot;0.&amp;quot; max=&amp;quot;10.&amp;quot; step=&amp;quot;0.1&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/variables&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
They will appear under the '''Flight Plan''' settings tab in the GCS. So more attributes can be specified: '''shortname''', '''unit''', '''alt_unit''', '''alt_unit_coef''', '''values'''. See [[Settings]] page for more information about these options.&lt;br /&gt;
&lt;br /&gt;
== Includes ==&lt;br /&gt;
&lt;br /&gt;
&amp;lt;tt&amp;gt;include&amp;lt;/tt&amp;gt; is used to add some flight plan elements defined in an external procedure. It’s useful to include pre-written procedures with only few arguments and then clarify the flight plan.&lt;br /&gt;
Here is the structure:&lt;br /&gt;
 &amp;lt;tt&amp;gt;&amp;lt;include name procedure&amp;gt; [&amp;lt;arg name value /&amp;gt;]*[&amp;lt;with from to /&amp;gt;]*&amp;lt;/include&amp;gt;&amp;lt;/tt&amp;gt;&lt;br /&gt;
where &amp;lt;tt&amp;gt;name&amp;lt;/tt&amp;gt; attribute of the include element will be used in this flight plan to prefix the blocks of the &amp;lt;tt&amp;gt;procedure&amp;lt;/tt&amp;gt;, the XML referenced file.&lt;br /&gt;
Named arguments may be given with their value in the &amp;lt;tt&amp;gt;arg&amp;lt;/tt&amp;gt; elements. The &amp;lt;tt&amp;gt;with&amp;lt;/tt&amp;gt; tag allows to link labels (e.g. attribute of a deroute instruction or of an exception) from the procedure to blocks of the main flight plan.&lt;br /&gt;
Then, each block of the procedure is like any block of the flight plan and is designated with a dotted identifier: block &amp;lt;tt&amp;gt;b&amp;lt;/tt&amp;gt; of a procedure named &amp;lt;tt&amp;gt;p&amp;lt;/tt&amp;gt; is named &amp;lt;tt&amp;gt;b.p&amp;lt;/tt&amp;gt; .&lt;br /&gt;
&lt;br /&gt;
Here is an example:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;includes&amp;gt;&lt;br /&gt;
    &amp;lt;include name=&amp;quot;landing&amp;quot; procedure=&amp;quot;landing.xml&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/includes&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Blocks ==&lt;br /&gt;
&lt;br /&gt;
Block elements are the main part of a flight plan: they describe each unit of the mission.&lt;br /&gt;
They are made of various primitives, called stages and exceptions, you can put one after the other. When a&lt;br /&gt;
stage (or a block) is finished, the autopilot goes to the next one. The behaviour after the last stage of the last block is undefined. &lt;br /&gt;
&lt;br /&gt;
As described in the DTD, the &amp;lt;tt&amp;gt;blocks&amp;lt;/tt&amp;gt; element is composed of &amp;lt;tt&amp;gt;block&amp;lt;/tt&amp;gt; elements which are sequence of ''stages'':&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;!ELEMENT blocks (block+)&amp;gt;&lt;br /&gt;
  &amp;lt;!ELEMENT block  (exception|while|heading|attitude|go|xyz|set|call|circle|deroute|stay|follow|survey_rectangle|for|return|eight|oval|home|path)*&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Example:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;block name=&amp;quot;circlehome&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;circle radius=&amp;quot;75&amp;quot; wp=&amp;quot;HOME&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
You can add a button in the [[GCS#Strips|strip of the aircraft]] with the attribute &amp;lt;tt&amp;gt;strip_button&amp;lt;/tt&amp;gt;:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;block name=&amp;quot;descent&amp;quot; strip_button=&amp;quot;Descent&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;circle wp=&amp;quot;HOME&amp;quot; throttle=&amp;quot;0.0&amp;quot; pitch=&amp;quot;-15&amp;quot; vmode=&amp;quot;throttle&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
This button will activate the block. If the attribute &amp;lt;tt&amp;gt;group&amp;lt;/tt&amp;gt; is specified, all strip buttons of the same group will be placed vertically on top of each other.&lt;br /&gt;
&lt;br /&gt;
In the same way, a key shortcut can be specified:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;block key=&amp;quot;D&amp;quot; name=&amp;quot;descent&amp;quot; strip_button=&amp;quot;Descent&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;circle wp=&amp;quot;HOME&amp;quot; throttle=&amp;quot;0.0&amp;quot; pitch=&amp;quot;-15&amp;quot; vmode=&amp;quot;throttle&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
Modifiers are allowed, using the syntax of [http://library.gnome.org/devel/gtk/2.15/gtk-Keyboard-Accelerators.html#gtk-accelerator-parse GTK accelerators].&lt;br /&gt;
&lt;br /&gt;
An icon can be specified to display the button. The &amp;lt;tt&amp;gt;strip_button&amp;lt;/tt&amp;gt; label then is a tooltip for the icon. The icon must be an image file available in the directory &amp;lt;tt&amp;gt;data/pictures/gcs_icons&amp;lt;/tt&amp;gt;:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;block name=&amp;quot;Takeoff&amp;quot; strip_icon=&amp;quot;takeoff.png&amp;quot; strip_button=&amp;quot;Takeoff&amp;quot;&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
You can call functions before or after each execution of the block:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;block name=&amp;quot;circlehome&amp;quot; pre_call=&amp;quot;function_to_call_before_circle()&amp;quot; post_call=&amp;quot;function_to_call_after_circle()&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;circle wp=&amp;quot;HOME&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Expressions ====&lt;br /&gt;
&lt;br /&gt;
Most of the numeric attributes in stages are analyzed as C expressions. The syntax of this C expression is restricted to &lt;br /&gt;
* numeric constants&lt;br /&gt;
* some internal autopilot variables (not fully documented, see [[Flight_Plans#Internal_Variables_in_Flight_Plans|internal variables section]] below and other examples)&lt;br /&gt;
* Some binary operators: &amp;lt;, &amp;gt;, &amp;lt;=, &amp;gt;=, &amp;lt;&amp;gt;, ==, +, -, /, *&lt;br /&gt;
* Some utility functions&lt;br /&gt;
&lt;br /&gt;
Some examples of usable expressions are given in the next sections.&lt;br /&gt;
=== Initialization  Blocks ===&lt;br /&gt;
Most flight plans will have three blocks of flight plan initialization blocks. It is good practice to follow this example below if you first start learning to create flightplans&lt;br /&gt;
&lt;br /&gt;
The first block waits until the GPS fix has been established, as shown below.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;blocks&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Wait GPS&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;set value=&amp;quot;1&amp;quot; var=&amp;quot;kill_throttle&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;while cond=&amp;quot;!GpsFixValid()&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
The second block updates the local waypoints with respect to the UAV.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Geo init&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;while cond=&amp;quot;LessThan(NavBlockTime(), 10)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;NavSetGroundReferenceHere()&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
This next block prevents the UAV from starting the engine and taking off. &lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Holding point&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;!--set var=&amp;quot;nav_mode&amp;quot; value=&amp;quot;NAV_MODE_ROLL&amp;quot;/--&amp;gt;&lt;br /&gt;
      &amp;lt;set value=&amp;quot;1&amp;quot; var=&amp;quot;kill_throttle&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;attitude roll=&amp;quot;0&amp;quot; throttle=&amp;quot;0&amp;quot; vmode=&amp;quot;throttle&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Exceptions ===&lt;br /&gt;
&lt;br /&gt;
The flight manager can handle exceptions. They consist in conditions checked periodically (at the same pace as the navigation control), allowing the control to jump to a given block. Here is the syntax of exceptions:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;exception cond=&amp;quot;...&amp;quot; deroute=&amp;quot;...&amp;quot;&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
where &amp;lt;tt&amp;gt;cond&amp;lt;/tt&amp;gt; is an expression and &amp;lt;tt&amp;gt;deroute&amp;lt;/tt&amp;gt; is the name of the block we want to switch to as soon as the condition is true.&lt;br /&gt;
&lt;br /&gt;
Here are some example of exceptions:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;exception cond=&amp;quot;10 &amp;gt; PowerVoltage()&amp;quot; deroute=&amp;quot;go_down&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;exception cond=&amp;quot;(ground_alt+10 &amp;gt; GetPosAlt())&amp;quot; deroute=&amp;quot;go_up&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;exception cond=&amp;quot;(autopilot_flight_time &amp;gt; 840)&amp;quot; deroute=&amp;quot;quick_land&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Exceptions can be local to a block or global to the flight plan, in the &amp;lt;tt&amp;gt;&amp;lt;exceptions&amp;gt;&amp;lt;/tt&amp;gt; element. In the following example, time since last reception of a message from the ground station is monitored and the navigation is switched to the &amp;lt;tt&amp;gt;Standby&amp;lt;/tt&amp;gt; block if no message have been received for 22s. This exception is valid for '''all''' the blocks.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;flight_plan ...&amp;gt;&lt;br /&gt;
    &amp;lt;waypoints&amp;gt; ... &amp;lt;/waypoints&amp;gt;&lt;br /&gt;
    &amp;lt;exceptions&amp;gt;&lt;br /&gt;
      &amp;lt;exception cond=&amp;quot;datalink_time &amp;gt; 22&amp;quot; deroute=&amp;quot;Standby&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/exceptions&amp;gt;&lt;br /&gt;
  &amp;lt;blocks&amp;gt; ...&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Deroute ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;deroute&amp;lt;/tt&amp;gt; is the ''goto'' directive of the flight plan; it switches the navigation to the given block:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;deroute block=&amp;quot;landing&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Note that this primitive should not be used to execute loops which are provided by the following elements.&lt;br /&gt;
&lt;br /&gt;
=== Return ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;return&amp;lt;/tt&amp;gt; is also a ''goto'' directive that brings you back to the last block (and last stage). It has no argument.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;return/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Loops ===&lt;br /&gt;
&lt;br /&gt;
Unbounded loops are written with &amp;lt;tt&amp;gt;while&amp;lt;/tt&amp;gt; elements whose &amp;lt;tt&amp;gt;cond&amp;lt;/tt&amp;gt; attribute is a boolean expression.&lt;br /&gt;
Children  of &amp;lt;tt&amp;gt;while&amp;lt;/tt&amp;gt; are stages:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;while cond=&amp;quot;TRUE&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;go wp=&amp;quot;A&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;go wp=&amp;quot;B&amp;quot;/&amp;gt; &lt;br /&gt;
    &amp;lt;go wp=&amp;quot;C&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;while cond=&amp;quot;5 &amp;gt; stage_time&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;/while&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
In this example, we run an infinite loop, letting the aircraft try to go via waypoints &amp;lt;tt&amp;gt;A&amp;lt;/tt&amp;gt;, &amp;lt;tt&amp;gt;B&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;C&amp;lt;/tt&amp;gt; and waiting for 5 seconds before repeating.&lt;br /&gt;
&lt;br /&gt;
Bounded loops are written with the &amp;lt;tt&amp;gt;for&amp;lt;/tt&amp;gt; tag:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;for var=&amp;quot;i&amp;quot; from=&amp;quot;0&amp;quot; to=&amp;quot;3&amp;quot;&amp;gt;&lt;br /&gt;
    ...&lt;br /&gt;
  &amp;lt;/for&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
where the body of the loop will be run four times.&lt;br /&gt;
&lt;br /&gt;
The variable of a &amp;lt;tt&amp;gt;for&amp;lt;/tt&amp;gt; loop can be used inside expressions appearing as attributes of the stages:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;for var=&amp;quot;i&amp;quot; from=&amp;quot;1&amp;quot; to=&amp;quot;5&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;circle wp=&amp;quot;HOME&amp;quot; radius=&amp;quot;75&amp;quot; alt=&amp;quot;ground_alt+50*$i&amp;quot; until=&amp;quot;stage_time&amp;gt;10&amp;quot; /&amp;gt;&lt;br /&gt;
  &amp;lt;/for&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
In this example, the aircraft will circle around waypoint '''HOME''' for 10 seconds at an altitude above ground of 50m (1x50), 10 seconds at an altitude of 100m (2x50), ... until 250m (5x50).&lt;br /&gt;
&lt;br /&gt;
Note: Two bounded loops using the same control variable are not allowed in the same block.&lt;br /&gt;
&lt;br /&gt;
=== Navigation modes ===&lt;br /&gt;
&lt;br /&gt;
Navigation modes give the description of the desired trajectory in 3D. While the horizontal mode is specified through&lt;br /&gt;
''stages'', the vertical control is specified with various attributes of these stages. The current available navigation stages are&lt;br /&gt;
* attitude : just keep a fixed attitude;&lt;br /&gt;
* heading : keep a given course;&lt;br /&gt;
* go : go to a given waypoint;&lt;br /&gt;
* path : list of waypoints linked by ''go''&lt;br /&gt;
* circle : circle around a waypoint;&lt;br /&gt;
* oval : two half circles with a straight between two nav points&lt;br /&gt;
* eight : fly a figure of eight through a waypoint and around another&lt;br /&gt;
* stay : hold the position (hard to realize for a fixed-wing aircraft);&lt;br /&gt;
* follow : follow another aircraft;&lt;br /&gt;
* xyz : circle around a point moveable with the RC transmitter stick (obsolete with the datalink).&lt;br /&gt;
&lt;br /&gt;
The vertical control is achieved using the &amp;lt;tt&amp;gt;vmode&amp;lt;/tt&amp;gt; attribute of these stages. The possible values are &lt;br /&gt;
* '''alt''' (the default) : the autopilot keeps the desired altitude which is the altitude of the waypoint (if any) or the altitude specified with the &amp;lt;tt&amp;gt;alt&amp;lt;/tt&amp;gt; attribute;&lt;br /&gt;
* '''climb''' : the autopilot keeps the desired vertical speed specified with the &amp;lt;tt&amp;gt;climb&amp;lt;/tt&amp;gt; attribute (in m/s);&lt;br /&gt;
* '''throttle''' : the autopilots sets the desired throttle specified with the &amp;lt;tt&amp;gt;throttle&amp;lt;/tt&amp;gt; attribute (between 0 and 1);&lt;br /&gt;
* '''glide''' : the autopilot keeps the desired slope between two waypoints&lt;br /&gt;
&lt;br /&gt;
The default control is done with the throttle. However, setting the &amp;lt;tt&amp;gt;pitch&amp;lt;/tt&amp;gt; attribute to '''auto''' and the &amp;lt;tt&amp;gt;throttle&amp;lt;/tt&amp;gt; attribute to a constant allows a vertical control only by controlling the attitude of the A/C.&lt;br /&gt;
The &amp;lt;tt&amp;gt;pitch&amp;lt;/tt&amp;gt; attribute also can be set to any value (in degrees) while the throttle control is in use: it usually affects the airspeed of the aircraft.  &lt;br /&gt;
&lt;br /&gt;
The different navigation modes are detailed in the next sections.&lt;br /&gt;
&lt;br /&gt;
=== Attitude ===&lt;br /&gt;
&lt;br /&gt;
Element &amp;lt;tt&amp;gt;attitude&amp;lt;/tt&amp;gt; is the navigation mode which corresponds to the current lowest control loop for horizontal mode.&lt;br /&gt;
The autopilot then keeps a constant attitude. The &amp;lt;tt&amp;gt;roll&amp;lt;/tt&amp;gt; attribute is required (in degrees, positive to put right wing low).&lt;br /&gt;
&lt;br /&gt;
To fly away, at constant airspeed:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;attitude roll=&amp;quot;0&amp;quot; vmode=&amp;quot;throttle&amp;quot;, throttle=&amp;quot;0.5&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
To fly around, holding a given altitude:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;attitude roll=&amp;quot;30&amp;quot; alt=&amp;quot;ground_alt+50&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Note that it is not a ''safe'' navigation mode since the geographic position of the plane is not controlled. However, this mode is useful to tune the roll attitude control loop.&lt;br /&gt;
&lt;br /&gt;
=== Heading ===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;tt&amp;gt;heading&amp;lt;/tt&amp;gt; primitive is relative to the second level loop for horizontal mode in the autopilot which will keep the given &amp;lt;tt&amp;gt;course&amp;lt;/tt&amp;gt;, a required attribute (in degrees, clockwise, north=0, east=90).&lt;br /&gt;
&lt;br /&gt;
One example to takeoff, following the QFU, 80% throttle, nose up (15 degrees) until height of 30m is reached:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;heading course=&amp;quot;QFU&amp;quot; vmode=&amp;quot;throttle&amp;quot; throttle=&amp;quot;0.8&amp;quot; pitch=&amp;quot;15&amp;quot; until=&amp;quot;(GetPosAlt() &amp;gt; ground_alt+30)&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Go ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;go&amp;lt;/tt&amp;gt; primitive is probably the most useful one. Basically, the autopilot will try to join a given waypoint (&amp;lt;tt&amp;gt;wp&amp;lt;/tt&amp;gt;, the only required attribute). So the simplest thing you can ask for is&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;go wp=&amp;quot;HOME&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
which will set the '''HOME''' waypoint as the desired target position. Note than since &amp;lt;tt&amp;gt;vmode=&amp;quot;alt&amp;quot;&amp;lt;/tt&amp;gt; is the default, the altitude of the target waypoint is also taken into account. The navigation will switch to the next stage as soon as the target is reached.&lt;br /&gt;
&lt;br /&gt;
It is usually not a good idea to try to join a waypoint without asking for a precise trajectory, i.e. a given line.&lt;br /&gt;
Setting the &amp;lt;tt&amp;gt;hmode&amp;lt;/tt&amp;gt; attribute to '''route''', the navigation will go over a segment joining two waypoints:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;go from=&amp;quot;wp1&amp;quot; wp=&amp;quot;wp2&amp;quot; hmode=&amp;quot;route&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The target altitude is the altitude of the target waypoint; it can also be set with the &amp;lt;tt&amp;gt;alt&amp;lt;/tt&amp;gt; attribute. The following example keeps an altitude with fixed throttle:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;go from=&amp;quot;wp2&amp;quot; wp=&amp;quot;wp3&amp;quot; hmode=&amp;quot;route&amp;quot; pitch=&amp;quot;auto&amp;quot; throttle=&amp;quot;0.75&amp;quot; alt=&amp;quot;ground_alt+100&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
The attributes related to the vertical control can also be set to replace the default altitude mode:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;go from=&amp;quot;wp1&amp;quot; wp=&amp;quot;wp2&amp;quot; hmode=&amp;quot;route&amp;quot; vmode=&amp;quot;climb&amp;quot; climb=&amp;quot;1.5&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Finally, the &amp;lt;tt&amp;gt;approaching_time&amp;lt;/tt&amp;gt; (in seconds) attribute helps to decide when the target is ''reached''. It can be set&lt;br /&gt;
to '''0''' to go over the target waypoint (default value is the '''CARROT''' time, set in the airframe configuration file).&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;go from=&amp;quot;wp1&amp;quot; wp=&amp;quot;wp2&amp;quot; hmode=&amp;quot;route&amp;quot; approaching_time=&amp;quot;1&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Path ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;path&amp;lt;/tt&amp;gt; primitive is just a shorthand expression for a set of &amp;lt;tt&amp;gt;go&amp;lt;/tt&amp;gt; primitives. A list of waypoints defined with the &amp;lt;tt&amp;gt;wpts&amp;lt;/tt&amp;gt; attribute is pre-processed into a set of &amp;lt;tt&amp;gt;go&amp;lt;/tt&amp;gt; primitives with the &amp;lt;tt&amp;gt;hmode&amp;lt;/tt&amp;gt; attribute. For example:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;path wpts=&amp;quot;wp1, wp2, wp3&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Other attributes are optional:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;path wpts=&amp;quot;wp3, wp1, wp2&amp;quot; approaching_time=&amp;quot;1&amp;quot; pitch=&amp;quot;auto&amp;quot; throttle=&amp;quot;0.5&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Circle ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;circle&amp;lt;/tt&amp;gt; primitive is the second main navigation mode: the trajectory is defined as a circle around a given waypoint with a given radius:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;circle wp=&amp;quot;HOME&amp;quot; radius=&amp;quot;75&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
A positive radius makes the UAS move clockwise, a negative counter-clockwise.&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;until&amp;lt;/tt&amp;gt; attribute may be used to control the end of the stage. The following example defines an ascending trajectory at constant throttle, nose up (15 degrees), over growing circles, until the battery level is low:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;circle wp=&amp;quot;wp1&amp;quot; radius=&amp;quot;50+(GetPosAlt()-ground_alt)/2&amp;quot; vmode=&amp;quot;throttle&amp;quot; throttle=&amp;quot;0.75&amp;quot; pitch=&amp;quot;15&amp;quot; until=&amp;quot;10&amp;gt;PowerVoltage()&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Oval ===&lt;br /&gt;
The oval consists of two half circles that are connected with two straight lines. This flight path is usefull when a IMU is used because the straights allow for level flight. &lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt; &amp;lt;oval p1=&amp;quot;1&amp;quot; p2=&amp;quot;2&amp;quot; radius=&amp;quot;nav_radius&amp;quot;/&amp;gt; &amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Eight ===&lt;br /&gt;
'''Works only for Fixed-wing!''' Fly a figure of eight that consists of two straight legs that pass though the center and the center of the half circle at the end of the two legs is in the turn around  waypoint. The altitude of the center waypoint is used for the entire figure. The turn around waypoint is moved to match radius given. &lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;  &amp;lt;eight center=&amp;quot;1&amp;quot; radius=&amp;quot;nav_radius&amp;quot; turn_around=&amp;quot;2&amp;quot;/&amp;gt; &amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Survey rectangle ===&lt;br /&gt;
Fly a survey rectangle defined by two waypoints. The distance between the legs of the grid (in meter) and the orientation of the grid (NS or WE) can be set by the operator. The plane will turn outside of the border of the rectangle before starting a new leg.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;  &amp;lt;survey_rectangle wp1=&amp;quot;1&amp;quot; wp2=&amp;quot;2&amp;quot; grid=&amp;quot;200&amp;quot; orientation=&amp;quot;NS&amp;quot;/&amp;gt; &amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Follow ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;follow&amp;lt;/tt&amp;gt; is a special primitive which makes the UAS follow another UAS (real or simulated, named with its &amp;lt;tt&amp;gt;ac_id&amp;lt;/tt&amp;gt;) at a given &amp;lt;tt&amp;gt;distance&amp;lt;/tt&amp;gt; (in meters) behind and at a given &amp;lt;tt&amp;gt;height&amp;lt;/tt&amp;gt; (in meters) above.&lt;br /&gt;
&lt;br /&gt;
In this example, the autopilot will try to follow A/C number '''4''', staying '''50'''m behind and '''20'''m above.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;follow ac_id=&amp;quot;4&amp;quot; distance=&amp;quot;50&amp;quot; height=&amp;quot;20&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Stay ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;stay&amp;lt;/tt&amp;gt; Here the UAS with try to stay at the waypoint as best as it can. For an aircraft capable of hovering it will just hang above the waypoint. For a fixedwing type UAV,&amp;lt;tt&amp;gt;stay&amp;lt;/tt&amp;gt; will mean the aircraft will constantly fly straight through the waypoint in a flower like pattern with the smallest turn radius it can manage.&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;stay wp=&amp;quot;HOME&amp;quot; alt=&amp;quot;10&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== XYZ ===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;tt&amp;gt;xyz&amp;lt;/tt&amp;gt; is a special mode where the UAS circles around a user moveable waypoint. This waypoint is moved with the RC sticks:&lt;br /&gt;
* YAW channel controls the point over the west-east axis;&lt;br /&gt;
* PITCH channel controls the point over the south-north axis;&lt;br /&gt;
* ROLL channel controls the altitude.&lt;br /&gt;
&lt;br /&gt;
Example (default radius is '''100'''):&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;xyz radius=&amp;quot;40&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Set ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;set&amp;lt;/tt&amp;gt; element is a dangerous one which should be used only by expert users: it is used to directly set an internal variable of the autopilot. For example, you can change the value of the default ground altitude, a variable used by the home mode failsafe procedure (and maybe by your own flight plan):&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;set var=&amp;quot;ground_alt&amp;quot; value=&amp;quot;ground_alt+50&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
This directive is extremely powerful and has great potential for error - use with caution.&lt;br /&gt;
&lt;br /&gt;
=== Call ===&lt;br /&gt;
&lt;br /&gt;
The &amp;lt;tt&amp;gt;call&amp;lt;/tt&amp;gt; allows the user to define its own navigation procedures in C. The &amp;lt;tt&amp;gt;value&amp;lt;/tt&amp;gt; must be a call to a boolean function which must return TRUE as long as the stage is not completed (a function which should be called only once would then return immediately FALSE).&lt;br /&gt;
This feature is illustrated with the '''line''' pattern:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;call fun=&amp;quot;nav_line_setup()&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;call fun=&amp;quot;nav_line_run(WP_1, WP_2, nav_radius)&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
where &amp;lt;tt&amp;gt;nav_line_setup()&amp;lt;/tt&amp;gt; returns FALSE and &amp;lt;tt&amp;gt;nav_line_run()&amp;lt;/tt&amp;gt; always returns TRUE (this stage never ends). '''Note''' that a waypoints index is derived/denoted by prefixing the waypoint name with &amp;lt;tt&amp;gt;WP_&amp;lt;/tt&amp;gt;(i.e.: 1 --&amp;gt; WP_1, 2 --&amp;gt; WP_2)&lt;br /&gt;
&amp;lt;br /&amp;gt;&lt;br /&gt;
&lt;br /&gt;
To call ''any'' function exactly once regardless of the return value (e.g. call a void function), add &amp;lt;tt&amp;gt;loop=&amp;quot;FALSE&amp;quot;&amp;lt;/tt&amp;gt;&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;call fun=&amp;quot;viewvideo_take_shot(TRUE)&amp;quot; loop=&amp;quot;FALSE&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
or use the &amp;lt;tt&amp;gt;call_once&amp;lt;/tt&amp;gt; alias:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;call_once fun=&amp;quot;viewvideo_take_shot(TRUE)&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Such extra navigation functions are usually written as a [[Modules|Module]] and the header files are included automatically.&lt;br /&gt;
&lt;br /&gt;
If you want to call functions that are not part of a module, you need to include the header file which contains the function declaration:or supplementary C file which must be specified in the &lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;header&amp;gt;&lt;br /&gt;
#include &amp;quot;path/to/header.h&amp;quot;&lt;br /&gt;
  &amp;lt;/header&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
where the path is relative to the &amp;lt;tt&amp;gt;sw/airborne&amp;lt;/tt&amp;gt; directory.&lt;br /&gt;
&lt;br /&gt;
You can also call functions before or after each execution of the block (this means continuously on each iteration of each stage of the block, not just when entering o exiting the block).&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;block name=&amp;quot;circlehome&amp;quot; pre_call=&amp;quot;function_to_call_before_circle()&amp;quot; post_call=&amp;quot;function_to_call_after_circle()&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;circle wp=&amp;quot;HOME&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Pre Call ===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;block name=&amp;quot;Standby&amp;quot; strip_button=&amp;quot;Standby&amp;quot; strip_icon=&amp;quot;home.png&amp;quot; pre_call=&amp;quot;if(!InsideKill(GetPosX(), GetPosY())) NavKillThrottle();&amp;quot;&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Post Call ===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;block name=&amp;quot;traj&amp;quot; pre_call=&amp;quot;formation_pre_call()&amp;quot; post_call=&amp;quot;formation_flight()&amp;quot;&amp;gt; &amp;lt;!-- formation flight is call after all other navigation tasks --&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Procedures ==&lt;br /&gt;
&lt;br /&gt;
Procedures are libraries which can be included in flight plans. They are composed of waypoints, sectors and blocks. The header of a procedure may contain some parameters which are replaced by arguments when the procedure is included.&lt;br /&gt;
&lt;br /&gt;
Extract of the DTD: a procedure is a sequence of parameters, waypoints, ...:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;!ELEMENT procedure (param*,header?,waypoints?,sectors?,exceptions?,blocks?)&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
A &amp;lt;tt&amp;gt;param&amp;lt;/tt&amp;gt;eter is just a name. A parameter is optional if it is declared with a default value.&lt;br /&gt;
An example with a required and an optional parameter:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;param name=&amp;quot;alt&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;param name=&amp;quot;radius&amp;quot; default_value=&amp;quot;75&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Procedures are called with the &amp;lt;tt&amp;gt;include&amp;lt;/tt&amp;gt; element in a flight plan. A procedure cannot be included twice or by another procedure. A procedure call requires:&lt;br /&gt;
&lt;br /&gt;
* the name of the procedure file, the name given to this inclusion; &lt;br /&gt;
* values for the parameters;&lt;br /&gt;
* backlinks for block name exits of the procedure.&lt;br /&gt;
&lt;br /&gt;
For example:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;include name=&amp;quot;landing&amp;quot; procedure=&amp;quot;landing.xml&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Here is the corresponding procedure '''landing.xml''':&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
&amp;lt;!DOCTYPE procedure SYSTEM &amp;quot;flight_plan.dtd&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;procedure&amp;gt;&lt;br /&gt;
    &amp;lt;waypoints&amp;gt;&lt;br /&gt;
      &amp;lt;waypoint name=&amp;quot;AF&amp;quot; x=&amp;quot;177.4&amp;quot; y=&amp;quot;45.1&amp;quot; alt=&amp;quot;30&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;waypoint name=&amp;quot;TD&amp;quot; x=&amp;quot;28.8&amp;quot; y=&amp;quot;57.0&amp;quot; alt=&amp;quot;0&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;waypoint name=&amp;quot;_BASELEG&amp;quot; x=&amp;quot;168.8&amp;quot; y=&amp;quot;-13.8&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/waypoints&amp;gt;&lt;br /&gt;
    &amp;lt;blocks&amp;gt;&lt;br /&gt;
      ...&lt;br /&gt;
      &amp;lt;block name=&amp;quot;land&amp;quot;&amp;gt;&lt;br /&gt;
        &amp;lt;call fun=&amp;quot;nav_compute_baseleg(WP_AF, WP_TD, WP__BASELEG, nav_radius)&amp;quot;/&amp;gt;&lt;br /&gt;
        &amp;lt;circle radius=&amp;quot;nav_radius&amp;quot; until=&amp;quot;NavCircleCount() &amp;gt; 0.5&amp;quot; wp=&amp;quot;_BASELEG&amp;quot;/&amp;gt;&lt;br /&gt;
        &amp;lt;circle radius=&amp;quot;nav_radius&amp;quot; until=&amp;quot;And(NavQdrCloseTo(DegOfRad(baseleg_out_qdr)-10), 10 &amp;gt; fabs(GetPosAlt()- WaypointAlt(WP__BASELEG)))&amp;quot; wp=&amp;quot;_BASELEG&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;/block&amp;gt;&lt;br /&gt;
      ...&lt;br /&gt;
    &amp;lt;/blocks&amp;gt;&lt;br /&gt;
  &amp;lt;/procedure&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Note that the name of procedure '''land''' block will be renamed into '''landing.land''':&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;deroute block=&amp;quot;landing.land&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
will jump to this procedure block.&lt;br /&gt;
&lt;br /&gt;
Suppose you have a go-around condition in your landing procedure. You would write it&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;exception cond=&amp;quot;...&amp;quot; deroute=&amp;quot;go-around&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
then you must link this block exit with one of your block (e.g. &amp;lt;tt&amp;gt;Standby&amp;lt;/tt&amp;gt;). So you would include the procedure as follows:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;include name=&amp;quot;landing&amp;quot; procedure=&amp;quot;landing.xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;with from=&amp;quot;go-around&amp;quot; to=&amp;quot;Standby&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/include&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Internal Variables in Flight Plans ==&lt;br /&gt;
&lt;br /&gt;
The flight plan can use several internal variables, macros and functions coming from the rest of the system or the flight plan API itself. The following list present some of the most commonly used variables, but much more are actually available:&lt;br /&gt;
&lt;br /&gt;
* '''autopilot_flight_time''': time in seconds since autopilot was booted (integer)&lt;br /&gt;
* '''datalink_time''': time in seconds since last connection of telemetry to ground control station (including ''subsystems/datalink/datallink.h'' in the '''header''' section is required) (integer)&lt;br /&gt;
* '''GetPosAlt()''': returns the current altitude above ground level in meter (float)&lt;br /&gt;
* '''GetPosX()''': returns x (easting) of current position relative to reference in meter (float)&lt;br /&gt;
* '''GetPosY()''': returns y (northing) of current position relative to reference in meter (float)&lt;br /&gt;
* &amp;lt;s&amp;gt;'''ground_alt''': altitude above ground level in meter (float)&amp;lt;/s&amp;gt; (v5.8 and higher - use '''GetAltRef()''' instead)&lt;br /&gt;
* '''GetAltRef()''': returns reference altitude, usually ground_alt&lt;br /&gt;
* '''NavSetGroundReferenceHere()''': reset position and altitude reference point to current position&lt;br /&gt;
* '''NavSetAltitudeReferenceHere()''': reset altitude reference to current alt but keep previous horizontal position reference&lt;br /&gt;
* '''NavSetWaypointHere(_wp)''': set position of a waypoint given as argument to the current position&lt;br /&gt;
* '''WaypointX(_wp)''': returns x (easting) of waypoint position relative to reference in meter (float)&lt;br /&gt;
* '''WaypointY(_wp)''': returns y (northing) of waypoint position relative to reference in meter (float)&lt;br /&gt;
* '''WaypointAlt(_wp)''': returns waypoint altitude in meter (float)&lt;br /&gt;
* '''nav_radius''': free variable usually used to set circle radius in flight plan&lt;br /&gt;
* '''NavKillThrottle()''': function to switch off throttle&lt;br /&gt;
* '''PowerVoltage()''': returns current voltage of the battery&lt;br /&gt;
* all functions from the [http://docs.paparazziuav.org/latest/group__state__interface.html state interface API]&lt;br /&gt;
* all functions from the [http://docs.paparazziuav.org/latest/subsystems_2navigation_2waypoints_8h.html waypoint API]&lt;br /&gt;
* all variables declared in [[modules]] headers&lt;br /&gt;
&lt;br /&gt;
== Advanced Examples ==&lt;br /&gt;
&lt;br /&gt;
Parameters used in a flight plan can be computed expressions. In this example, the plane is asked to perform 5 circles at progressively increasing altitudes for exactly one minute at each altitude:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;for var=&amp;quot;i&amp;quot; from=&amp;quot;1&amp;quot; to=&amp;quot;5&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;circle wp=&amp;quot;HOME&amp;quot; radius=&amp;quot;75&amp;quot;&lt;br /&gt;
          alt=&amp;quot;ground_alt + 50*$i&amp;quot;&lt;br /&gt;
          until=&amp;quot;stage_time &amp;gt; 60&amp;quot; /&amp;gt;&lt;br /&gt;
  &amp;lt;/for&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Below you find some random examples of the posibilities. This is only the tip of the iceberg, use your imagination and go wild with new creative ideas for your flightplan&lt;br /&gt;
&lt;br /&gt;
=== Gains on the fly ===&lt;br /&gt;
&lt;br /&gt;
It is very well possible to set specific gain for an airframe if it reaches e.g a certain block.&lt;br /&gt;
&lt;br /&gt;
=== Dynacmically adjustable maximum speed ===&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
&amp;lt;call_once fun=&amp;quot;gh_set_max_speed(2.0)&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Immobilize Actuators === &lt;br /&gt;
&lt;br /&gt;
h_ctl setpoints variable are set by the h_ctl_attitude_loop() (from fw_h_ctl.c) loop) which can be disabled with the h_ctl_disabled flag:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;set var=&amp;quot;h_ctl_disabled&amp;quot; value=&amp;quot;TRUE&amp;quot;/&amp;gt;&lt;br /&gt;
 &amp;lt;set var=&amp;quot;h_ctl_aileron_setpoint&amp;quot; value=&amp;quot;0&amp;quot;/&amp;gt;&lt;br /&gt;
 &amp;lt;set var=&amp;quot;h_ctl_elevator_setpoint&amp;quot; value=&amp;quot;MAX_PPRZ/2&amp;quot;/&amp;gt;&lt;br /&gt;
 .... waiting for a condition ...&lt;br /&gt;
 &amp;lt;set var=&amp;quot;h_ctl_disabled&amp;quot; value=&amp;quot;FALSE&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Tips and Tricks ==&lt;br /&gt;
&lt;br /&gt;
There are many ways to skin a cat just as there are many ways to craft your flight plan. Following the best practices tips can save you from a lot of frustration and mishap.&lt;br /&gt;
&lt;br /&gt;
* Simulate your flight plan before taking it to the sky. Flight plans should always be carefully tested prior to flight, take a look at the [[Simulation|simulation]] page for details on how to simulate your plan.&lt;br /&gt;
* Make an subdirectory in the Flight_plan directory with your own name and add your flight plans there. Make sure that the location of the DTD is correct, e.g by using relative directory double dots as in &amp;lt;tt&amp;gt;&amp;lt;!DOCTYPE flight_plan SYSTEM &amp;quot;../flight_plan.dtd&amp;quot;&amp;gt;&amp;lt;/tt&amp;gt;&lt;br /&gt;
&lt;br /&gt;
* Take a good look at other flight plans included with Paparazzi. To learn from example flight plans please visit the [[Flight_Plan_Examples|flight plan examples]] page&lt;br /&gt;
* There are several option to build failsafe features into you flightplan, [[Failsafe|for some examples visit the Failsafe page]].&lt;br /&gt;
* Some flight plan examples define waypoint locations using relative coordinates. These are relative positions from the fixed lat and lon in the header of the flight plan. When simulating your flight plan the aircraft always use the lat/lon as defined in the flight plan since a regular simulation has no notion of you current position of you local PC where you simulate on. This is something to keep in mind if you test your flight plan in real flights.&lt;br /&gt;
&lt;br /&gt;
=== V5.8+ ===&lt;br /&gt;
* If you don't like the '''No SRTM data found to check altitude''' warning, either in your flight plan editor or in GCS itself click on the '''Nav-&amp;gt;display SRTM'''. It will ask you whether you want to download SRTM data. Say yes, and it will save the data in ''data/srtm'' directory, so you don't get the warning any more and check the ground altitude even without GPS.&lt;br /&gt;
&lt;br /&gt;
[[Category:Software]] [[Category:User_Documentation]]&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Advanced_Navigation_Routines&amp;diff=23641</id>
		<title>Advanced Navigation Routines</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Advanced_Navigation_Routines&amp;diff=23641"/>
		<updated>2017-03-29T13:56:26Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: /* Navigation Routines (Prev.OSAM) */  : added the new path&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;= Introduction =&lt;br /&gt;
&lt;br /&gt;
The flight plan standard navigation functions are very flexible. However sometimes one needs to perform a very specific task, and the basic functions are not enough to accomplish a special mission. In that case you can use additional modules functions in the flight plan. By adding a navigation capability to your airframe. The flight plan now has extra functionality that can be used.&lt;br /&gt;
&lt;br /&gt;
= Available navigation modules =&lt;br /&gt;
&lt;br /&gt;
==  Navigation Routines (Prev.OSAM) ==&lt;br /&gt;
&lt;br /&gt;
Thanks to Team OSAM's contribution these navigation capabilities have been added.&lt;br /&gt;
&lt;br /&gt;
To use these navigation routines, you need to change the navigation subsystem type to extra in your airframe file. The navigation extra subsystem includes extra navigation routines like OSAMnav, spiral, poly_survey_advanced, nav_cube, etc.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;subsystem name=&amp;quot;navigation&amp;quot; type=&amp;quot;extra&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Also include OSAMNav.h in your flight plan:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 #include &amp;quot;subsystems/navigation/OSAMNav.h&amp;quot;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
'''NOTE''' The latest version of PaparazziUAV (v5.10 is the one I am using at the moment) does not have the OSAM navigation contributions as a subsystem but a module. It can be found in the link mentioned below. Not sure from which version the changes apply, but if you cannot find the header file in the subsystems folder, it is most probably in the modules folder.&lt;br /&gt;
&lt;br /&gt;
  sw/airborne/modules/nav&lt;br /&gt;
&lt;br /&gt;
== Flower ==&lt;br /&gt;
[[Image:FlowerScreenShot.png|thumb|Screen shot of flower routine]]&lt;br /&gt;
The flower navigation routine flies the aircraft in a flower pattern defined by two waypoints. The center waypoint defines the center of the flower and the altitude the plane flies at. The edge waypoint defines the radius of the flower.&lt;br /&gt;
&lt;br /&gt;
In our example the waypoints are called &amp;quot;Center&amp;quot; and &amp;quot;Edge&amp;quot;:&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;waypoint name=&amp;quot;Center&amp;quot; x=&amp;quot;-20.0&amp;quot; y=&amp;quot;-160.0&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;waypoint name=&amp;quot;Edge&amp;quot; x=&amp;quot;-10.0&amp;quot; y=&amp;quot;-60.0&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
Then you can add flower to your flight plan:&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;block name=&amp;quot;Flower&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;call fun=&amp;quot;InitializeFlower(WP_Center,WP_Edge)&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;call fun=&amp;quot;FlowerNav()&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
Note that in the function InitializeFlower the waypoints need the prefix &amp;quot;WP_&amp;quot;.&lt;br /&gt;
&lt;br /&gt;
== Bungee Takeoff ==&lt;br /&gt;
&lt;br /&gt;
The bungee takeoff routine helps to automate takeoff by turning the throttle on after the bungee has been release from the hook. The only waypoint you need for this routine is the position of where the bungee is pegged to the ground. Using this waypoint, a line is drawn from the position of the aircraft to the bungee waypoint. This line is called the launch line and will stop updating once the speed of the plane exceeds the MinSpeed. This allows the user to initialize the routine, move the plane and launch it without having to reinitialize. Once the plane is launched, it will follow the launch line until it crosses the throttle line. The throttle line is a line perpendicular to the launch line at a distance d from the bungee waypoint (see the diagram below). When the plane crosses the throttle line and the speed of the aircraft is greater than MinSpeed, the throttle comes on. After the throttle comes on, the plane keeps going straight until it reaches a specified speed and altitude above the bungee waypoint altitude. When it reaches the takeoff speed and takeoff altitude, the next block in the flight plan is executed. The takeoff speed, takeoff altitude, MinSpeed and the distance d from the bungee waypoint are specified in the airframe file. You will need to add those values to your airframe file like this...&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/airframes/myAircraft.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;section name=&amp;quot;Takeoff&amp;quot; prefix=&amp;quot;Takeoff_&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;Height&amp;quot; value=&amp;quot;30&amp;quot; unit=&amp;quot;m&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;Speed&amp;quot; value=&amp;quot;15&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;Distance&amp;quot; value=&amp;quot;3&amp;quot; unit=&amp;quot;m&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;MinSpeed&amp;quot; value=&amp;quot;5&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;    &lt;br /&gt;
  &amp;lt;/section&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
You can add the bungee takeoff routine to your flight plan like so...&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;block name=&amp;quot;Takeoff&amp;quot; strip_button=&amp;quot;Takeoff (wp CLIMB)&amp;quot; strip_icon=&amp;quot;takeoff.png&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;call fun=&amp;quot;InitializeBungeeTakeoff(WP_Bungee)&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;call fun=&amp;quot;BungeeTakeoff()&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
To get this routine to work consistently, you will need to tune the values in the airframe config file. If the prop doesn't automatically turn on when it crosses the throttle line, it could be because the Distance and/or the MinSpeed are too big. If it turns on to early, it could be because the Distance and/or MinSpeed are too small. &lt;br /&gt;
&lt;br /&gt;
&amp;lt;span style=&amp;quot;color:#ff0000&amp;quot;&amp;gt; ***Precaution should be taken while tuning the auto takeoff with electrical plane. If the MinSpeed is too low, the prop could turn on while holding the aircraft!***&amp;lt;/span&amp;gt; &lt;br /&gt;
&lt;br /&gt;
&amp;lt;gallery&amp;gt;&lt;br /&gt;
Image:BungeeTakeoffDiagram.png|Bungee takeoff diagram&lt;br /&gt;
Image:BungeeTakeoffInit.png|After bungee takeoff initialization&lt;br /&gt;
Image:BungeeTakeoffThrottleOn.png|After crossing the throttle line&lt;br /&gt;
&amp;lt;/gallery&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Polygon Survey ==&lt;br /&gt;
=== Explanation ===&lt;br /&gt;
With this navigation routine, an aircraft can survey the area of any [http://en.wikipedia.org/wiki/Convex_polygon convex polygon] given an entry point, the number of waypoints which define the polygon, the sweep width and the desired orientation of the sweeps.&lt;br /&gt;
&lt;br /&gt;
The entry point is the first corner of the polygon and the point at which the aircraft will begin surveying the area. When in the entry state, the aircraft will circle around the entry point in order to smoothly transition into the first sweep. The aircraft will also keep circling around the entry point until it gets to the waypoint altitude. After the first sweep is made, the direction of the next sweep is determined by the distance of the entry point to the edges of the polygon. If there is more area above the first sweep, the aircraft will sweep up. If there is more area below the first sweep, the aircraft will sweep down.&lt;br /&gt;
&lt;br /&gt;
The aircraft will keep sweeping back and forth until it reaches the end of the polygon. At this point, the aircraft will sweep back up/down the polygon halfway in between the sweeps previously made by the aircraft (just like the rectangle survey function). The aircraft will keep sweeping up and down the polygon unless the user manually exits the block or unless an exception is used ([[#Exceptions|see below]]).&lt;br /&gt;
&lt;br /&gt;
The orientation of the sweeps can ranges from north south to east west and any where in between (-90 &amp;lt;-&amp;gt; 90 degrees respectively). The side of the polygon the aircraft starts on (ex. north or south)  is determined by the side of the polygon the entry point is located.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;gallery&amp;gt;&lt;br /&gt;
Image:PolySurveySweepDef.png|Sweep Definition&lt;br /&gt;
Image:PolySurveyEntryPic.png|Entry Point&lt;br /&gt;
Image:PolySurveySweepBack.png|Sweeping Back&lt;br /&gt;
&amp;lt;/gallery&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Implementation ====&lt;br /&gt;
&lt;br /&gt;
You can add this navigation routine in your flight plan like so... &lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Poly Survey&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;InitializePolygonSurvey(WP_S1, NumOfCorners, SweepWidth, Orientation)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;PolygonSurvey()&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
The parameters are the entry waypoint, the number of waypoints in the polygon, the sweep width (meters), and the desired orientation of the sweeps (degrees). The maximum number of waypoints a polygon can have is currently ten (can be changed in the code). If the number of waypoints in the polygon exceeds the maximum number, the routine will exit and move to the next block in the flight plan. The routine will also exit if the orientation is not between -90 and 90 degrees.&lt;br /&gt;
&lt;br /&gt;
Here is an example of how you should declare each of the corners of the polygon.&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
   &amp;lt;waypoint alt=&amp;quot;1453.0&amp;quot; name=&amp;quot;S1&amp;quot; x=&amp;quot;-546.2&amp;quot; y=&amp;quot;297.4&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;waypoint alt=&amp;quot;1453.0&amp;quot; name=&amp;quot;S2&amp;quot; x=&amp;quot;-129.8&amp;quot; y=&amp;quot;744.1&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;waypoint alt=&amp;quot;1553.0&amp;quot; name=&amp;quot;S3&amp;quot; x=&amp;quot;1030.5&amp;quot; y=&amp;quot;535.5&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;waypoint alt=&amp;quot;1453.0&amp;quot; name=&amp;quot;S4&amp;quot; x=&amp;quot;523.0&amp;quot; y=&amp;quot;-236.7&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;waypoint alt=&amp;quot;1453.0&amp;quot; name=&amp;quot;S5&amp;quot; x=&amp;quot;-285.9&amp;quot; y=&amp;quot;-255.7&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
S1 is the entry waypoint and the first corner. The other corners should be in order clockwise or counter clockwise around the polygon. Even though this group of waypoints must be declared together, where the group appears in the list of waypoints doesn't matter.&lt;br /&gt;
&lt;br /&gt;
If you want the edges of the polygon to show up on the GCS, you can also declare the polygon as a sector. This is not required to run the routine.&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;sectors&amp;gt;&lt;br /&gt;
    &amp;lt;sector name=&amp;quot;PolySector&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;S1&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;S2&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;S3&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;S4&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;S5&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/sector&amp;gt;&lt;br /&gt;
  &amp;lt;/sectors&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;gallery caption=&amp;quot;A Range of Different Sweep Orientations&amp;quot;&amp;gt;&lt;br /&gt;
Image:PolySurvey0DegreeEx.png|0 Degrees&lt;br /&gt;
Image:PolySurvey30DegreeEx.png|30 Degrees&lt;br /&gt;
Image:PolySurvey65DegreeEx.png|65 Degrees&lt;br /&gt;
Image:PolySurvey90DegreeEx.png|90 Degrees&lt;br /&gt;
&amp;lt;/gallery&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==== Alternative configurations ====&lt;br /&gt;
&lt;br /&gt;
If you are wanting to start and stop the Poly Survey this is possible by splitting the Poly Survey code above into the initialization routine and the execution routine. You might want to do this if you are searching for something inside the Poly Survey, think you have found it and then realized you haven't, so you want to continue the survey (not restart it). Using the example above, but with the initialisation and execution code separate:&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Init Poly Survey&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;InitializePolygonSurvey(WP_S1, NumOfCorners, SweepWidth, Orientation)&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Execute Poly Survey&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;PolygonSurvey()&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
==== Exceptions ====&lt;br /&gt;
There are a couple of built in variables which can be used to exit the routine with an exception. PolySurveySweepNum gives the number of sweeps the aircraft has made and PolySurveySweepBackNum gives the number of times the aircraft has gotten to the bottom of the polygon and swept back. The first example would deroute the aircraft to standby after the aircraft made it's second sweep. The second example would deroute the aircraft to standby before it starts to sweep back up the polygon for the first time.&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Poly Survey&amp;quot;&amp;gt;&lt;br /&gt;
       &amp;lt;exception cond=&amp;quot;PolySurveySweepNum &amp;gt;= 2&amp;quot; deroute=&amp;quot;Standby&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;InitializePolygonSurvey(WP_S1, 5, 200, 45)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;PolygonSurvey()&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Poly Survey&amp;quot;&amp;gt;&lt;br /&gt;
       &amp;lt;exception cond=&amp;quot;PolySurveySweepBackNum &amp;gt;= 1&amp;quot; deroute=&amp;quot;Standby&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;InitializePolygonSurvey(WP_S1, 5, 200, 45)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;PolygonSurvey()&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
=== Flight Line ===&lt;br /&gt;
The Flight Line Routine allows the user to map/follow one dimensional areas of interest like roads and rivers. Given two waypoints, the routine will automatically transition into the flight line to ensure full coverage between the waypoints. In addition, distances before and after the flight line can be used to add extra security to the coverage.&lt;br /&gt;
&lt;br /&gt;
[[Image:OSAMFlightLineDiagram.png|Flight Line Diagram]]&lt;br /&gt;
&lt;br /&gt;
To use this navigation routine, you need to include OSAMNav.h in your flight plan and OSAMNav.c to your airframe file. Then add this navigation routine in your flight plan like so... &lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Map River&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;FlightLine(WP_R1,WP_R2,nav_radius,distance_before,distance_after)&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
Multiple flight lines can be daisy chained by reusing waypoints as shown below...&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Map River&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;FlightLine(WP_R1,WP_R2,nav_radius,100,100)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;FlightLine(WP_R2,WP_R3,nav_radius,100,100)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;FlightLine(WP_R3,WP_R4,nav_radius,100,100)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;FlightLine(WP_R5,WP_R6,nav_radius,100,100)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;deroute block=&amp;quot;Standby&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
However, the previous block can also be implemented using the FlightLineBlock function. The FlightLineBlock function works the same as the FlightLine function except it automatically steps through the waypoints between the given waypoints. Make sure the waypoints are declared in order or else it won't work!&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
   &amp;lt;block name=&amp;quot;Map River&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;FlightLineBlock(WP_R1,WP_R6,nav_radius,100,100)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;deroute block=&amp;quot;Standby&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;gallery&amp;gt;&lt;br /&gt;
Image:OSAMFlightLineExample.jpg |Multiple Flight Line Example&lt;br /&gt;
&amp;lt;/gallery&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== misc ==&lt;br /&gt;
&lt;br /&gt;
=== Border line ===&lt;br /&gt;
&lt;br /&gt;
border_line is a nav-routine pretty similar to the nav-line-routine. You can use this nav-routine whenever you want to take care your plane stays on a defined site of a border.&lt;br /&gt;
For example you can use this routine to fly along a mountain and always turn away from the mountain ridge wall. Or use it fly along a border road without penetrating the other side of the border.&lt;br /&gt;
&lt;br /&gt;
Use &amp;quot;extra&amp;quot; navigation subsystem with:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;subsystem name=&amp;quot;navigation&amp;quot; type=&amp;quot;extra&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
If you want to use waypoint 1 and 2 you can add border_line in your flight plan like this:&lt;br /&gt;
* Include header in &amp;quot;header&amp;quot; section at the beginning&lt;br /&gt;
 #include &amp;quot;subsystems/navigation/border_line.h&amp;quot;&lt;br /&gt;
* Add function in a flight plan block:&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block group=&amp;quot;extra_pattern&amp;quot; name=&amp;quot;border line&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;border_line_init()&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;border_line(WP_1, WP_2, -nav_radius)&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&amp;lt;gallery caption=&amp;quot;example&amp;quot;&amp;gt;&lt;br /&gt;
Image:border_line.png|Screen shot of border_line&lt;br /&gt;
Image:border_line2.png|Screen shot of border_line2&lt;br /&gt;
Image:border_line3.png|Screen shot of border_line3&lt;br /&gt;
&amp;lt;/gallery&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== GLS ===&lt;br /&gt;
&lt;br /&gt;
GLS or  '''G'''lobal Navigation Satellite System (GNSS) '''L'''anding '''S'''ystem adds advanced landing functions to your flightplan&lt;br /&gt;
&lt;br /&gt;
It add the following capabilities:&lt;br /&gt;
&lt;br /&gt;
# Fly via defined glide path angle&lt;br /&gt;
# In flight changeable landing direction without loosing the glide path angle!&lt;br /&gt;
# Smooth intercept, independent of approach angle or wind&lt;br /&gt;
# Separation of '''a'''pproach '''f'''ix, '''s'''tart '''d'''ecent and '''t'''op '''o'''f '''d'''ecent&lt;br /&gt;
# With fixed target speed (in airspeed mode only)&lt;br /&gt;
&lt;br /&gt;
====GLS related abbreviations====&lt;br /&gt;
&lt;br /&gt;
* GLS = '''G'''lobal Navigation Satellite System (GNSS) '''L'''anding '''S'''ystem&lt;br /&gt;
* TOD = '''t'''op '''o'''f '''d'''ecent&lt;br /&gt;
* AF  = '''A'''pproach '''Fix'''&lt;br /&gt;
* SD  = '''S'''tart '''D'''ecend&lt;br /&gt;
* TD  = '''T'''ouch '''D'''own point, The spot where the plane should touch the ground for landing&lt;br /&gt;
&lt;br /&gt;
====Configure====&lt;br /&gt;
&lt;br /&gt;
What to add to your airframe.&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;section name=&amp;quot;GLS_APPROACH&amp;quot; prefix=&amp;quot;APP_&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;ANGLE&amp;quot; value=&amp;quot;5&amp;quot; unit=&amp;quot;deg&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;INTERCEPT_RATE&amp;quot; value=&amp;quot;0.624&amp;quot; unit=&amp;quot;m/s/s&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;DISTANCE_AF_SD&amp;quot; value=&amp;quot;20&amp;quot; unit=&amp;quot;m&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;TARGET_SPEED&amp;quot; value=&amp;quot;14&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/section&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
ANGLE                   - angle from TOD to TD&lt;br /&gt;
&lt;br /&gt;
DISTANCE_AF_SD  - minimum distance (meter) between AF and SD to allow the plane to self stabilize before the intercept starts (e.g. for speed reduction)&lt;br /&gt;
&lt;br /&gt;
You can set the landing direction by moving the approach fix (AF) in relation to the touch down point (TD).&lt;br /&gt;
If you try to set the AF close to the TD  you will see how the top of decent (TOD) and start decent (SD) is calculated and if necessary the AF is moved backwards.&lt;br /&gt;
(please try in simulation)&lt;br /&gt;
&lt;br /&gt;
TARGET_SPEED      - desired airspeed from AF to TD &lt;br /&gt;
&lt;br /&gt;
INTERCEPT_RATE   -&lt;br /&gt;
&lt;br /&gt;
e.g. no wind: TARGET_SPEED = 14m/s and ANGLE = 10 --&amp;gt; desired decent rate 2.5 m/s    (speed * tan(ANGLE))&lt;br /&gt;
&lt;br /&gt;
with an INTERCEPT_RATE of 0.624 m/s/s it will take 4s to intercept the final approach path (desired decent rate / intercept_rate)&lt;br /&gt;
&lt;br /&gt;
the idea is that the INTERCEPT_RATE is unique to each plane and will not change with different approach angles&lt;br /&gt;
&lt;br /&gt;
to find an appropriate value you can start with a lower (to match 8s for example) and increase it until the intercept will be made from above&lt;br /&gt;
&lt;br /&gt;
in general: bigger plane - smaller value!&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
how to setup your flightplan.xml:&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;waypoints&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint height=&amp;quot;150&amp;quot; name=&amp;quot;AF&amp;quot; x=&amp;quot;-260.6&amp;quot; y=&amp;quot;-344.6&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;SD&amp;quot; x=&amp;quot;-1600.&amp;quot; y=&amp;quot;-36.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;TOD&amp;quot; x=&amp;quot;-1600.&amp;quot; y=&amp;quot;-36.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint height=&amp;quot;0.0&amp;quot; name=&amp;quot;TD&amp;quot; x=&amp;quot;-27.2&amp;quot; y=&amp;quot;-243.5&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint height=&amp;quot;266.0&amp;quot; name=&amp;quot;_BASELEG&amp;quot; x=&amp;quot;-1652.1&amp;quot; y=&amp;quot;-113.5&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/waypoints&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
    &amp;lt;block name=&amp;quot;land&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;gls_init(WP_AF,WP_SD, WP_TOD, WP_TD)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;nav_compute_baseleg(WP_AF, WP_TD, WP__BASELEG, nav_radius)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;circle radius=&amp;quot;nav_radius&amp;quot; until=&amp;quot;NavCircleCount() &amp;gt; 0.5&amp;quot; wp=&amp;quot;_BASELEG&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;circle radius=&amp;quot;nav_radius&amp;quot; until=&amp;quot;And(NavQdrCloseTo(DegOfRad(baseleg_out_qdr)-(nav_radius/fabs(nav_radius))*10),&lt;br /&gt;
                               10 &amp;gt; fabs(GetPosAlt() - WaypointAlt(WP__BASELEG)))&amp;quot; wp=&amp;quot;_BASELEG&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&lt;br /&gt;
    &amp;lt;block name=&amp;quot;final&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;exception cond=&amp;quot;ground_alt + 10 &amp;gt; estimator_z&amp;quot; deroute=&amp;quot;flare&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;gls(WP_AF,WP_SD, WP_TOD, WP_TD)&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
those pictures match the old gls routine! anyway - the new one is not much different... (POS I = SD)&lt;br /&gt;
&amp;lt;gallery caption=&amp;quot;theory&amp;quot;&amp;gt;&lt;br /&gt;
Image:gls1.png|side view&lt;br /&gt;
Image:gls2.png|from above&lt;br /&gt;
Image:gls3.png|screen shot of flight test&lt;br /&gt;
&amp;lt;/gallery&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Multi-UAV ==&lt;br /&gt;
For TCAS (Traffic Collision Avoidance System) see the [[MultiUAV]] page.&lt;br /&gt;
&lt;br /&gt;
[[Category:Software]] [[Category:Navigation]] [[Category:User_Documentation]]&lt;br /&gt;
&lt;br /&gt;
= Create a navigation module =&lt;br /&gt;
&lt;br /&gt;
Creating a navigation module is not to complex. Have said that, it is not very likely to need to create one module oneself. The already available functions are very flexible and powerful. Before you set of to create and additional navigation module, make sure you understand all current modules and their capabilities. After you investigated current modules and came to the conclusion, there is no way to solve you flightplan mission by creating a new module, go ahead and plz share your work with the community. The more people test the new module, the faster it will reach a stable state.&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Advanced_Navigation_Routines&amp;diff=23640</id>
		<title>Advanced Navigation Routines</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Advanced_Navigation_Routines&amp;diff=23640"/>
		<updated>2017-03-29T13:52:40Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: /* Navigation Routines (Prev.OSAM) */  : put a note mentioning that the newer versions of PaparazziUAV does not OSAM as a subsystem but a module&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;= Introduction =&lt;br /&gt;
&lt;br /&gt;
The flight plan standard navigation functions are very flexible. However sometimes one needs to perform a very specific task, and the basic functions are not enough to accomplish a special mission. In that case you can use additional modules functions in the flight plan. By adding a navigation capability to your airframe. The flight plan now has extra functionality that can be used.&lt;br /&gt;
&lt;br /&gt;
= Available navigation modules =&lt;br /&gt;
&lt;br /&gt;
==  Navigation Routines (Prev.OSAM) ==&lt;br /&gt;
&lt;br /&gt;
Thanks to Team OSAM's contribution these navigation capabilities have been added.&lt;br /&gt;
&lt;br /&gt;
To use these navigation routines, you need to change the navigation subsystem type to extra in your airframe file. The navigation extra subsystem includes extra navigation routines like OSAMnav, spiral, poly_survey_advanced, nav_cube, etc.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;subsystem name=&amp;quot;navigation&amp;quot; type=&amp;quot;extra&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Also include OSAMNav.h in your flight plan:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 #include &amp;quot;subsystems/navigation/OSAMNav.h&amp;quot;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
'''NOTE''' The latest version of PaparazziUAV (v5.10 is the one I am using at the moment) does not have the OSAM navigation contributions as a subsystem but a module. Not sure from which version the changes apply, but if you cannot find the header file in the subsystems folder, it is most probably in the modules folder.&lt;br /&gt;
&lt;br /&gt;
== Flower ==&lt;br /&gt;
[[Image:FlowerScreenShot.png|thumb|Screen shot of flower routine]]&lt;br /&gt;
The flower navigation routine flies the aircraft in a flower pattern defined by two waypoints. The center waypoint defines the center of the flower and the altitude the plane flies at. The edge waypoint defines the radius of the flower.&lt;br /&gt;
&lt;br /&gt;
In our example the waypoints are called &amp;quot;Center&amp;quot; and &amp;quot;Edge&amp;quot;:&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;waypoint name=&amp;quot;Center&amp;quot; x=&amp;quot;-20.0&amp;quot; y=&amp;quot;-160.0&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;waypoint name=&amp;quot;Edge&amp;quot; x=&amp;quot;-10.0&amp;quot; y=&amp;quot;-60.0&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
Then you can add flower to your flight plan:&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;block name=&amp;quot;Flower&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;call fun=&amp;quot;InitializeFlower(WP_Center,WP_Edge)&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;call fun=&amp;quot;FlowerNav()&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
Note that in the function InitializeFlower the waypoints need the prefix &amp;quot;WP_&amp;quot;.&lt;br /&gt;
&lt;br /&gt;
== Bungee Takeoff ==&lt;br /&gt;
&lt;br /&gt;
The bungee takeoff routine helps to automate takeoff by turning the throttle on after the bungee has been release from the hook. The only waypoint you need for this routine is the position of where the bungee is pegged to the ground. Using this waypoint, a line is drawn from the position of the aircraft to the bungee waypoint. This line is called the launch line and will stop updating once the speed of the plane exceeds the MinSpeed. This allows the user to initialize the routine, move the plane and launch it without having to reinitialize. Once the plane is launched, it will follow the launch line until it crosses the throttle line. The throttle line is a line perpendicular to the launch line at a distance d from the bungee waypoint (see the diagram below). When the plane crosses the throttle line and the speed of the aircraft is greater than MinSpeed, the throttle comes on. After the throttle comes on, the plane keeps going straight until it reaches a specified speed and altitude above the bungee waypoint altitude. When it reaches the takeoff speed and takeoff altitude, the next block in the flight plan is executed. The takeoff speed, takeoff altitude, MinSpeed and the distance d from the bungee waypoint are specified in the airframe file. You will need to add those values to your airframe file like this...&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/airframes/myAircraft.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;section name=&amp;quot;Takeoff&amp;quot; prefix=&amp;quot;Takeoff_&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;Height&amp;quot; value=&amp;quot;30&amp;quot; unit=&amp;quot;m&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;Speed&amp;quot; value=&amp;quot;15&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;Distance&amp;quot; value=&amp;quot;3&amp;quot; unit=&amp;quot;m&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;MinSpeed&amp;quot; value=&amp;quot;5&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;    &lt;br /&gt;
  &amp;lt;/section&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
You can add the bungee takeoff routine to your flight plan like so...&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;block name=&amp;quot;Takeoff&amp;quot; strip_button=&amp;quot;Takeoff (wp CLIMB)&amp;quot; strip_icon=&amp;quot;takeoff.png&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;call fun=&amp;quot;InitializeBungeeTakeoff(WP_Bungee)&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;call fun=&amp;quot;BungeeTakeoff()&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
To get this routine to work consistently, you will need to tune the values in the airframe config file. If the prop doesn't automatically turn on when it crosses the throttle line, it could be because the Distance and/or the MinSpeed are too big. If it turns on to early, it could be because the Distance and/or MinSpeed are too small. &lt;br /&gt;
&lt;br /&gt;
&amp;lt;span style=&amp;quot;color:#ff0000&amp;quot;&amp;gt; ***Precaution should be taken while tuning the auto takeoff with electrical plane. If the MinSpeed is too low, the prop could turn on while holding the aircraft!***&amp;lt;/span&amp;gt; &lt;br /&gt;
&lt;br /&gt;
&amp;lt;gallery&amp;gt;&lt;br /&gt;
Image:BungeeTakeoffDiagram.png|Bungee takeoff diagram&lt;br /&gt;
Image:BungeeTakeoffInit.png|After bungee takeoff initialization&lt;br /&gt;
Image:BungeeTakeoffThrottleOn.png|After crossing the throttle line&lt;br /&gt;
&amp;lt;/gallery&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Polygon Survey ==&lt;br /&gt;
=== Explanation ===&lt;br /&gt;
With this navigation routine, an aircraft can survey the area of any [http://en.wikipedia.org/wiki/Convex_polygon convex polygon] given an entry point, the number of waypoints which define the polygon, the sweep width and the desired orientation of the sweeps.&lt;br /&gt;
&lt;br /&gt;
The entry point is the first corner of the polygon and the point at which the aircraft will begin surveying the area. When in the entry state, the aircraft will circle around the entry point in order to smoothly transition into the first sweep. The aircraft will also keep circling around the entry point until it gets to the waypoint altitude. After the first sweep is made, the direction of the next sweep is determined by the distance of the entry point to the edges of the polygon. If there is more area above the first sweep, the aircraft will sweep up. If there is more area below the first sweep, the aircraft will sweep down.&lt;br /&gt;
&lt;br /&gt;
The aircraft will keep sweeping back and forth until it reaches the end of the polygon. At this point, the aircraft will sweep back up/down the polygon halfway in between the sweeps previously made by the aircraft (just like the rectangle survey function). The aircraft will keep sweeping up and down the polygon unless the user manually exits the block or unless an exception is used ([[#Exceptions|see below]]).&lt;br /&gt;
&lt;br /&gt;
The orientation of the sweeps can ranges from north south to east west and any where in between (-90 &amp;lt;-&amp;gt; 90 degrees respectively). The side of the polygon the aircraft starts on (ex. north or south)  is determined by the side of the polygon the entry point is located.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;gallery&amp;gt;&lt;br /&gt;
Image:PolySurveySweepDef.png|Sweep Definition&lt;br /&gt;
Image:PolySurveyEntryPic.png|Entry Point&lt;br /&gt;
Image:PolySurveySweepBack.png|Sweeping Back&lt;br /&gt;
&amp;lt;/gallery&amp;gt;&lt;br /&gt;
&lt;br /&gt;
==== Implementation ====&lt;br /&gt;
&lt;br /&gt;
You can add this navigation routine in your flight plan like so... &lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Poly Survey&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;InitializePolygonSurvey(WP_S1, NumOfCorners, SweepWidth, Orientation)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;PolygonSurvey()&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
The parameters are the entry waypoint, the number of waypoints in the polygon, the sweep width (meters), and the desired orientation of the sweeps (degrees). The maximum number of waypoints a polygon can have is currently ten (can be changed in the code). If the number of waypoints in the polygon exceeds the maximum number, the routine will exit and move to the next block in the flight plan. The routine will also exit if the orientation is not between -90 and 90 degrees.&lt;br /&gt;
&lt;br /&gt;
Here is an example of how you should declare each of the corners of the polygon.&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
   &amp;lt;waypoint alt=&amp;quot;1453.0&amp;quot; name=&amp;quot;S1&amp;quot; x=&amp;quot;-546.2&amp;quot; y=&amp;quot;297.4&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;waypoint alt=&amp;quot;1453.0&amp;quot; name=&amp;quot;S2&amp;quot; x=&amp;quot;-129.8&amp;quot; y=&amp;quot;744.1&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;waypoint alt=&amp;quot;1553.0&amp;quot; name=&amp;quot;S3&amp;quot; x=&amp;quot;1030.5&amp;quot; y=&amp;quot;535.5&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;waypoint alt=&amp;quot;1453.0&amp;quot; name=&amp;quot;S4&amp;quot; x=&amp;quot;523.0&amp;quot; y=&amp;quot;-236.7&amp;quot;/&amp;gt;&lt;br /&gt;
   &amp;lt;waypoint alt=&amp;quot;1453.0&amp;quot; name=&amp;quot;S5&amp;quot; x=&amp;quot;-285.9&amp;quot; y=&amp;quot;-255.7&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
S1 is the entry waypoint and the first corner. The other corners should be in order clockwise or counter clockwise around the polygon. Even though this group of waypoints must be declared together, where the group appears in the list of waypoints doesn't matter.&lt;br /&gt;
&lt;br /&gt;
If you want the edges of the polygon to show up on the GCS, you can also declare the polygon as a sector. This is not required to run the routine.&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;sectors&amp;gt;&lt;br /&gt;
    &amp;lt;sector name=&amp;quot;PolySector&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;S1&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;S2&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;S3&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;S4&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;corner name=&amp;quot;S5&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/sector&amp;gt;&lt;br /&gt;
  &amp;lt;/sectors&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;gallery caption=&amp;quot;A Range of Different Sweep Orientations&amp;quot;&amp;gt;&lt;br /&gt;
Image:PolySurvey0DegreeEx.png|0 Degrees&lt;br /&gt;
Image:PolySurvey30DegreeEx.png|30 Degrees&lt;br /&gt;
Image:PolySurvey65DegreeEx.png|65 Degrees&lt;br /&gt;
Image:PolySurvey90DegreeEx.png|90 Degrees&lt;br /&gt;
&amp;lt;/gallery&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
==== Alternative configurations ====&lt;br /&gt;
&lt;br /&gt;
If you are wanting to start and stop the Poly Survey this is possible by splitting the Poly Survey code above into the initialization routine and the execution routine. You might want to do this if you are searching for something inside the Poly Survey, think you have found it and then realized you haven't, so you want to continue the survey (not restart it). Using the example above, but with the initialisation and execution code separate:&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Init Poly Survey&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;InitializePolygonSurvey(WP_S1, NumOfCorners, SweepWidth, Orientation)&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Execute Poly Survey&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;PolygonSurvey()&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
==== Exceptions ====&lt;br /&gt;
There are a couple of built in variables which can be used to exit the routine with an exception. PolySurveySweepNum gives the number of sweeps the aircraft has made and PolySurveySweepBackNum gives the number of times the aircraft has gotten to the bottom of the polygon and swept back. The first example would deroute the aircraft to standby after the aircraft made it's second sweep. The second example would deroute the aircraft to standby before it starts to sweep back up the polygon for the first time.&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Poly Survey&amp;quot;&amp;gt;&lt;br /&gt;
       &amp;lt;exception cond=&amp;quot;PolySurveySweepNum &amp;gt;= 2&amp;quot; deroute=&amp;quot;Standby&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;InitializePolygonSurvey(WP_S1, 5, 200, 45)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;PolygonSurvey()&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Poly Survey&amp;quot;&amp;gt;&lt;br /&gt;
       &amp;lt;exception cond=&amp;quot;PolySurveySweepBackNum &amp;gt;= 1&amp;quot; deroute=&amp;quot;Standby&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;InitializePolygonSurvey(WP_S1, 5, 200, 45)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;PolygonSurvey()&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
=== Flight Line ===&lt;br /&gt;
The Flight Line Routine allows the user to map/follow one dimensional areas of interest like roads and rivers. Given two waypoints, the routine will automatically transition into the flight line to ensure full coverage between the waypoints. In addition, distances before and after the flight line can be used to add extra security to the coverage.&lt;br /&gt;
&lt;br /&gt;
[[Image:OSAMFlightLineDiagram.png|Flight Line Diagram]]&lt;br /&gt;
&lt;br /&gt;
To use this navigation routine, you need to include OSAMNav.h in your flight plan and OSAMNav.c to your airframe file. Then add this navigation routine in your flight plan like so... &lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Map River&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;FlightLine(WP_R1,WP_R2,nav_radius,distance_before,distance_after)&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
Multiple flight lines can be daisy chained by reusing waypoints as shown below...&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block name=&amp;quot;Map River&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;FlightLine(WP_R1,WP_R2,nav_radius,100,100)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;FlightLine(WP_R2,WP_R3,nav_radius,100,100)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;FlightLine(WP_R3,WP_R4,nav_radius,100,100)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;FlightLine(WP_R5,WP_R6,nav_radius,100,100)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;deroute block=&amp;quot;Standby&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
However, the previous block can also be implemented using the FlightLineBlock function. The FlightLineBlock function works the same as the FlightLine function except it automatically steps through the waypoints between the given waypoints. Make sure the waypoints are declared in order or else it won't work!&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
   &amp;lt;block name=&amp;quot;Map River&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;FlightLineBlock(WP_R1,WP_R6,nav_radius,100,100)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;deroute block=&amp;quot;Standby&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
&amp;lt;gallery&amp;gt;&lt;br /&gt;
Image:OSAMFlightLineExample.jpg |Multiple Flight Line Example&lt;br /&gt;
&amp;lt;/gallery&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== misc ==&lt;br /&gt;
&lt;br /&gt;
=== Border line ===&lt;br /&gt;
&lt;br /&gt;
border_line is a nav-routine pretty similar to the nav-line-routine. You can use this nav-routine whenever you want to take care your plane stays on a defined site of a border.&lt;br /&gt;
For example you can use this routine to fly along a mountain and always turn away from the mountain ridge wall. Or use it fly along a border road without penetrating the other side of the border.&lt;br /&gt;
&lt;br /&gt;
Use &amp;quot;extra&amp;quot; navigation subsystem with:&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;subsystem name=&amp;quot;navigation&amp;quot; type=&amp;quot;extra&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
If you want to use waypoint 1 and 2 you can add border_line in your flight plan like this:&lt;br /&gt;
* Include header in &amp;quot;header&amp;quot; section at the beginning&lt;br /&gt;
 #include &amp;quot;subsystems/navigation/border_line.h&amp;quot;&lt;br /&gt;
* Add function in a flight plan block:&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;block group=&amp;quot;extra_pattern&amp;quot; name=&amp;quot;border line&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;border_line_init()&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;border_line(WP_1, WP_2, -nav_radius)&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&amp;lt;gallery caption=&amp;quot;example&amp;quot;&amp;gt;&lt;br /&gt;
Image:border_line.png|Screen shot of border_line&lt;br /&gt;
Image:border_line2.png|Screen shot of border_line2&lt;br /&gt;
Image:border_line3.png|Screen shot of border_line3&lt;br /&gt;
&amp;lt;/gallery&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
=== GLS ===&lt;br /&gt;
&lt;br /&gt;
GLS or  '''G'''lobal Navigation Satellite System (GNSS) '''L'''anding '''S'''ystem adds advanced landing functions to your flightplan&lt;br /&gt;
&lt;br /&gt;
It add the following capabilities:&lt;br /&gt;
&lt;br /&gt;
# Fly via defined glide path angle&lt;br /&gt;
# In flight changeable landing direction without loosing the glide path angle!&lt;br /&gt;
# Smooth intercept, independent of approach angle or wind&lt;br /&gt;
# Separation of '''a'''pproach '''f'''ix, '''s'''tart '''d'''ecent and '''t'''op '''o'''f '''d'''ecent&lt;br /&gt;
# With fixed target speed (in airspeed mode only)&lt;br /&gt;
&lt;br /&gt;
====GLS related abbreviations====&lt;br /&gt;
&lt;br /&gt;
* GLS = '''G'''lobal Navigation Satellite System (GNSS) '''L'''anding '''S'''ystem&lt;br /&gt;
* TOD = '''t'''op '''o'''f '''d'''ecent&lt;br /&gt;
* AF  = '''A'''pproach '''Fix'''&lt;br /&gt;
* SD  = '''S'''tart '''D'''ecend&lt;br /&gt;
* TD  = '''T'''ouch '''D'''own point, The spot where the plane should touch the ground for landing&lt;br /&gt;
&lt;br /&gt;
====Configure====&lt;br /&gt;
&lt;br /&gt;
What to add to your airframe.&lt;br /&gt;
&lt;br /&gt;
{{Box Code|conf/flight_plans/myflightplan.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;section name=&amp;quot;GLS_APPROACH&amp;quot; prefix=&amp;quot;APP_&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;ANGLE&amp;quot; value=&amp;quot;5&amp;quot; unit=&amp;quot;deg&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;INTERCEPT_RATE&amp;quot; value=&amp;quot;0.624&amp;quot; unit=&amp;quot;m/s/s&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;DISTANCE_AF_SD&amp;quot; value=&amp;quot;20&amp;quot; unit=&amp;quot;m&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;define name=&amp;quot;TARGET_SPEED&amp;quot; value=&amp;quot;14&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/section&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
ANGLE                   - angle from TOD to TD&lt;br /&gt;
&lt;br /&gt;
DISTANCE_AF_SD  - minimum distance (meter) between AF and SD to allow the plane to self stabilize before the intercept starts (e.g. for speed reduction)&lt;br /&gt;
&lt;br /&gt;
You can set the landing direction by moving the approach fix (AF) in relation to the touch down point (TD).&lt;br /&gt;
If you try to set the AF close to the TD  you will see how the top of decent (TOD) and start decent (SD) is calculated and if necessary the AF is moved backwards.&lt;br /&gt;
(please try in simulation)&lt;br /&gt;
&lt;br /&gt;
TARGET_SPEED      - desired airspeed from AF to TD &lt;br /&gt;
&lt;br /&gt;
INTERCEPT_RATE   -&lt;br /&gt;
&lt;br /&gt;
e.g. no wind: TARGET_SPEED = 14m/s and ANGLE = 10 --&amp;gt; desired decent rate 2.5 m/s    (speed * tan(ANGLE))&lt;br /&gt;
&lt;br /&gt;
with an INTERCEPT_RATE of 0.624 m/s/s it will take 4s to intercept the final approach path (desired decent rate / intercept_rate)&lt;br /&gt;
&lt;br /&gt;
the idea is that the INTERCEPT_RATE is unique to each plane and will not change with different approach angles&lt;br /&gt;
&lt;br /&gt;
to find an appropriate value you can start with a lower (to match 8s for example) and increase it until the intercept will be made from above&lt;br /&gt;
&lt;br /&gt;
in general: bigger plane - smaller value!&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
how to setup your flightplan.xml:&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
  &amp;lt;waypoints&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint height=&amp;quot;150&amp;quot; name=&amp;quot;AF&amp;quot; x=&amp;quot;-260.6&amp;quot; y=&amp;quot;-344.6&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;SD&amp;quot; x=&amp;quot;-1600.&amp;quot; y=&amp;quot;-36.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint name=&amp;quot;TOD&amp;quot; x=&amp;quot;-1600.&amp;quot; y=&amp;quot;-36.&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint height=&amp;quot;0.0&amp;quot; name=&amp;quot;TD&amp;quot; x=&amp;quot;-27.2&amp;quot; y=&amp;quot;-243.5&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;waypoint height=&amp;quot;266.0&amp;quot; name=&amp;quot;_BASELEG&amp;quot; x=&amp;quot;-1652.1&amp;quot; y=&amp;quot;-113.5&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/waypoints&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
    &amp;lt;block name=&amp;quot;land&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;gls_init(WP_AF,WP_SD, WP_TOD, WP_TD)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;nav_compute_baseleg(WP_AF, WP_TD, WP__BASELEG, nav_radius)&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;circle radius=&amp;quot;nav_radius&amp;quot; until=&amp;quot;NavCircleCount() &amp;gt; 0.5&amp;quot; wp=&amp;quot;_BASELEG&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;circle radius=&amp;quot;nav_radius&amp;quot; until=&amp;quot;And(NavQdrCloseTo(DegOfRad(baseleg_out_qdr)-(nav_radius/fabs(nav_radius))*10),&lt;br /&gt;
                               10 &amp;gt; fabs(GetPosAlt() - WaypointAlt(WP__BASELEG)))&amp;quot; wp=&amp;quot;_BASELEG&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&lt;br /&gt;
    &amp;lt;block name=&amp;quot;final&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;exception cond=&amp;quot;ground_alt + 10 &amp;gt; estimator_z&amp;quot; deroute=&amp;quot;flare&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;call fun=&amp;quot;gls(WP_AF,WP_SD, WP_TOD, WP_TD)&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/block&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
those pictures match the old gls routine! anyway - the new one is not much different... (POS I = SD)&lt;br /&gt;
&amp;lt;gallery caption=&amp;quot;theory&amp;quot;&amp;gt;&lt;br /&gt;
Image:gls1.png|side view&lt;br /&gt;
Image:gls2.png|from above&lt;br /&gt;
Image:gls3.png|screen shot of flight test&lt;br /&gt;
&amp;lt;/gallery&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Multi-UAV ==&lt;br /&gt;
For TCAS (Traffic Collision Avoidance System) see the [[MultiUAV]] page.&lt;br /&gt;
&lt;br /&gt;
[[Category:Software]] [[Category:Navigation]] [[Category:User_Documentation]]&lt;br /&gt;
&lt;br /&gt;
= Create a navigation module =&lt;br /&gt;
&lt;br /&gt;
Creating a navigation module is not to complex. Have said that, it is not very likely to need to create one module oneself. The already available functions are very flexible and powerful. Before you set of to create and additional navigation module, make sure you understand all current modules and their capabilities. After you investigated current modules and came to the conclusion, there is no way to solve you flightplan mission by creating a new module, go ahead and plz share your work with the community. The more people test the new module, the faster it will reach a stable state.&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Talk:Telemetry&amp;diff=21102</id>
		<title>Talk:Telemetry</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Talk:Telemetry&amp;diff=21102"/>
		<updated>2016-03-15T17:25:48Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;The add messages section seems to be out dated for version 5.8. The AIRSPEED messages are already implemented. I tried to get this working for a module I made following the instructions but it did not work. I think they need to be updated. Also the &amp;quot;find_free_msg_id.out&amp;quot; was replaced by *.ml script which I could not use. --[[User:Lethargi|Lethargi]]&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Telemetry&amp;diff=21101</id>
		<title>Telemetry</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Telemetry&amp;diff=21101"/>
		<updated>2016-03-15T17:24:41Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: /* Add Messages */; changed the section introduction and included the information about making paparazzi again before the changes from messages.xml take effect.&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Messages ==&lt;br /&gt;
&lt;br /&gt;
Telemetry messages (sent from the aircraft to the ground) are defined in the telemetry class of [https://github.com/paparazzi/paparazzi/blob/master/conf/messages.xml conf/messages.xml].&lt;br /&gt;
See also the generated documentation: http://docs.paparazziuav.org/latest/paparazzi_messages.html&lt;br /&gt;
&lt;br /&gt;
== Sending periodic messages ==&lt;br /&gt;
The set of periodic messages sent over the downlink channel by an aircraft to the ground station is configurable&lt;br /&gt;
with the help of one XML file, located in the &amp;lt;tt&amp;gt;conf/telemetry&amp;lt;/tt&amp;gt; directory. This file is referenced by &amp;lt;tt&amp;gt;conf/conf.xml&amp;lt;/tt&amp;gt; and must follow the&lt;br /&gt;
&amp;lt;tt&amp;gt;telemetry.dtd&amp;lt;/tt&amp;gt; syntax. The &amp;lt;tt&amp;gt;fixedwing_default.xml&amp;lt;/tt&amp;gt; and &amp;lt;tt&amp;gt;rotorcraft_default.xml&amp;lt;/tt&amp;gt; are provided as an example and should be suitable for most users.&lt;br /&gt;
{{Box Code|default.xml|&lt;br /&gt;
 &amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;!DOCTYPE telemetry SYSTEM &amp;quot;telemetry.dtd&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;telemetry&amp;gt;&lt;br /&gt;
  &amp;lt;process name=&amp;quot;Ap&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;default&amp;quot;&amp;gt;&lt;br /&gt;
     &amp;lt;message name=&amp;quot;ATTITUDE&amp;quot; period=&amp;quot;0.5&amp;quot;/&amp;gt;&lt;br /&gt;
     &amp;lt;message name=&amp;quot;PPRZ_MODE&amp;quot; period=&amp;quot;5&amp;quot;/&amp;gt;&lt;br /&gt;
     &amp;lt;message name=&amp;quot;SOME_MODULE_MSG&amp;quot; period=&amp;quot;2&amp;quot; module=&amp;quot;module_name&amp;quot;/&amp;gt;&lt;br /&gt;
     ...&lt;br /&gt;
    &amp;lt;/mode&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;fast attitude&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;ATTITUDE&amp;quot; period=&amp;quot;0.1&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/mode&amp;gt;&lt;br /&gt;
 &amp;lt;/process&amp;gt;&lt;br /&gt;
  &amp;lt;process name=&amp;quot;Fbw&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;default&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;COMMANDS&amp;quot; period=&amp;quot;1&amp;quot;/&amp;gt;&lt;br /&gt;
      ...&lt;br /&gt;
    &amp;lt;/mode&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;debug&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;PPM&amp;quot; period=&amp;quot;0.5&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;/mode&amp;gt;&lt;br /&gt;
  &amp;lt;/process&amp;gt;&lt;br /&gt;
 &amp;lt;/telemetry&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
If a [[Modules|module]] attribute is specified for a message, it will be include in the telemetry only if the corresponding module is loaded.&lt;br /&gt;
&lt;br /&gt;
It is even possible to create your own telemetry XML definition. By the time you need that, it is highly likely you are already an advanced paparazzi user and know why you would and how you will.&lt;br /&gt;
&lt;br /&gt;
===Add Messages===&lt;br /&gt;
&lt;br /&gt;
This section provides instructions of an example case of how one would add a new message to Paparazzi and send the data to the ground station. The example is a little old and considers the addition of the AIRSPEED message, which is already present in newer versions of paparazzi. The user will have to implement her own message objects instead of the AIRSPEED message.&lt;br /&gt;
&lt;br /&gt;
==== Step 1 ====&lt;br /&gt;
&lt;br /&gt;
In conf/messages.xml add an airspeed message:&lt;br /&gt;
{{Box Code|conf/messages.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
   &amp;lt;message name=&amp;quot;AIRSPEED&amp;quot; id=&amp;quot;54&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;adc_airspeed&amp;quot; type=&amp;quot;uint16&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;estimator_airspeed&amp;quot;   type=&amp;quot;float&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;airspeed_setpoint&amp;quot;    type=&amp;quot;float&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;airspeed_controlled&amp;quot;  type=&amp;quot;float&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
    &amp;lt;field name=&amp;quot;groundspeed_setpoint&amp;quot; type=&amp;quot;float&amp;quot; unit=&amp;quot;m/s&amp;quot;/&amp;gt;&lt;br /&gt;
  &amp;lt;/message&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;}}&lt;br /&gt;
Where id=&amp;quot;54&amp;quot; has to be unique. To find an new ID to use there is a script file located at ${PAPARAZZI_HOME}/sw/tools/find_free_msg_id.out (yes it is really a script). &lt;br /&gt;
&lt;br /&gt;
 Type: ${PAPARAZZI_SRC}/sw/tools/find_msg_id.out &lt;br /&gt;
&lt;br /&gt;
NOTE: Be sure your Paparazzi source and home environment variables are set correctly in your shell [[Installation#Launching_the_Software]])&lt;br /&gt;
&lt;br /&gt;
Every field in the output is a variable from Paparazzi. The type must be the type of a variable in your code (ie. look in your code). Add your message along with the frequency to be sent over the messaging bus (AKA telemetry messages).&lt;br /&gt;
&lt;br /&gt;
After making the modifications to the messages.xml file, make your paparazzi again (i.e. cd ${PAPARAZZI_HOME} &amp;amp;&amp;amp; make) so that your changes to the messages.xml file are reflected in the paparazzi/var/include/messages.h file. This will create a DOWNLINK_SEND_AIRSPEED macro (in ${PAPARAZZI_HOME}/var/include/messages.h). If you do not make paparazzi, this macro will not be created.&lt;br /&gt;
&lt;br /&gt;
==== Step 2 ====&lt;br /&gt;
&lt;br /&gt;
Add a message to your telemetry file (for example conf/telemetry/default_fixedwing.xml). The message name in telemetry file usually match the message name in messages.xml file, but can be different or even group several messages.&lt;br /&gt;
{{Box Code|conf/telemetry/default.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;telemetry&amp;gt;&lt;br /&gt;
   &amp;lt;process name=&amp;quot;Ap&amp;quot;&amp;gt;&lt;br /&gt;
    &amp;lt;mode name=&amp;quot;default&amp;quot;&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;ALIVE&amp;quot;          period=&amp;quot;5&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;GPS&amp;quot;            period=&amp;quot;0.25&amp;quot;/&amp;gt;&lt;br /&gt;
      &amp;lt;message name=&amp;quot;AIRSPEED&amp;quot;       period=&amp;quot;1&amp;quot;/&amp;gt;&lt;br /&gt;
      ....&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
&lt;br /&gt;
The result is a generated file in ${PAPARAZZI_HOME}/var/aircrafts/&amp;lt;AC&amp;gt;/generated/periodic_telemetry.h which consist in a (static) scheduler to that calls specific functions.&lt;br /&gt;
&lt;br /&gt;
==== Step 3 ====&lt;br /&gt;
&lt;br /&gt;
Create a function in your C source file that will send your message(s) (using the generated DOWNLINK_SEND_* macros) and register it to the telemetry system so that it will be send automatically for you. You also need to include the header &amp;lt;tt&amp;gt;subsystems/datalink/telemetry.h&amp;lt;/tt&amp;gt;:&lt;br /&gt;
{{Box Code|firmware/fixedwing/autopilot.c|&lt;br /&gt;
&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
 ...&lt;br /&gt;
 #include &amp;quot;subsystems/datalink/telemetry.h&amp;quot;&lt;br /&gt;
&lt;br /&gt;
 static void send_airspeed(struct transport_tx *trans, struct link_device *dev)&lt;br /&gt;
 {&lt;br /&gt;
   pprz_msg_send_AIRSPEED(trans, dev, AC_ID,&lt;br /&gt;
                         &amp;amp;airspeed, &amp;amp;v_ctl_auto_airspeed_setpoint,&lt;br /&gt;
                         &amp;amp;v_ctl_auto_airspeed_controlled, &amp;amp;v_ctl_auto_groundspeed_setpoint);&lt;br /&gt;
 }&lt;br /&gt;
&lt;br /&gt;
 ...&lt;br /&gt;
 void autopilot_init(void) {&lt;br /&gt;
 ...&lt;br /&gt;
  register_periodic_telemetry(DefaultPeriodic, PPRZ_MSG_ID_AIRSPEED, send_airspeed);&lt;br /&gt;
 ...&lt;br /&gt;
 }&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
}}&lt;br /&gt;
where the second parameter in the register function is the id of the message (use the define &amp;lt;tt&amp;gt;PPRZ_MSG_ID_&amp;lt;MESSAGE_NAME&amp;gt;&amp;lt;/tt&amp;gt;).&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&amp;lt;div class=&amp;quot;toccolours mw-collapsible mw-collapsed&amp;quot; style=&amp;quot;width:800px&amp;quot;&amp;gt;&lt;br /&gt;
Prior to '''v5.0''':&lt;br /&gt;
&amp;lt;div class=&amp;quot;mw-collapsible-content&amp;quot;&amp;gt;Past Reference for Paparazzi v5.0 or older:&lt;br /&gt;
Create a PERIODIC_SEND_AIRSPEED with the following code in the firmware specific telemetry header file (In ap_downlink.h/fbw_downlink.h for fixedwing or telemetry.h for rotorcraft) :&lt;br /&gt;
{{Box Code|conf/telemetry/default.xml|&lt;br /&gt;
&amp;lt;source lang=&amp;quot;c&amp;quot;&amp;gt;&lt;br /&gt;
 #ifdef USE_AIRSPEED&lt;br /&gt;
 #define PERIODIC_SEND_AIRSPEED(_chan) DOWNLINK_SEND_AIRSPEED (_chan, _dev   &amp;amp;adc_airspeed_val,&amp;amp;estimator_airspeed,&amp;amp;v_ctl_auto_airspeed_setpoint,&amp;amp;v_ctl_auto_airspeed_controlled,&amp;amp;v_ctl_auto_groundspeed_setpoint)&lt;br /&gt;
 #else&lt;br /&gt;
 #define PERIODIC_SEND_AIRSPEED(_chan) {}&lt;br /&gt;
 #endif&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
&amp;lt;/div&amp;gt;&amp;lt;/div&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Configuring the Downlink Data Rate===&lt;br /&gt;
&lt;br /&gt;
The limited throughput of our RF modems results in a need to carefully choose which data to send, as well as the frequency at which to send it.  A sophisticated set of files and parameters have been developed in order to tailor the data downlink behavior automatically, manually, temporarily, or permanently according to any desired parameter.  This allows the user to create an almost unlimited possibility of downlink configurations.  For example:&lt;br /&gt;
* Tailor the data rate to work with very slow modems (9600 baud or slower)&lt;br /&gt;
* Reduce the data rate of some messages so that others can be increased:&lt;br /&gt;
*: Automatically send GPS data at a very high rate by sacrificing navigation data when not flying (to help GPS/RFI troubleshooting) then automatically reduce the GPS data rate and send normal navigation data when the launch is initiated.&lt;br /&gt;
*: Automatically switch to sending only position data upon landing to conserve power and increase the chance of the operator receiving a position packet when recovering a distant aircraft.&lt;br /&gt;
*: Manually send selected sensor data at very high speeds (60Hz) for real time tuning.&lt;br /&gt;
* Maintain independent telemetry configurations for aircraft with different modems, sensors, or mission profiles.&lt;br /&gt;
&lt;br /&gt;
Any number of configuration files can be created in the &amp;lt;tt&amp;gt;conf/telemetry&amp;lt;/tt&amp;gt; directory and selected from the &amp;lt;tt&amp;gt;conf/conf.xml&amp;lt;/tt&amp;gt; file.  The telemetry downlink is divided into two processes, '''Ap''' and '''Fbw''' each with a possible &amp;lt;tt&amp;gt;mode&amp;lt;/tt&amp;gt; option.  Any number of modes could be created, the default is the first in the sequence. A mode contains the list of messages to be sent as well as the period of each message in seconds. In this example, the '''ATTITUDE''' message will be sent by the '''Ap''' process at 2Hz in the default mode and at 10Hz in the '''fast attitude''' mode. The maximum allowed frequency is 60Hz (0.017s) and the maximum period is 1092s.&lt;br /&gt;
&lt;br /&gt;
The mode can be chosen in the airframe file by setting the '''TELEMETRY_MODE_FBW''' constant:&lt;br /&gt;
 &amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&amp;lt;define name=&amp;quot;TELEMETRY_MODE_FBW&amp;quot; value=&amp;quot;1&amp;quot;/&amp;gt;&amp;lt;/source&amp;gt;&lt;br /&gt;
where the (default) first mode is numbered '''0'''.&lt;br /&gt;
&lt;br /&gt;
This mode can also be changed dynamically with a datalink [[#Settings|setting]] or with a [[Flight_Plans#set|set]] stage in the flight plan.&lt;br /&gt;
&lt;br /&gt;
Note that an (undocumented!) subset of the messages is required to be able to use ground station properly. So it is not advisable to completely remove messages for the '''Ap''' process listed in the default mode.&lt;br /&gt;
&lt;br /&gt;
==Specific Messages==&lt;br /&gt;
&lt;br /&gt;
===GPS_SOL===&lt;br /&gt;
Specification in telemetry file&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;message name=&amp;quot;GPS_SOL&amp;quot;        period=&amp;quot;2.0&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
Example from logfile(.data):&lt;br /&gt;
 6.742 1 GPS_SOL 232 43 198 8&lt;br /&gt;
&lt;br /&gt;
Meaning of tokens:&lt;br /&gt;
 Timestamp, Aircraft-Number, GPS_SOL, Pacc, Sacc, PDOP, numSV&lt;br /&gt;
&lt;br /&gt;
*Pacc = Position accuracy (units: CM)&lt;br /&gt;
*Sacc = Speed accuracy (units: CM/sec ?)&lt;br /&gt;
*PDOP = Position [http://en.wikipedia.org/wiki/Dilution_of_precision_%28GPS%29 Dilution_of_precision_(GPS)] , if this value is high the value of position will be less accurate&lt;br /&gt;
*numSV = number of Space Vehicles (Satellites) used in Nav Solution&lt;br /&gt;
&lt;br /&gt;
===PPRZ_MODE===&lt;br /&gt;
Specification in telemetry file&lt;br /&gt;
&amp;lt;source lang=&amp;quot;xml&amp;quot;&amp;gt;&lt;br /&gt;
 &amp;lt;message name=&amp;quot;PPRZ_MODE&amp;quot;      period=&amp;quot;5.&amp;quot;/&amp;gt;&lt;br /&gt;
&amp;lt;/source&amp;gt;&lt;br /&gt;
Example from logfile(.data):&lt;br /&gt;
 20.433 2 PPRZ_MODE 0 1 2 0 0 1&lt;br /&gt;
&lt;br /&gt;
Meaning of tokens:&lt;br /&gt;
 Timestamp, Aircraft-Number, PPRZ_MODE, ap_mode, ap_gaz, ap_horizontal, if_calib_mode, mcul_status&lt;br /&gt;
*ap_mode = (0 = MANUAL, 1 = AUTO1, 2 = AUTO2, 3 = HOME mode (Circle Home waypoint), 4 = NO_GPS (GPS not working), 5 = NB (?)&lt;br /&gt;
*ap_gaz = ?&lt;br /&gt;
*ap_horizontal = ?&lt;br /&gt;
*if_calib_mode = ?&lt;br /&gt;
*mcul_status = ?&lt;br /&gt;
&lt;br /&gt;
== Audio-based downlink ==&lt;br /&gt;
&lt;br /&gt;
The audio-based downlink has been removed from current hardware designs however using the old designs it is possible to implement. With the current low prices of a simple video transmitter, data over audio may come in as a welcomed addition. Feel free to experiment and revive this classical feature.&lt;br /&gt;
&lt;br /&gt;
[[Category:Software]] [[Category:User_Documentation]] [[Category:Telemetry]]&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Talk:Telemetry&amp;diff=21100</id>
		<title>Talk:Telemetry</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Talk:Telemetry&amp;diff=21100"/>
		<updated>2016-03-15T10:19:37Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;The add messages section seems to be out dated for version 5.8. The AIRSPEED messages are already implemented. I tried to get this working for a module I made following the instructions but it did not work. I think they need to be updated. --[[User:Lethargi|Lethargi]]&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
	<entry>
		<id>http://wiki.paparazziuav.org/w/index.php?title=Talk:Telemetry&amp;diff=21099</id>
		<title>Talk:Telemetry</title>
		<link rel="alternate" type="text/html" href="http://wiki.paparazziuav.org/w/index.php?title=Talk:Telemetry&amp;diff=21099"/>
		<updated>2016-03-15T10:17:36Z</updated>

		<summary type="html">&lt;p&gt;Lethargi: Created page with &amp;quot;The add messages section seems to be out dated for version 5.8. The AIRSPEED messages are already implemented. I tried to get this working for a module I made following the in...&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;The add messages section seems to be out dated for version 5.8. The AIRSPEED messages are already implemented. I tried to get this working for a module I made following the instructions but it did not work. I think they need to be updated.&lt;/div&gt;</summary>
		<author><name>Lethargi</name></author>
	</entry>
</feed>