-
-
Save marc-hanheide/4c35796e6a7cd0042dca274bf9e5e9f5 to your computer and use it in GitHub Desktop.
''' | |
This script saves each topic in a bagfile as a csv. | |
Accepts a filename as an optional argument. Operates on all bagfiles in current directory if no argument provided | |
Usage1 (for one bag file): | |
python bag2csv.py filename.bag | |
Usage 2 (for all bag files in current directory): | |
python bag2csv.py | |
Written by Nick Speal in May 2013 at McGill University's Aerospace Mechatronics Laboratory. Bugfixed by Marc Hanheide June 2016. | |
www.speal.ca | |
Supervised by Professor Inna Sharf, Professor Meyer Nahon | |
''' | |
import rosbag, sys, csv | |
import time | |
import string | |
import os #for file management make directory | |
import shutil #for file management, copy file | |
#verify correct input arguments: 1 or 2 | |
if (len(sys.argv) > 2): | |
print "invalid number of arguments: " + str(len(sys.argv)) | |
print "should be 2: 'bag2csv.py' and 'bagName'" | |
print "or just 1 : 'bag2csv.py'" | |
sys.exit(1) | |
elif (len(sys.argv) == 2): | |
listOfBagFiles = [sys.argv[1]] | |
numberOfFiles = 1 | |
print "reading only 1 bagfile: " + str(listOfBagFiles[0]) | |
elif (len(sys.argv) == 1): | |
listOfBagFiles = [f for f in os.listdir(".") if f[-4:] == ".bag"] #get list of only bag files in current dir. | |
numberOfFiles = str(len(listOfBagFiles)) | |
print "reading all " + numberOfFiles + " bagfiles in current directory: \n" | |
for f in listOfBagFiles: | |
print f | |
print "\n press ctrl+c in the next 10 seconds to cancel \n" | |
time.sleep(10) | |
else: | |
print "bad argument(s): " + str(sys.argv) #shouldnt really come up | |
sys.exit(1) | |
count = 0 | |
for bagFile in listOfBagFiles: | |
count += 1 | |
print "reading file " + str(count) + " of " + str(numberOfFiles) + ": " + bagFile | |
#access bag | |
bag = rosbag.Bag(bagFile) | |
bagContents = bag.read_messages() | |
bagName = bag.filename | |
#create a new directory | |
folder = string.rstrip(bagName, ".bag") | |
try: #else already exists | |
os.makedirs(folder) | |
except: | |
pass | |
shutil.copyfile(bagName, folder + '/' + bagName) | |
#get list of topics from the bag | |
listOfTopics = [] | |
for topic, msg, t in bagContents: | |
if topic not in listOfTopics: | |
listOfTopics.append(topic) | |
for topicName in listOfTopics: | |
#Create a new CSV file for each topic | |
filename = folder + '/' + string.replace(topicName, '/', '_slash_') + '.csv' | |
with open(filename, 'w+') as csvfile: | |
filewriter = csv.writer(csvfile, delimiter = ',') | |
firstIteration = True #allows header row | |
for subtopic, msg, t in bag.read_messages(topicName): # for each instant in time that has data for topicName | |
#parse data from this instant, which is of the form of multiple lines of "Name: value\n" | |
# - put it in the form of a list of 2-element lists | |
msgString = str(msg) | |
msgList = string.split(msgString, '\n') | |
instantaneousListOfData = [] | |
for nameValuePair in msgList: | |
splitPair = string.split(nameValuePair, ':') | |
for i in range(len(splitPair)): #should be 0 to 1 | |
splitPair[i] = string.strip(splitPair[i]) | |
instantaneousListOfData.append(splitPair) | |
#write the first row from the first element of each pair | |
if firstIteration: # header | |
headers = ["rosbagTimestamp"] #first column header | |
for pair in instantaneousListOfData: | |
headers.append(pair[0]) | |
filewriter.writerow(headers) | |
firstIteration = False | |
# write the value from each pair to the file | |
values = [str(t)] #first column will have rosbag timestamp | |
for pair in instantaneousListOfData: | |
if len(pair)>1: | |
values.append(pair[1]) | |
filewriter.writerow(values) | |
bag.close() | |
print "Done reading all " + str(numberOfFiles) + " bag files." |
Thanks,
I suggest making the line 85 to be
splitPair = string.split(nameValuePair, ':', 1)
(I had ':' in value so it did not work).
Where is the output .CSV file will be located?
Hello, I have around 1800 images but its giving only 32 .csv file why so ? Also the pose files are not correct any other method by which we could get pose data (converting .bag --> .csv )
I have just taken this gist from the original source and made it work in 2016 for my own purposes. I'm afraid, I don't maintain it, but I welcome anyone taking it and hosting it as a proper project. Also, this one might be a better alternative: https://github.com/AtsushiSakai/rosbag_to_csv
Or simply rostopic echo -b file.bag -p /topic
will work for some simple data types. The best is probably the really neat rosbag_pandas package for python that also includes a bag2csv.py
tool
Hope this helps @Shivani1796
I am new to working with rosbag files and was having a hard time, trying to get rosbag_pandas to work. This script was a lifesaver. Thanks @marc-hanheide
Thanks for this!!