Skip to content

Commit e1577e2

Browse files
committed
Merge branch 's2025_EstCal' of https://github.com/krishauser/GEMstack into s2025_EstCal
2 parents d8b3ba1 + 65ddc11 commit e1577e2

3 files changed

Lines changed: 70 additions & 13 deletions

File tree

GEMstack/onboard/perception/gnss_kalman_filter.py

Lines changed: 15 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -21,12 +21,15 @@ def __init__(self):
2121
self.Q = np.eye(12) * 0.1
2222
self.R = np.eye(6) * 0.1
2323

24-
def update(self, time: float, state: ObjectPose = None, th = 0) -> ObjectPose:
24+
25+
self.speed = None #TODO
26+
27+
def update(self, time: float, state: ObjectPose = None, speed = None, th = 0) -> ObjectPose:
2528
if not self.is_initialized:
2629
if state is None:
2730
return None
2831
else:
29-
self._initialize(state, time)
32+
self._initialize(state, speed, time)
3033
return self._current_pose()
3134

3235
dt = time - self.last_time
@@ -59,7 +62,7 @@ def update(self, time: float, state: ObjectPose = None, th = 0) -> ObjectPose:
5962
self.last_time = time
6063
return self._current_pose()
6164

62-
def _initialize(self, state: ObjectPose, time: float):
65+
def _initialize(self, state: ObjectPose, speed: float, time: float):
6366
self.state = np.zeros(12)
6467
self.state[0] = state.x
6568
self.state[2] = state.y
@@ -68,6 +71,8 @@ def _initialize(self, state: ObjectPose, time: float):
6871
self.state[8] = state.roll
6972
self.state[10] = state.pitch
7073

74+
self.speed = speed #TODO
75+
7176
self.covariance = np.eye(12) * 0.1
7277
for i in [1, 3, 5, 7, 9, 11]:
7378
self.covariance[i, i] = 10.0 # Higher uncertainty for velocities
@@ -92,7 +97,7 @@ def _current_pose(self) -> ObjectPose:
9297
yaw=self.state[6],
9398
roll=self.state[8],
9499
pitch=self.state[10]
95-
)
100+
),self.speed
96101

97102
def test0():
98103
th = 0.95 # 95% confidence threshold
@@ -109,7 +114,7 @@ def test0():
109114
print("-- Initialization --")
110115
print("Update 0:", kf.update(0, ObjectPose(ObjectFrameEnum.GLOBAL,
111116
0, -0.118092, 51.509865, 35.0, 0, 0, 0
112-
), th))
117+
), 0.00017,th=th))
113118

114119
# Straight movement north at 60 km/h (~16.67 m/s)
115120
print("\n-- Straight movement --")
@@ -125,7 +130,7 @@ def test0():
125130
5.0, # Slight right turn
126131
1.5, # Small roll from turning
127132
0.5 # Small pitch from acceleration
128-
), th))
133+
), 0.00017,th=th))
129134

130135
# Turning right sequence with realistic coordinate changes
131136
print("\n-- Right turn sequence --")
@@ -138,7 +143,7 @@ def test0():
138143
5.0 + 15*(t-3), # Increasing yaw
139144
1.5 + 0.5*(t-3), # Roll increasing
140145
0.5 - 0.2*(t-3) # Pitch decreasing
141-
), th))
146+
), 0.00017,th=th))
142147

143148
# Hill climb with pitch changes
144149
print("\n-- Hill climb --")
@@ -151,7 +156,7 @@ def test0():
151156
35.0, # Completed turn
152157
2.0, # Reduced roll
153158
4.0 # Significant pitch from hill
154-
), th))
159+
), 0.00017,th=th))
155160

156161
# Test outlier rejection (sudden jump to China coordinates)
157162
print("\n-- Outlier test --")
@@ -164,7 +169,7 @@ def test0():
164169
35.0, # Same yaw
165170
2.0,
166171
4.0
167-
), th)) # Should be rejected by threshold
172+
), 0.00017,th=th))
168173

169174
# Continue normal operation
170175
print("\n-- Post-outlier recovery --")
@@ -177,7 +182,7 @@ def test0():
177182
35.0 + 2*(t-9),
178183
2.0 - 0.3*(t-9),
179184
4.0 - 0.5*(t-9)
180-
), th))
185+
), 0.00017,th=th))
181186

182187
if __name__ == "__main__":
183188
import sys
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
from dataclasses import replace
2+
import math
3+
from typing import List
4+
from ...utils import settings
5+
from ...mathutils import transforms
6+
from ...state.vehicle import VehicleState,VehicleGearEnum
7+
from ...state.physical_object import ObjectFrameEnum,ObjectPose,convert_xyhead
8+
from ...knowledge.vehicle.geometry import front2steer,steer2front
9+
from ...mathutils.signal import OnlineLowPassFilter
10+
from ..interface.gem import GEMInterface
11+
from ..component import Component
12+
from ..interface.gem import GNSSReading
13+
14+
import numpy as np
15+
import open3d as o3d
16+
import copy
17+
import utm
18+
import time
19+
import argparse
20+
import os
21+
import glob
22+
from scipy.spatial.transform import Rotation as R
23+
from .gnss_kalman_filter import GNSSKalmanFilter
24+
import rospy
25+
26+
class KFStateEstimator(Component):
27+
def __init__(self,vehicle_interface : GEMInterface):
28+
self.vehicle_interface = vehicle_interface
29+
self.filter = GNSSKalmanFilter
30+
vehicle_interface.subscribe_sensor('gnss',self.gnss_callback,GNSSReading)
31+
#TODO create subscription on mapbased estimation with self.map_based_estimation_callback
32+
# Get GNSS information
33+
def gnss_callback(self, reading : GNSSReading):
34+
self.filter.update(rospy.get_time(),reading.pose,reading.speed,0.98)
35+
36+
def map_based_estimation_callback(self, reading : GNSSReading):
37+
self.filter.update(rospy.get_time(),reading.pose,reading.speed,0.93)
38+
39+
def rate(self):
40+
return 1.0
41+
42+
def state_outputs(self) -> List[str]:
43+
return ['vehicle']
44+
45+
def healthy(self):
46+
return self.filter.is_initialized
47+
48+
def update(self) -> VehicleState:
49+
50+
return GNSSReading(
51+
*(self.filter.update(rospy.get_time())),
52+
"ok",#or error but when
53+
)
54+

GEMstack/onboard/perception/map_based_estimation.py

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -218,9 +218,7 @@ def multi_scale_icp(source, target, voxel_sizes=[2.0, 1.0, 0.5], max_iterations=
218218

219219
return current_transform
220220

221-
222-
223-
def transform_to_pose(transformation_matrix,origin):
221+
def transform_to_pose(transformation_matrix):
224222
"""Convert transformation matrix to position and orientation (RPY)."""
225223
# Extract translation
226224
x, y, z = transformation_matrix[:3, 3]

0 commit comments

Comments
 (0)