From 6335db69bd08201478e6857282eb6a96a8938dd0 Mon Sep 17 00:00:00 2001 From: Daniel Koepping Date: Wed, 22 Jul 2026 16:23:32 -0700 Subject: [PATCH] eGPU UI (#38419) --- .../selfdrive/ui/mici/onroad/hud_renderer.py | 16 ++++++++++++++++ openpilot/selfdrive/ui/ui_state.py | 7 ++++++- 2 files changed, 22 insertions(+), 1 deletion(-) diff --git a/openpilot/selfdrive/ui/mici/onroad/hud_renderer.py b/openpilot/selfdrive/ui/mici/onroad/hud_renderer.py index 27bb815590..0225bc8d57 100644 --- a/openpilot/selfdrive/ui/mici/onroad/hud_renderer.py +++ b/openpilot/selfdrive/ui/mici/onroad/hud_renderer.py @@ -177,8 +177,24 @@ class HudRenderer(Widget): if self.is_cruise_set: self._draw_set_speed(rect) + if ui_state.usbgpu and ui_state.usbgpu_compiled: + self._draw_model_source(rect) + self._draw_steering_wheel(rect) + def _draw_model_source(self, rect: rl.Rectangle) -> None: + if ui_state.sm.recv_frame['selfdriveState'] < ui_state.started_frame: + return + small_drives = not ui_state.usbgpu_loading and not ui_state.usbgpu_active and ui_state.sm.recv_frame['modelV2'] > ui_state.started_frame + big_color = rl.GREEN if ui_state.usbgpu_active else rl.RED if small_drives else rl.GRAY + small_color = rl.GREEN if small_drives else rl.WHITE if ui_state.usbgpu_active else rl.GRAY + big_size = measure_text_cached(self._font_semi_bold, "BIG", FONT_SIZES.max_speed) + small_size = measure_text_cached(self._font_semi_bold, "SM", FONT_SIZES.max_speed) + big_pos = rl.Vector2(rect.x + rect.width - 12 - big_size.x, rect.y + rect.height - 14 - FONT_SIZES.max_speed) + small_pos = rl.Vector2(big_pos.x + (big_size.x - small_size.x) / 2, big_pos.y - FONT_SIZES.max_speed - 2) + rl.draw_text_ex(self._font_semi_bold, "BIG", big_pos, FONT_SIZES.max_speed, 0, big_color) + rl.draw_text_ex(self._font_semi_bold, "SM", small_pos, FONT_SIZES.max_speed, 0, small_color) + def _draw_steering_wheel(self, rect: rl.Rectangle) -> None: wheel_txt = self._txt_wheel_critical if self._show_wheel_critical else self._txt_wheel diff --git a/openpilot/selfdrive/ui/ui_state.py b/openpilot/selfdrive/ui/ui_state.py index 7efcf2a7c9..a12df6906d 100644 --- a/openpilot/selfdrive/ui/ui_state.py +++ b/openpilot/selfdrive/ui/ui_state.py @@ -78,6 +78,8 @@ class UIState: self.experimental_mode: bool = self.params.get_bool("ExperimentalMode") self.usbgpu: bool = False self.usbgpu_compiled: bool = usbgpu_compiled() + self.usbgpu_active: bool = self.params.get_bool("UsbGpuActive") + self.usbgpu_loading: bool = self.params.get_bool("UsbGpuLoading") self.started: bool = False self.ignition: bool = False self.recording_audio: bool = False @@ -204,9 +206,12 @@ class UIState: self.is_metric = self.params.get_bool("IsMetric") self.always_on_dm = self.params.get_bool("AlwaysOnDM") self.experimental_mode = self.params.get_bool("ExperimentalMode") - self.usbgpu = self.sm["deviceState"].chestnutPresent + # keep usbgpu UI active until offroad transition when gpu disappears + self.usbgpu = self.sm["deviceState"].chestnutPresent or (self.usbgpu and self.started) if not self.usbgpu_compiled: self.usbgpu_compiled = usbgpu_compiled() + self.usbgpu_active = self.params.get_bool("UsbGpuActive") + self.usbgpu_loading = self.params.get_bool("UsbGpuLoading") class Device: