From 62a403d0f149bf8767fc09b551e55c1362cd545b Mon Sep 17 00:00:00 2001 From: Brian Hanson Date: Sun, 19 Apr 2026 12:54:56 -0500 Subject: [PATCH] UI: shift speed-limit/cruise numbers down; modeld: keep 20fps at standstill-in-drive; health: FPS instead of LAG MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - onroad: speed-limit sign and cruise over/under sign — shift the number ~10% further down inside the inner box (adjusted top inset 42→86). - modeld: narrow the standby condition. Previously 0fps when standstill-or-parked; now 0fps only when parked. Standstill in drive (red light) continues to run at 20fps so lateral can engage/stay responsive and liveCalibration/paramsd keep seeing observations. Ignition-off still stops modeld at the manager level. - Health overlay: replace LAG row with FPS (modeld framerate read from ModelFps memory param, which modeld already writes only on standby transition — no per-frame writes). Co-Authored-By: Claude Opus 4.7 (1M context) --- selfdrive/modeld/modeld.py | 8 +++++--- selfdrive/ui/qt/onroad.cc | 23 ++++++++++++----------- 2 files changed, 17 insertions(+), 14 deletions(-) diff --git a/selfdrive/modeld/modeld.py b/selfdrive/modeld/modeld.py index fd6c17a..a9ea1b7 100755 --- a/selfdrive/modeld/modeld.py +++ b/selfdrive/modeld/modeld.py @@ -241,10 +241,12 @@ def main(demo=False): sm.update(0) - # CLEARPILOT: two-state modeld — 0fps at standstill or parked, 20fps otherwise. - standstill = sm['carState'].standstill + # CLEARPILOT: two-state modeld — 0fps only when parked (ignition-on means + # engine running in park; ignition-off stops modeld at the manager level). + # Standstill in drive (red light) keeps running so lateral stays responsive + # and liveCalibration/paramsd observations continue. parked = sm['carState'].gearShifter == car.CarState.GearShifter.park - should_standby = standstill or parked + should_standby = parked if should_standby and not model_standby: params_memory.put_bool("ModelStandby", True) params_memory.put("ModelFps", "0") diff --git a/selfdrive/ui/qt/onroad.cc b/selfdrive/ui/qt/onroad.cc index 8c786f2..ff2962e 100755 --- a/selfdrive/ui/qt/onroad.cc +++ b/selfdrive/ui/qt/onroad.cc @@ -607,9 +607,9 @@ void AnnotatedCameraWidget::drawSpeedLimitSign(QPainter &p) { p.setFont(InterFont(30, QFont::Bold)); p.drawText(innerRect.adjusted(0, 48, 0, 0), Qt::AlignTop | Qt::AlignHCenter, "LIMIT"); - // Speed limit number + // Speed limit number — shifted down ~10% of innerRect height via extra top inset p.setFont(InterFont(90, QFont::Bold)); - p.drawText(innerRect.adjusted(0, 42, 0, 0), Qt::AlignCenter, clpSpeedLimitDisplay); + p.drawText(innerRect.adjusted(0, 86, 0, 0), Qt::AlignCenter, clpSpeedLimitDisplay); } else { // Normal: white background, black border and text QColor borderColor(0, 0, 0); @@ -635,9 +635,9 @@ void AnnotatedCameraWidget::drawSpeedLimitSign(QPainter &p) { p.setFont(InterFont(30, QFont::Bold)); p.drawText(innerRect.adjusted(0, 48, 0, 0), Qt::AlignTop | Qt::AlignHCenter, "LIMIT"); - // Speed limit number + // Speed limit number — shifted down ~10% of innerRect height via extra top inset p.setFont(InterFont(90, QFont::Bold)); - p.drawText(innerRect.adjusted(0, 42, 0, 0), Qt::AlignCenter, clpSpeedLimitDisplay); + p.drawText(innerRect.adjusted(0, 86, 0, 0), Qt::AlignCenter, clpSpeedLimitDisplay); } p.restore(); @@ -691,7 +691,7 @@ void AnnotatedCameraWidget::drawCruiseWarningSign(QPainter &p) { // Cruise speed number p.setFont(InterFont(90, QFont::Bold)); - p.drawText(innerRect.adjusted(0, 42, 0, 0), Qt::AlignCenter, clpCruiseWarningSpeed); + p.drawText(innerRect.adjusted(0, 86, 0, 0), Qt::AlignCenter, clpCruiseWarningSpeed); } else { // Normal: colored background with white border/text QColor bgColor = isOver ? QColor(200, 30, 30, 240) : QColor(40, 160, 60, 240); @@ -717,7 +717,7 @@ void AnnotatedCameraWidget::drawCruiseWarningSign(QPainter &p) { // Cruise speed number p.setFont(InterFont(90, QFont::Bold)); - p.drawText(innerRect.adjusted(0, 42, 0, 0), Qt::AlignCenter, clpCruiseWarningSpeed); + p.drawText(innerRect.adjusted(0, 86, 0, 0), Qt::AlignCenter, clpCruiseWarningSpeed); } p.restore(); @@ -733,12 +733,14 @@ void AnnotatedCameraWidget::drawText(QPainter &p, int x, int y, const QString &t // CLEARPILOT: System health overlay — shows metrics that indicate the system // is overburdened or behind. Toggled via ClearpilotShowHealthMetrics param. -// Metrics (top→bottom): LAG, DROP, TEMP, CPU, MEM -// LAG (ms): controlsd cumLagMs — most direct "is the loop keeping up" indicator +// Metrics (top→bottom): FPS, DROP, TEMP, CPU, MEM, FAN +// FPS: modeld framerate — 20 normally, 0 in park. Read from ModelFps memory +// param which modeld writes only on transition. // DROP (%): modelV2 frameDropPerc — modeld losing frames; controlsd errors >20% // TEMP (°C): deviceState.maxTempC — thermal throttling starts ~75, serious >88 // CPU (%): max core from deviceState.cpuUsagePercent // MEM (%): deviceState.memoryUsagePercent +// FAN (%): actual fan duty from peripheralState RPM (scaled to 6500 RPM = 100%) // Each value color-codes green/yellow/red by severity. void AnnotatedCameraWidget::drawHealthMetrics(QPainter &p) { static bool enabled = Params().getBool("ClearpilotShowHealthMetrics"); @@ -751,12 +753,11 @@ void AnnotatedCameraWidget::drawHealthMetrics(QPainter &p) { if (!enabled) return; SubMaster &sm = *(uiState()->sm); - auto cs = sm["controlsState"].getControlsState(); auto ds = sm["deviceState"].getDeviceState(); auto mv = sm["modelV2"].getModelV2(); auto ps = sm["peripheralState"].getPeripheralState(); - float lag_ms = cs.getCumLagMs(); + int model_fps = paramsMemory.getInt("ModelFps"); float drop_pct = mv.getFrameDropPerc(); float temp_c = ds.getMaxTempC(); int mem_pct = ds.getMemoryUsagePercent(); @@ -773,7 +774,7 @@ void AnnotatedCameraWidget::drawHealthMetrics(QPainter &p) { struct Row { QString label; QString value; QColor color; }; Row rows[] = { - {"LAG", QString::number((int)lag_ms), color_for(lag_ms, 50.f, 200.f)}, + {"FPS", QString::number(model_fps), QColor(0xff, 0xff, 0xff)}, {"DROP", QString::number((int)drop_pct),color_for(drop_pct, 5.f, 15.f)}, {"TEMP", QString::number((int)temp_c), color_for(temp_c, 75.f, 88.f)}, {"CPU", QString::number(cpu_pct), color_for((float)cpu_pct, 75.f, 90.f)},