mirror of
https://github.com/sunnypilot/sunnypilot.git
synced 2026-07-16 13:02:27 +08:00
ddf63701e8
* init * some fixes * move * more * old navd helpers * bring back cereal * fix linting * more * add to cereal first * sp events * lint * implement in long plan * fixme-sp * refactor state machine * wrong state * start refactor controller * some type hints * init these * enable debug print * ui? ui! * print them out * fix spinner import * fix path * let's use gps chips directly for now * service missing * publish events * no nav for now * need to sub * no car state speed yet * missed event * Car: `CarStateSP` * fix tests * bring back car state speed limit * fix * use old controller for now * fix * fix source * type hints * none for now * formatting * more * create directory if does not exist * mypy my bt * policy param catch exceptions * handle all params with exceptions * more * single method * define types in init * rename * simpler op enabled check * more mypy stuff * rename * no need for brake pressed * don't reset if gas pressed * type hint all * type hint all * back to upstream * in another pr * no longer need data type * qlog * slc in another pr * use horizontal accuracy * use horizontal accuracy * set core affinity for all realtime processes * unused * sort * unused * type hint and slight cleanup * from old implementation * use directly * combine pm * slight more cleanup * type hints * even more type hint * Revert "slc in another pr" This reverts commit3a6987e6* Revert "in another pr" This reverts commita29bccff12. * rebump * no need to check alive * use it directly * fix test * refactor * use gps data directly * quote...? * lint * fix tests * use CC.longActive * user confirm in another PR * rename * fix import * params fix * no more * fix * drop new state machine for now * more fixes * internalize output * unused * rearrange * auto draft * rename * this * no * no need * use existing * wrong cruise speed * fix * not used for now * Revert "not used for now" This reverts commitf0083d6241. * some * use frames instead * split speed limit resolver out of slc * no need to pass sm * fix params * test init * use frame instead of time * track session * some tests * too limiting * bump * always reset state * end session if long_active but slc inactive at any given time * off * no warning in this PR * no speed factor engage type yet * wide open * no * introduce disabled, no longer transitions at inactive * fix tests * no more tempinactive * clean * rename * offset default > off * new tests, fixes controller * more tests * not really needed yet * lint * fix * some more tests * wrap * more * more * use vCruiseCluster for set speed * init better * finish it up * no * typo * one method state machine * refactor preactive timeout check * refactor new session check * directly return statuses * comments * v_target * refactor speed limit resolver * turn off debug * more resolver refactor * no longer needed * lint * more lint * fix * move around * fix events * update event * already happens while in enabled * add carstateSP * less * Speed Limit Control -> Speed Limit Assist * in another PR * more rename * overriding state * fix * make sure to return the correct type * just slr in this one * more * update * redundant * fix * fix * lint * fix * fix * match toggle * fix priority checks * fix combined source for picking 0 limit * no need to wrap * add speed limit offset to resolver * add speed limit offset * make sure it displays distance when higher * Revert "make sure it displays distance when higher" This reverts commit15c6834d4e. * some rename * translations * unused for now * more * lint --------- Co-authored-by: nayan <nayan8teen@gmail.com> Co-authored-by: DevTekVE <devtekve@gmail.com>
192 lines
6.9 KiB
Python
Executable File
192 lines
6.9 KiB
Python
Executable File
#!/usr/bin/env python3
|
|
import time
|
|
import numpy as np
|
|
|
|
from cereal import log
|
|
import cereal.messaging as messaging
|
|
from openpilot.common.realtime import Ratekeeper, DT_MDL
|
|
from openpilot.selfdrive.controls.lib.longcontrol import LongCtrlState
|
|
from openpilot.selfdrive.modeld.constants import ModelConstants
|
|
from openpilot.selfdrive.controls.lib.longitudinal_planner import LongitudinalPlanner
|
|
from openpilot.selfdrive.controls.radard import _LEAD_ACCEL_TAU
|
|
|
|
|
|
class Plant:
|
|
messaging_initialized = False
|
|
|
|
def __init__(self, lead_relevancy=False, speed=0.0, distance_lead=2.0,
|
|
enabled=True, only_lead2=False, only_radar=False, e2e=False, personality=0, force_decel=False):
|
|
self.rate = 1. / DT_MDL
|
|
|
|
if not Plant.messaging_initialized:
|
|
Plant.radar = messaging.pub_sock('radarState')
|
|
Plant.controls_state = messaging.pub_sock('controlsState')
|
|
Plant.selfdrive_state = messaging.pub_sock('selfdriveState')
|
|
Plant.car_state = messaging.pub_sock('carState')
|
|
Plant.plan = messaging.sub_sock('longitudinalPlan')
|
|
Plant.messaging_initialized = True
|
|
|
|
self.v_lead_prev = 0.0
|
|
|
|
self.distance = 0.
|
|
self.speed = speed
|
|
self.should_stop = False
|
|
self.acceleration = 0.0
|
|
|
|
# lead car
|
|
self.lead_relevancy = lead_relevancy
|
|
self.distance_lead = distance_lead
|
|
self.enabled = enabled
|
|
self.only_lead2 = only_lead2
|
|
self.only_radar = only_radar
|
|
self.e2e = e2e
|
|
self.personality = personality
|
|
self.force_decel = force_decel
|
|
|
|
self.rk = Ratekeeper(self.rate, print_delay_threshold=100.0)
|
|
self.ts = 1. / self.rate
|
|
time.sleep(0.1)
|
|
self.sm = messaging.SubMaster(['longitudinalPlan'])
|
|
|
|
from opendbc.car.honda.values import CAR
|
|
from opendbc.car.honda.interface import CarInterface
|
|
|
|
self.planner = LongitudinalPlanner(CarInterface.get_non_essential_params(CAR.HONDA_CIVIC), init_v=self.speed)
|
|
|
|
@property
|
|
def current_time(self):
|
|
return float(self.rk.frame) / self.rate
|
|
|
|
def step(self, v_lead=0.0, prob_lead=1.0, v_cruise=50., pitch=0.0, prob_throttle=1.0):
|
|
# ******** publish a fake model going straight and fake calibration ********
|
|
# note that this is worst case for MPC, since model will delay long mpc by one time step
|
|
radar = messaging.new_message('radarState')
|
|
control = messaging.new_message('controlsState')
|
|
ss = messaging.new_message('selfdriveState')
|
|
car_state = messaging.new_message('carState')
|
|
lp = messaging.new_message('liveParameters')
|
|
car_control = messaging.new_message('carControl')
|
|
model = messaging.new_message('modelV2')
|
|
car_state_sp = messaging.new_message('carStateSP')
|
|
live_map_data_sp = messaging.new_message('liveMapDataSP')
|
|
gps_data = messaging.new_message('gpsLocation')
|
|
a_lead = (v_lead - self.v_lead_prev)/self.ts
|
|
self.v_lead_prev = v_lead
|
|
|
|
if self.lead_relevancy:
|
|
d_rel = np.maximum(0., self.distance_lead - self.distance)
|
|
v_rel = v_lead - self.speed
|
|
if self.only_radar:
|
|
status = True
|
|
elif prob_lead > .5:
|
|
status = True
|
|
else:
|
|
status = False
|
|
else:
|
|
d_rel = 200.
|
|
v_rel = 0.
|
|
prob_lead = 0.0
|
|
status = False
|
|
|
|
lead = log.RadarState.LeadData.new_message()
|
|
lead.dRel = float(d_rel)
|
|
lead.yRel = 0.0
|
|
lead.vRel = float(v_rel)
|
|
lead.aRel = float(a_lead - self.acceleration)
|
|
lead.vLead = float(v_lead)
|
|
lead.vLeadK = float(v_lead)
|
|
lead.aLeadK = float(a_lead)
|
|
# TODO use real radard logic for this
|
|
lead.aLeadTau = float(_LEAD_ACCEL_TAU)
|
|
lead.status = status
|
|
lead.modelProb = float(prob_lead)
|
|
if not self.only_lead2:
|
|
radar.radarState.leadOne = lead
|
|
radar.radarState.leadTwo = lead
|
|
|
|
# Simulate model predicting slightly faster speed
|
|
# this is to ensure lead policy is effective when model
|
|
# does not predict slowdown in e2e mode
|
|
position = log.XYZTData.new_message()
|
|
position.x = [float(x) for x in (self.speed + 0.5) * np.array(ModelConstants.T_IDXS)]
|
|
model.modelV2.position = position
|
|
model.modelV2.action.desiredAcceleration = float(self.acceleration + 0.1)
|
|
velocity = log.XYZTData.new_message()
|
|
velocity.x = [float(x) for x in (self.speed + 0.5) * np.ones_like(ModelConstants.T_IDXS)]
|
|
velocity.x[0] = float(self.speed) # always start at current speed
|
|
model.modelV2.velocity = velocity
|
|
acceleration = log.XYZTData.new_message()
|
|
acceleration.x = [float(x) for x in np.zeros_like(ModelConstants.T_IDXS)]
|
|
model.modelV2.acceleration = acceleration
|
|
model.modelV2.meta.disengagePredictions.gasPressProbs = [float(prob_throttle) for _ in range(6)]
|
|
|
|
control.controlsState.longControlState = LongCtrlState.pid if self.enabled else LongCtrlState.off
|
|
ss.selfdriveState.experimentalMode = self.e2e
|
|
ss.selfdriveState.personality = self.personality
|
|
control.controlsState.forceDecel = self.force_decel
|
|
car_state.carState.vEgo = float(self.speed)
|
|
car_state.carState.standstill = bool(self.speed < 0.01)
|
|
car_state.carState.vCruise = float(v_cruise * 3.6)
|
|
car_control.carControl.orientationNED = [0., float(pitch), 0.]
|
|
|
|
# ******** get controlsState messages for plotting ***
|
|
sm = {'radarState': radar.radarState,
|
|
'carState': car_state.carState,
|
|
'carControl': car_control.carControl,
|
|
'controlsState': control.controlsState,
|
|
'selfdriveState': ss.selfdriveState,
|
|
'liveParameters': lp.liveParameters,
|
|
'modelV2': model.modelV2,
|
|
'carStateSP': car_state_sp.carStateSP,
|
|
'liveMapDataSP': live_map_data_sp.liveMapDataSP,
|
|
'gpsLocation': gps_data.gpsLocation}
|
|
self.planner.update(sm)
|
|
self.acceleration = self.planner.output_a_target
|
|
self.speed = self.speed + self.acceleration * self.ts
|
|
self.should_stop = self.planner.output_should_stop
|
|
fcw = self.planner.fcw
|
|
self.distance_lead = self.distance_lead + v_lead * self.ts
|
|
|
|
# ******** run the car ********
|
|
#print(self.distance, speed)
|
|
if self.speed <= 0:
|
|
self.speed = 0
|
|
self.acceleration = 0
|
|
self.distance = self.distance + self.speed * self.ts
|
|
|
|
# *** radar model ***
|
|
if self.lead_relevancy:
|
|
d_rel = np.maximum(0., self.distance_lead - self.distance)
|
|
v_rel = v_lead - self.speed
|
|
else:
|
|
d_rel = 200.
|
|
v_rel = 0.
|
|
|
|
# print at 5hz
|
|
# if (self.rk.frame % (self.rate // 5)) == 0:
|
|
# print("%2.2f sec %6.2f m %6.2f m/s %6.2f m/s2 lead_rel: %6.2f m %6.2f m/s"
|
|
# % (self.current_time, self.distance, self.speed, self.acceleration, d_rel, v_rel))
|
|
|
|
|
|
# ******** update prevs ********
|
|
self.rk.monitor_time()
|
|
|
|
return {
|
|
"distance": self.distance,
|
|
"speed": self.speed,
|
|
"acceleration": self.acceleration,
|
|
"should_stop": self.should_stop,
|
|
"distance_lead": self.distance_lead,
|
|
"fcw": fcw,
|
|
}
|
|
|
|
# simple engage in standalone mode
|
|
def plant_thread():
|
|
plant = Plant()
|
|
while 1:
|
|
plant.step()
|
|
|
|
|
|
if __name__ == "__main__":
|
|
plant_thread()
|