quat2eular / app.py
lily-hust's picture
Upload 2 files
6b24496
raw
history blame
4.06 kB
import streamlit as st
#from pandas import DataFrame as df
import csv
import math
def main():
st.title('Quaternion to Eular angle conversion for SLAM')
st.markdown('Only support single file conversion at this time. Will be processing batch files in the future. \n')
st.markdown('The input file should be in the format of csv where fields are separated by ";". The output will be also a csv file. \n')
st.markdown('The input field order is\n')
st.markdown('fileID; image file name; time stamp; pose_x; pose_y; pose_z; ori_w; ori_x; ori_y; ori_z.\n')
st.markdown('The unit of the input pos_x, pos_y and pos_z is meter.\n')
st.markdown('The unit of the output pos_x, pos_y and pos_z is feet, and ori_roll, ori_pitch, ori_yaw is degree.\n')
run_the_app()
@st.cache_data()
def euler_from_quaternion(x, y, z, w):
t0 = +2.0 * (w * x + y * z)
t1 = +1.0 - 2.0 * (x * x + y * y)
roll_x = math.atan2(t0, t1)
t2 = +2.0 * (w * y - z * x)
#t2 = +1.0 if t2 > +1.0 else t2
#t2 = -1.0 if t2 < -1.0 else t2
pitch_y = math.asin(t2)
t3 = +2.0 * (w * z + x * y)
t4 = +1.0 - 2.0 * (y * y + z * z)
yaw_z = math.atan2(t3, t4)
# the y here obvious points to the 90 anticlockwise to x, instead of the general definition of quaternion and Eular angles where y points to 90 degree clockwise to x
return math.degrees(roll_x), -math.degrees(pitch_y), math.degrees(yaw_z) # in degree
def run_the_app():
uploaded_files = st.file_uploader(
"Upload csv files",
type="csv",
accept_multiple_files=True)
if uploaded_files:
if st.button("Clear uploaded files"):
st.empty()
st.experimental_rerun()
with open('converted.csv', 'w', newline='', encoding='utf-8') as wf:
fieldnames = ['# pano poses v1.0: ID',
'filename',
'timestamp',
'pano_pos_x',
'pano_pos_y',
'pano_pos_z',
'pano_ori_roll',
'pano_ori_pitch',
'pano_ori_yaw'
]
writer = csv.DictWriter(wf, fieldnames=fieldnames)
writer.writeheader()
with open(uploaded_files, 'r', encoding='utf-8') as rf:
reader = csv.DictReader(rf)
for row in reader:
row_v = list(row.values())[0].split(';')
# in the input file, the quat order is ori_w,ori_x,ori_y,ori_z
roll, pitch, yaw = euler_from_quaternion(float(row_v[7]),
float(row_v[8]),
float(row_v[9]),
float(row_v[6]))
# now yaw is the angle to x, anticlockwise. But our definition is the angle to y(north), clockwise
yaw = -yaw + 90.0
if yaw < -180.0:
yaw += 360.0
elif yaw > 180.0:
yaw -= 360.0
rec = {fieldnames[0]: row_v[0],
fieldnames[1]: row_v[1][1:],
fieldnames[2]: row_v[2],
fieldnames[3]: float(row_v[3])*3.28084,
fieldnames[4]: float(row_v[4])*3.28084,
fieldnames[5]: float(row_v[5])*3.28084,
fieldnames[6]: roll,
fieldnames[7]: pitch,
fieldnames[8]: yaw}
writer.writerow(rec)
st.download_button("Download the converted files",
data = "converted.csv")
if __name__ == "__main__":
main()