Friday, May 25, 2012

AVC: Visualizing Position


Look at all those pretty lines. Each represents the path of Data Bus as recorded in a log file for each run. Visualizing Data Bus' reported path has been invaluable in troubleshooting, tuning, and tweaking.

So, how do I turn the log file into the mapping above? A series of handy scripts and tools...

Let's say I just got back from a series of test runs. I plug a USB cable into the mbed on Data Bus and connect it to my computer. Then I fire up my custom Java serial terminal (serterm).



Select option 8, shell, wait for the shell prompt and type ls and now I can see a list of logfiles. Now, just type, for example, send log036.csv



While serterm is transferring the file for me, I fire up a Cygwin terminal. When the transfer is finished, log036.csv will reside in my Downloads folder. I copy it into a directory to analyze. Let's look at the csv log file...


Yuck, what a mess. Good thing I've written a perl library to make parsing it easier. I can quickly write a script to parse the file.


use lib "/home/mes/lib";
use DATABUS::FIELDS;


The perl library lets me parse the fields in each line of the log file into a hash.


 while (<$fin>) {
  s/[\r\n]+//g;
  my %data = parseFields($_);


Then just reference the field within the hash: $data{"speed"}. So I can write a whole script quickly to parse out the data I want. Here's the entire speed.pl script.


#!/usr/bin/perl

use Cwd;
use lib "/home/mes/lib";
use DATABUS::FIELDS;

if ($#ARGV < 0) {
  printf "usage: $0 infile\n";
  exit(1);
}

$lastSpeed = 0;
foreach my $file (@ARGV) {
 open my $fin, "<", "$file" || die "cant open $file\n";
 $file =~ tr/A-Z/a-z/;
 printf "# Millis,GPSspeed,lrspeed,rrspeed\n";
 while (<$fin>) {
  s/[\r\n]+//g;
  my %data = parseFields($_);
  next if ($data{"millis"} eq "Millis");
  if ($data{"lat"} == 0) {
   $data{"speed"} = $lastSpeed;
  } else {
   $lastSpeed = $data{"speed"};
  }
  printf "%d,%.2f,%.2f,%.2f\n", 
   $data{"millis"}, $data{"speed"}, 
   $data{"lrspeed"}, $data{"rrspeed"};
 }
 close($fin);
}


I can create new files on the fly by using a simple one like this as a template.

The KML generation script is the most complicated. Here's what it can do.

$ gps.pl log034.csv log035.csv log036.csv > gps034_035_036.kml


 

Opening up the file in Google Earth, each path is color coded, and named uniquely. I thought that was kinda handy.

What if I want to view the estimated position instead of the reported GPS position?  Just stick the -e switch in the command line.

$ gps.pl -e log034.csv log035.csv log036.csv > est034_035_036.kml


Of course the estimated path displayed in Google Earth is where the robot thought it was. To see how accurate the robot's estimate was, I've used a few techniques. The best and most accurate is to use a site with markers on the ground visible in Google Earth.


Set waypoints on these markers so they can easily be identified as you stand at the site. Then run the robot and see how close or far it is to these markers. When I did my Demo in front of friends, Data Bus was typically within a couple meters of each waypoint.

Another way is to film the robot and compare by eyeball between video and Google Earth plot. Instead, when informally testing outside the house I just kind of eyeball where I think the waypoints are and see if the robot is getting in the ballpark. Then I go to the site above to test against real markers.

Links to Code
gps.pl and FIELDS.pm

No comments:

Post a Comment