mirror of
https://github.com/firestar5683/StarPilot.git
synced 2026-06-28 01:52:06 +08:00
Pond Updates
This commit is contained in:
@@ -43,6 +43,13 @@
|
||||
}
|
||||
|
||||
/* ――― Search / Filter ――― */
|
||||
.ds-search-row {
|
||||
align-items: center;
|
||||
display: flex;
|
||||
gap: 0.5rem;
|
||||
margin-bottom: var(--margin-lg);
|
||||
}
|
||||
|
||||
.ds-search {
|
||||
background-color: var(--input-bg);
|
||||
border: var(--border-style-input);
|
||||
@@ -51,17 +58,37 @@
|
||||
color: var(--text-color);
|
||||
font-family: var(--font-body);
|
||||
font-size: var(--font-size-base);
|
||||
margin-bottom: var(--margin-lg);
|
||||
margin-bottom: 0;
|
||||
outline: none;
|
||||
padding: var(--padding-sm) var(--padding-base);
|
||||
transition: box-shadow var(--transition-fast);
|
||||
width: 100%;
|
||||
flex: 1;
|
||||
}
|
||||
|
||||
.ds-search:focus {
|
||||
box-shadow: 0 0 0 2px var(--main-fg);
|
||||
}
|
||||
|
||||
.ds-search-clear {
|
||||
background: var(--input-bg);
|
||||
border: var(--border-style-main);
|
||||
border-radius: var(--border-radius-base);
|
||||
color: var(--text-color);
|
||||
cursor: pointer;
|
||||
font-family: var(--font-body);
|
||||
font-size: var(--font-size-sm);
|
||||
min-width: 4.75rem;
|
||||
padding: 0.6rem 0.8rem;
|
||||
transition: background-color var(--transition-fast), border-color var(--transition-fast), color var(--transition-fast);
|
||||
}
|
||||
|
||||
.ds-search-clear:hover {
|
||||
background: var(--main-fg);
|
||||
border-color: var(--main-fg);
|
||||
color: var(--color-black);
|
||||
}
|
||||
|
||||
/* ――― Section Cards ――― */
|
||||
.ds-section {
|
||||
background-color: var(--secondary-bg);
|
||||
@@ -397,6 +424,15 @@
|
||||
padding: var(--padding-sm) var(--padding-base) var(--padding-xl);
|
||||
}
|
||||
|
||||
.ds-search-row {
|
||||
align-items: stretch;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.ds-search-clear {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.ds-tabs {
|
||||
flex-wrap: nowrap;
|
||||
overflow-x: auto;
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
import { html, reactive } from "https://esm.sh/@arrow-js/core"
|
||||
import { Navigate } from "/assets/components/router.js"
|
||||
|
||||
const endpointOptionsCache = {}
|
||||
const endpointOptionsInflight = {}
|
||||
@@ -501,6 +500,29 @@ function matchesFilter(p) {
|
||||
return p.label.toLowerCase().includes(q) || p.key.toLowerCase().includes(q)
|
||||
}
|
||||
|
||||
function clearSearchFilter() {
|
||||
if (!state.filter) return
|
||||
state.filter = ""
|
||||
scheduleSyncInputs()
|
||||
}
|
||||
|
||||
function handleSectionTabClick(sectionSlug, event) {
|
||||
if (!sectionSlug || sectionSlug === state.activeSectionSlug) return
|
||||
|
||||
// Preserve horizontal tab strip position on mobile when switching sections.
|
||||
const tabsEl = event?.currentTarget?.closest(".ds-tabs")
|
||||
const preservedScrollLeft = tabsEl ? tabsEl.scrollLeft : null
|
||||
|
||||
state.activeSectionSlug = sectionSlug
|
||||
|
||||
if (preservedScrollLeft !== null) {
|
||||
requestAnimationFrame(() => {
|
||||
const nextTabsEl = document.getElementById("ds-tabs")
|
||||
if (nextTabsEl) nextTabsEl.scrollLeft = preservedScrollLeft
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
function renderSettingRow(p) {
|
||||
if (p.parent_key && !state.filter) {
|
||||
if (!state.values[p.parent_key]) return ""
|
||||
@@ -619,14 +641,27 @@ export function DeviceSettings({ params }) {
|
||||
<div class="ds-wrapper">
|
||||
<h2>Toggles</h2>
|
||||
|
||||
<input
|
||||
class="ds-search"
|
||||
type="text"
|
||||
placeholder="Search settings..."
|
||||
@input="${(e) => {
|
||||
state.filter = e.target.value
|
||||
scheduleSyncInputs()
|
||||
}}" />
|
||||
<div class="ds-search-row">
|
||||
<input
|
||||
class="ds-search"
|
||||
type="text"
|
||||
placeholder="Search settings..."
|
||||
value="${() => state.filter}"
|
||||
@keydown="${(e) => {
|
||||
if (e.key === "Escape") clearSearchFilter()
|
||||
}}"
|
||||
@input="${(e) => {
|
||||
state.filter = e.target.value
|
||||
scheduleSyncInputs()
|
||||
}}" />
|
||||
${() => state.filter ? html`
|
||||
<button
|
||||
class="ds-search-clear"
|
||||
@click="${() => clearSearchFilter()}">
|
||||
Clear
|
||||
</button>
|
||||
` : ""}
|
||||
</div>
|
||||
|
||||
${() => {
|
||||
if (state.loadingLayout || state.loadingValues) {
|
||||
@@ -678,14 +713,12 @@ export function DeviceSettings({ params }) {
|
||||
const visibleParams = activeSection.params.filter(p => matchesFilter(p))
|
||||
|
||||
return html`
|
||||
<div class="ds-tabs">
|
||||
<div class="ds-tabs" id="ds-tabs">
|
||||
${sections.map(section => html`
|
||||
<button
|
||||
class="ds-tab ${section.slug === state.activeSectionSlug ? "active" : ""}"
|
||||
@click="${() => {
|
||||
if (section.slug !== state.activeSectionSlug) {
|
||||
Navigate("/device_settings/" + section.slug)
|
||||
}
|
||||
@click="${(e) => {
|
||||
handleSectionTabClick(section.slug, e)
|
||||
}}">
|
||||
<i class="bi ${section.icon}"></i>
|
||||
<span>${section.name}</span>
|
||||
|
||||
@@ -811,12 +811,52 @@
|
||||
"ui_type": "toggle",
|
||||
"is_parent_toggle": true
|
||||
},
|
||||
{
|
||||
"key": "AccelerationProfile",
|
||||
"label": "Acceleration Profile",
|
||||
"description": "How quickly openpilot speeds up: Eco, Normal, Sport, or Sport+.",
|
||||
"data_type": "int",
|
||||
"ui_type": "dropdown",
|
||||
"options": [
|
||||
{
|
||||
"value": 0,
|
||||
"label": "Normal"
|
||||
},
|
||||
{
|
||||
"value": 1,
|
||||
"label": "Eco"
|
||||
},
|
||||
{
|
||||
"value": 2,
|
||||
"label": "Sport"
|
||||
},
|
||||
{
|
||||
"value": 3,
|
||||
"label": "Sport+"
|
||||
}
|
||||
],
|
||||
"parent_key": "LongitudinalTune"
|
||||
},
|
||||
{
|
||||
"key": "DecelerationProfile",
|
||||
"label": "Deceleration Profile",
|
||||
"description": "How firmly openpilot slows down. \"Eco\" favors",
|
||||
"data_type": "bool",
|
||||
"ui_type": "toggle",
|
||||
"description": "How firmly openpilot slows down: Eco, Normal, or Sport.",
|
||||
"data_type": "int",
|
||||
"ui_type": "dropdown",
|
||||
"options": [
|
||||
{
|
||||
"value": 0,
|
||||
"label": "Normal"
|
||||
},
|
||||
{
|
||||
"value": 1,
|
||||
"label": "Eco"
|
||||
},
|
||||
{
|
||||
"value": 2,
|
||||
"label": "Sport"
|
||||
}
|
||||
],
|
||||
"parent_key": "LongitudinalTune"
|
||||
},
|
||||
{
|
||||
|
||||
@@ -183,6 +183,8 @@ _fast_update_state = {
|
||||
}
|
||||
|
||||
_PLOTS_POLL_INTERVAL_S = 0.5
|
||||
_PLOTS_BOOT_STABILIZATION_WINDOW_S = 45.0
|
||||
_PLOTS_BOOT_POLL_INTERVAL_S = 1.0
|
||||
_PLOTS_CLIENT_IDLE_TIMEOUT_S = 15.0
|
||||
_PLOTS_SAMPLE_STALE_AFTER_S = 1.5
|
||||
|
||||
@@ -220,6 +222,18 @@ def _safe_float(value, default=0.0):
|
||||
except Exception:
|
||||
return float(default)
|
||||
|
||||
def _get_system_uptime_seconds():
|
||||
try:
|
||||
with open("/proc/uptime", "r", encoding="utf-8") as uptime_file:
|
||||
return _safe_float((uptime_file.read().split() or ["0"])[0], 0.0)
|
||||
except Exception:
|
||||
return 0.0
|
||||
|
||||
def _is_plots_boot_stabilizing():
|
||||
if not params.get_bool("IsOnroad"):
|
||||
return False
|
||||
return _get_system_uptime_seconds() < _PLOTS_BOOT_STABILIZATION_WINDOW_S
|
||||
|
||||
def _extract_lateral_accel_values(controls_state, speed_mps):
|
||||
v_ego = max(0.0, _safe_float(speed_mps))
|
||||
speed_sq = v_ego * v_ego
|
||||
@@ -353,7 +367,10 @@ def _plots_worker():
|
||||
with _plots_lock:
|
||||
_plots_state["lastError"] = str(exception)
|
||||
|
||||
time.sleep(_PLOTS_POLL_INTERVAL_S)
|
||||
sleep_interval = _PLOTS_POLL_INTERVAL_S
|
||||
if _is_plots_boot_stabilizing():
|
||||
sleep_interval = max(_PLOTS_POLL_INTERVAL_S, _PLOTS_BOOT_POLL_INTERVAL_S)
|
||||
time.sleep(sleep_interval)
|
||||
|
||||
with _plots_lock:
|
||||
_plots_worker_thread = None
|
||||
@@ -2547,6 +2564,7 @@ def setup(app):
|
||||
return jsonify({
|
||||
**payload,
|
||||
"isOnroad": params.get_bool("IsOnroad"),
|
||||
"bootStabilizing": _is_plots_boot_stabilizing(),
|
||||
"sampleAgeSeconds": round(age_seconds, 3),
|
||||
"stale": age_seconds > _PLOTS_SAMPLE_STALE_AFTER_S,
|
||||
}), 200
|
||||
|
||||
@@ -121,9 +121,10 @@ procs = [
|
||||
PythonProcess("frogpilot_process", "frogpilot.frogpilot_process", always_run),
|
||||
PythonProcess("mapd", "frogpilot.navigation.mapd", always_run),
|
||||
PythonProcess("speed_limit_filler", "frogpilot.system.speed_limit_filler", run_speed_limit_filler),
|
||||
# Lower priority so onroad processes win CPU time if The Pond is busy.
|
||||
PythonProcess("the_pond", "frogpilot.system.the_pond.the_pond", always_run, nice=15),
|
||||
PythonProcess("galaxy", "frogpilot.system.galaxy.galaxy", always_run),
|
||||
# Keep remote UI/tunnel services at the lowest scheduling priority so
|
||||
# driving-critical processes always win CPU under startup or onroad load.
|
||||
PythonProcess("the_pond", "frogpilot.system.the_pond.the_pond", always_run, nice=19),
|
||||
PythonProcess("galaxy", "frogpilot.system.galaxy.galaxy", always_run, nice=19),
|
||||
PythonProcess("tinygrad_modeld", "frogpilot.tinygrad_modeld.tinygrad_modeld", run_tinygrad_modeld),
|
||||
]
|
||||
|
||||
|
||||
Reference in New Issue
Block a user