mirror of
https://github.com/sunnypilot/sunnypilot.git
synced 2026-06-26 16:12:06 +08:00
Compare commits
15 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| ac65fb5f54 | |||
| 801a17edea | |||
| f4f48ee55c | |||
| 8bddfda0dd | |||
| a9aa92bfcf | |||
| a29714a610 | |||
| c51e74e6af | |||
| c392b2b269 | |||
| 213b977774 | |||
| f1837b8502 | |||
| 3e7240516e | |||
| 403d77ff3f | |||
| 9fe4d7ecc7 | |||
| 8d7315fa28 | |||
| 3e4be4a393 |
@@ -1,2 +1,3 @@
|
||||
Wen
|
||||
REGIST
|
||||
PullRequest
|
||||
|
||||
@@ -0,0 +1,162 @@
|
||||
name: Nightly Branch Reset and PR Squash
|
||||
|
||||
env:
|
||||
DEFAULT_SOURCE_BRANCH: "master-new"
|
||||
DEFAULT_TARGET_BRANCH: "nightly"
|
||||
PR_LABEL: "dev-c3"
|
||||
|
||||
on:
|
||||
workflow_dispatch:
|
||||
inputs:
|
||||
source_branch:
|
||||
description: 'Source branch to reset from'
|
||||
required: true
|
||||
default: 'master-new'
|
||||
type: string
|
||||
target_branch:
|
||||
description: 'Target branch to reset and squash into'
|
||||
required: true
|
||||
default: 'master-dev-c3-new'
|
||||
type: string
|
||||
# schedule:
|
||||
# - cron: '0 0 * * *' # Run at midnight UTC for nightly
|
||||
|
||||
jobs:
|
||||
reset-and-squash:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
with:
|
||||
fetch-depth: 0 # Fetch all history for all branches
|
||||
token: ${{ secrets.GITHUB_TOKEN }}
|
||||
|
||||
- name: Configure Git
|
||||
run: |
|
||||
git config --global user.name 'github-actions[bot]'
|
||||
git config --global user.email 'github-actions[bot]@users.noreply.github.com'
|
||||
|
||||
- name: Set up Python
|
||||
uses: actions/setup-python@v5
|
||||
with:
|
||||
python-version: '3.10'
|
||||
|
||||
- name: Install dependencies
|
||||
run: |
|
||||
python -m pip install --upgrade pip
|
||||
pip install PyGithub
|
||||
|
||||
- name: Check branches exist
|
||||
run: |
|
||||
# Check if source branch exists
|
||||
if ! git ls-remote --heads origin ${{ inputs.source_branch || env.DEFAULT_SOURCE_BRANCH }} | grep -q "${{ inputs.source_branch || env.DEFAULT_SOURCE_BRANCH }}"; then
|
||||
echo "Source branch ${{ inputs.source_branch || env.DEFAULT_SOURCE_BRANCH }} does not exist!"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# Make sure we have the latest source branch
|
||||
git fetch origin ${{ inputs.source_branch || env.DEFAULT_SOURCE_BRANCH }}
|
||||
|
||||
# Check if target branch exists
|
||||
if ! git ls-remote --heads origin ${{ inputs.target_branch || env.DEFAULT_TARGET_BRANCH }} | grep -q "${{ inputs.target_branch || env.DEFAULT_TARGET_BRANCH }}"; then
|
||||
echo "Target branch ${{ inputs.target_branch || env.DEFAULT_TARGET_BRANCH }} does not exist, creating it from ${{ inputs.source_branch || env.DEFAULT_SOURCE_BRANCH }}"
|
||||
git checkout -b ${{ inputs.target_branch || env.DEFAULT_TARGET_BRANCH }} origin/${{ inputs.source_branch || env.DEFAULT_SOURCE_BRANCH }}
|
||||
git push origin ${{ inputs.target_branch || env.DEFAULT_TARGET_BRANCH }}
|
||||
else
|
||||
# Fetch target branch if it exists
|
||||
git fetch origin ${{ inputs.target_branch || env.DEFAULT_TARGET_BRANCH }}
|
||||
fi
|
||||
|
||||
- name: Reset target branch
|
||||
run: |
|
||||
echo "Resetting ${{ inputs.target_branch || env.DEFAULT_TARGET_BRANCH }} to match ${{ inputs.source_branch || env.DEFAULT_SOURCE_BRANCH }}"
|
||||
# Delete if exists and recreate pointing to source
|
||||
git branch -D ${{ inputs.target_branch || env.DEFAULT_TARGET_BRANCH }} || true
|
||||
git branch ${{ inputs.target_branch || env.DEFAULT_TARGET_BRANCH }} origin/${{ inputs.source_branch || env.DEFAULT_SOURCE_BRANCH }}
|
||||
|
||||
- name: Get PRs to squash
|
||||
id: get-prs
|
||||
run: |
|
||||
# Use GitHub API to get PRs with specific label, ordered by creation date
|
||||
PR_LIST=$(gh api graphql -f query='
|
||||
query($label:String!) {
|
||||
search(query: $label, type:ISSUE, first:100) {
|
||||
nodes {
|
||||
... on PullRequest {
|
||||
number
|
||||
headRefName
|
||||
title
|
||||
createdAt
|
||||
commits(last: 1) {
|
||||
nodes {
|
||||
commit {
|
||||
statusCheckRollup {
|
||||
state
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}' -F label="is:pr is:open label:${PR_LABEL} sort:created-asc")
|
||||
|
||||
echo "PR_LIST=${PR_LIST}" >> $GITHUB_OUTPUT
|
||||
env:
|
||||
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||
|
||||
- name: Process PRs
|
||||
run: |
|
||||
python3 ${{ github.workspace }}/release/ci/squash_and_merge_prs.py \
|
||||
--pr-data '${{ steps.get-prs.outputs.PR_LIST }}' \
|
||||
--target-branch ${{ inputs.target_branch || env.DEFAULT_TARGET_BRANCH }} \
|
||||
--squash-script-path '${{ github.workspace }}/release/ci/squash_and_merge.py'
|
||||
env:
|
||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||
|
||||
- name: Push changes if there are diffs
|
||||
id: push-changes # Add an id so we can reference this step
|
||||
run: |
|
||||
TARGET_BRANCH="${{ inputs.target_branch || env.DEFAULT_TARGET_BRANCH }}"
|
||||
|
||||
# Fetch the latest from remote
|
||||
git fetch origin $TARGET_BRANCH
|
||||
|
||||
# Check for diffs between local and remote
|
||||
if git diff $TARGET_BRANCH origin/$TARGET_BRANCH --quiet; then
|
||||
echo "No changes to push - local and remote branches are identical"
|
||||
echo "has_changes=false" >> $GITHUB_OUTPUT
|
||||
exit 0
|
||||
fi
|
||||
|
||||
# If we get here, there are diffs, so push
|
||||
if ! git push origin $TARGET_BRANCH --force; then
|
||||
echo "Failed to push changes to $TARGET_BRANCH"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
echo "Branch $TARGET_BRANCH has been reset and updated with squashed PRs"
|
||||
echo "has_changes=true" >> $GITHUB_OUTPUT
|
||||
|
||||
- name: Trigger and wait for selfdrive tests
|
||||
if: steps.push-changes.outputs.has_changes == 'true'
|
||||
run: |
|
||||
echo "Triggering selfdrive tests..."
|
||||
gh workflow run selfdrive_tests.yaml --ref "${{ inputs.target_branch || env.DEFAULT_TARGET_BRANCH }}"
|
||||
|
||||
echo "Sleeping for 120s to give plenty of time for the action to start and then we wait"
|
||||
sleep 120
|
||||
|
||||
echo "Getting latest run ID..."
|
||||
RUN_ID=$(gh run list --workflow=selfdrive_tests.yaml --branch="${{ inputs.target_branch || env.DEFAULT_TARGET_BRANCH }}" --limit=1 --json databaseId --jq '.[0].databaseId')
|
||||
|
||||
echo "Watching run ID: $RUN_ID"
|
||||
gh run watch "$RUN_ID"
|
||||
env:
|
||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||
|
||||
- name: Trigger prebuilt workflow
|
||||
if: success() && steps.push-changes.outputs.has_changes == 'true'
|
||||
run: |
|
||||
gh workflow run sunnypilot-build-prebuilt.yaml --ref "${{ inputs.target_branch || env.DEFAULT_TARGET_BRANCH }}"
|
||||
env:
|
||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||
@@ -86,7 +86,7 @@ jobs:
|
||||
run: >-
|
||||
sudo apt-get install -y imagemagick
|
||||
|
||||
scenes="homescreen settings_device settings_software settings_sunnylink settings_toggles settings_sunnypilot settings_sunnypilot_mads settings_trips settings_developer offroad_alert update_available prime onroad onroad_disengaged onroad_override onroad_sidebar onroad_wide onroad_wide_sidebar onroad_alert_small onroad_alert_mid onroad_alert_full driver_camera body keyboard keyboard_uppercase"
|
||||
scenes="homescreen settings_device settings_network settings_network_advanced settings_software settings_sunnylink settings_toggles settings_sunnypilot settings_sunnypilot_mads settings_trips settings_vehicle settings_developer offroad_alert update_available prime onroad onroad_disengaged onroad_override onroad_sidebar onroad_wide onroad_wide_sidebar onroad_alert_small onroad_alert_mid onroad_alert_full driver_camera body keyboard keyboard_uppercase"
|
||||
A=($scenes)
|
||||
|
||||
DIFF=""
|
||||
|
||||
+25
-16
@@ -10,23 +10,23 @@ $Cxx.namespace("cereal");
|
||||
# DO rename the structs
|
||||
# DON'T change the identifier (e.g. @0x81c2f05a394cf4af)
|
||||
|
||||
struct ModularAssistiveDrivingSystem {
|
||||
state @0 :ModularAssistiveDrivingSystemState;
|
||||
enabled @1 :Bool;
|
||||
active @2 :Bool;
|
||||
available @3 :Bool;
|
||||
|
||||
enum ModularAssistiveDrivingSystemState {
|
||||
disabled @0;
|
||||
paused @1;
|
||||
enabled @2;
|
||||
softDisabling @3;
|
||||
overriding @4;
|
||||
}
|
||||
}
|
||||
|
||||
struct SelfdriveStateSP @0x81c2f05a394cf4af {
|
||||
mads @0 :ModularAssistiveDrivingSystem;
|
||||
|
||||
struct ModularAssistiveDrivingSystem {
|
||||
state @0 :ModularAssistiveDrivingSystemState;
|
||||
enabled @1 :Bool;
|
||||
active @2 :Bool;
|
||||
available @3 :Bool;
|
||||
|
||||
enum ModularAssistiveDrivingSystemState {
|
||||
disabled @0;
|
||||
paused @1;
|
||||
enabled @2;
|
||||
softDisabling @3;
|
||||
overriding @4;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
struct ModelManagerSP @0xaedffd8f31e7b55d {
|
||||
@@ -87,6 +87,7 @@ struct ModelManagerSP @0xaedffd8f31e7b55d {
|
||||
|
||||
struct LongitudinalPlanSP @0xf35cc4560bbf6ec2 {
|
||||
dec @0 :DynamicExperimentalControl;
|
||||
accelPersonality @1 :AccelerationPersonality;
|
||||
|
||||
struct DynamicExperimentalControl {
|
||||
state @0 :DynamicExperimentalControlState;
|
||||
@@ -98,6 +99,13 @@ struct LongitudinalPlanSP @0xf35cc4560bbf6ec2 {
|
||||
blended @1;
|
||||
}
|
||||
}
|
||||
|
||||
enum AccelerationPersonality {
|
||||
sport @0;
|
||||
normal @1;
|
||||
eco @2;
|
||||
stock @3;
|
||||
}
|
||||
}
|
||||
|
||||
struct OnroadEventSP @0xda96579883444c35 {
|
||||
@@ -138,7 +146,8 @@ struct CarParamsSP @0x80ae746ee2596b11 {
|
||||
flags @0 :UInt32; # flags for car specific quirks in sunnypilot
|
||||
}
|
||||
|
||||
struct CustomReserved5 @0xa5cd762cd951a455 {
|
||||
struct CarControlSP @0xa5cd762cd951a455 {
|
||||
mads @0 :ModularAssistiveDrivingSystem;
|
||||
}
|
||||
|
||||
struct CustomReserved6 @0xf98d843bfd7004a3 {
|
||||
|
||||
+1
-1
@@ -2570,7 +2570,7 @@ struct Event {
|
||||
longitudinalPlanSP @109 :Custom.LongitudinalPlanSP;
|
||||
onroadEventsSP @110 :List(Custom.OnroadEventSP);
|
||||
carParamsSP @111 :Custom.CarParamsSP;
|
||||
customReserved5 @112 :Custom.CustomReserved5;
|
||||
carControlSP @112 :Custom.CarControlSP;
|
||||
customReserved6 @113 :Custom.CustomReserved6;
|
||||
customReserved7 @114 :Custom.CustomReserved7;
|
||||
customReserved8 @115 :Custom.CustomReserved8;
|
||||
|
||||
@@ -80,6 +80,7 @@ _services: dict[str, tuple] = {
|
||||
"longitudinalPlanSP": (True, 20., 10),
|
||||
"onroadEventsSP": (True, 1., 1),
|
||||
"carParamsSP": (True, 0.02, 1),
|
||||
"carControlSP": (True, 100., 10),
|
||||
|
||||
# debug
|
||||
"uiDebug": (True, 0., 1),
|
||||
|
||||
@@ -236,6 +236,7 @@ std::unordered_map<std::string, uint32_t> keys = {
|
||||
{"HyundaiRadarTracksToggle", PERSISTENT},
|
||||
|
||||
{"DynamicExperimentalControl", PERSISTENT},
|
||||
{"AccelPersonality", PERSISTENT},
|
||||
};
|
||||
|
||||
} // namespace
|
||||
|
||||
+1
-1
Submodule opendbc_repo updated: fec0423422...5e5885c75b
@@ -117,7 +117,7 @@ def workspace_manager(original_branch: str):
|
||||
if temp_branch:
|
||||
run_command(f"git branch -D {temp_branch}")
|
||||
print("\nOperation interrupted, but changes were already restored.")
|
||||
sys.exit(1)
|
||||
sys.exit(3)
|
||||
|
||||
# First, switch back to original branch
|
||||
current = get_current_branch()
|
||||
@@ -139,12 +139,12 @@ def workspace_manager(original_branch: str):
|
||||
|
||||
if signum:
|
||||
print("\nOperation interrupted. Cleaned up and restored original state.")
|
||||
sys.exit(1)
|
||||
sys.exit(4)
|
||||
|
||||
except Exception as e:
|
||||
print(f"Error during cleanup: {e}")
|
||||
if signum:
|
||||
sys.exit(1)
|
||||
sys.exit(5)
|
||||
|
||||
try:
|
||||
# Set up signal handlers
|
||||
@@ -275,7 +275,7 @@ def squash_and_merge(source_branch: str, target_branch: str, manual_title: str |
|
||||
return False
|
||||
|
||||
print(f"Attempting to merge changes from {temp_branch}...")
|
||||
code, _, error = run_command(f"git merge {temp_branch}")
|
||||
code, _, error = run_command(f"git rebase {temp_branch}")
|
||||
|
||||
if code != 0:
|
||||
print(f"\nMerge failed with error: {error}")
|
||||
@@ -344,7 +344,7 @@ def main():
|
||||
parser.add_argument('--push', action='store_true',
|
||||
help='Push changes to remote after squashing')
|
||||
|
||||
args = parser.parse_args()
|
||||
args, unknown = parser.parse_known_args()
|
||||
|
||||
# Determine source branch early
|
||||
source_branch = args.source
|
||||
@@ -354,7 +354,7 @@ def main():
|
||||
sys.exit(1)
|
||||
|
||||
if not squash_and_merge(source_branch, args.target, args.title, args.backup, args.push):
|
||||
sys.exit(1)
|
||||
sys.exit(2)
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
|
||||
Executable
+163
@@ -0,0 +1,163 @@
|
||||
#!/usr/bin/env python3
|
||||
|
||||
import subprocess
|
||||
import sys
|
||||
import os
|
||||
import argparse
|
||||
import json
|
||||
from datetime import datetime
|
||||
|
||||
|
||||
def setup_argument_parser():
|
||||
parser = argparse.ArgumentParser(description='Process and squash GitHub PRs')
|
||||
parser.add_argument('--pr-data', type=str, help='PR data in JSON format')
|
||||
parser.add_argument('--source-branch', type=str, default='master-new',
|
||||
help='Source branch for merging')
|
||||
parser.add_argument('--target-branch', type=str, default='master-dev-c3-new-test',
|
||||
help='Target branch for merging')
|
||||
parser.add_argument('--squash-script-path', type=str, required=True,
|
||||
help='Path to the squash_and_merge.py script')
|
||||
return parser
|
||||
|
||||
|
||||
def validate_squash_script(script_path):
|
||||
if not os.path.isfile(script_path):
|
||||
raise FileNotFoundError(f"Squash script not found at: {script_path}")
|
||||
if not os.access(script_path, os.X_OK):
|
||||
raise PermissionError(f"Squash script is not executable: {script_path}")
|
||||
|
||||
|
||||
def sort_prs_by_creation(pr_data):
|
||||
"""Sort PRs by creation date"""
|
||||
nodes = (pr_data.get('data', {}).get('search', {}).get('nodes', []))
|
||||
|
||||
return sorted(
|
||||
nodes,
|
||||
key=lambda x: datetime.fromisoformat(x.get('createdAt', '').replace('Z', '+00:00'))
|
||||
)
|
||||
|
||||
|
||||
def add_pr_comment(pr_number, comment):
|
||||
"""Add a comment to a PR using gh cli"""
|
||||
try:
|
||||
subprocess.run(
|
||||
['gh', 'pr', 'comment', str(pr_number), '--body', comment],
|
||||
check=True,
|
||||
capture_output=True,
|
||||
text=True
|
||||
)
|
||||
except subprocess.CalledProcessError as e:
|
||||
print(f"Failed to add comment to PR #{pr_number}: {e.stderr}")
|
||||
|
||||
|
||||
def validate_pr(pr):
|
||||
"""Validate a PR and return (is_valid, skip_reason)"""
|
||||
pr_number = pr.get('number', 'UNKNOWN')
|
||||
branch = pr.get('headRefName', '')
|
||||
|
||||
if not branch:
|
||||
return False, f"Missing branch name for PR #{pr_number}"
|
||||
|
||||
# Check if checks have passed
|
||||
commits = pr.get('commits', {}).get('nodes', [])
|
||||
if not commits:
|
||||
return False, "No commit data found"
|
||||
|
||||
status = commits[0].get('commit', {}).get('statusCheckRollup', {})
|
||||
if not status or status.get('state') != 'SUCCESS':
|
||||
return False, "Not all checks have passed"
|
||||
|
||||
# Check for merge conflicts
|
||||
merge_status = subprocess.run(['gh', 'pr', 'view', str(pr_number), '--json', 'mergeable,mergeStateStatus'], capture_output=True, text=True)
|
||||
merge_data = json.loads(merge_status.stdout)
|
||||
if not merge_data.get('mergeable'):
|
||||
return False, "Merge conflicts detected"
|
||||
|
||||
if (mergeStateStatus := merge_data.get('mergeStateStatus')) == "BEHIND":
|
||||
return False, f"Branch is `{mergeStateStatus}`"
|
||||
|
||||
return True, None
|
||||
|
||||
|
||||
def process_pr(pr_data, source_branch, target_branch, squash_script_path):
|
||||
try:
|
||||
nodes = sort_prs_by_creation(pr_data)
|
||||
if not nodes:
|
||||
print("No PRs to squash")
|
||||
return 0
|
||||
|
||||
print(f"Deleting target branch {target_branch}")
|
||||
subprocess.run(['git', 'branch', '-D', target_branch], check=False)
|
||||
subprocess.run(['git', 'branch', target_branch, f'origin/{source_branch}'], check=True)
|
||||
success_count = 0
|
||||
for pr in nodes:
|
||||
pr_number = pr.get('number', 'UNKNOWN')
|
||||
branch = pr.get('headRefName', '')
|
||||
title = pr.get('title', '')
|
||||
is_valid, skip_reason = validate_pr(pr)
|
||||
|
||||
if not is_valid:
|
||||
print(f"Warning: {skip_reason} for PR #{pr_number}, skipping")
|
||||
add_pr_comment(pr_number, f"⚠️ This PR was skipped in the automated `{target_branch}` squash because {skip_reason}.")
|
||||
continue
|
||||
|
||||
try:
|
||||
# Fetch PR branch
|
||||
subprocess.run(['git', 'fetch', 'origin', branch], check=True)
|
||||
# Delete branch if it exists (ignore errors if it doesn't)
|
||||
subprocess.run(['git', 'branch', '-D', branch], check=False)
|
||||
# Create new branch pointing to origin's branch
|
||||
subprocess.run(['git', 'branch', branch, f'origin/{branch}'], check=True)
|
||||
|
||||
# Run squash script
|
||||
subprocess.run([
|
||||
squash_script_path,
|
||||
'--target', target_branch,
|
||||
'--source', branch,
|
||||
'--title', f"{title} (#{pr_number})",
|
||||
], check=True)
|
||||
|
||||
print(f"Successfully processed PR #{pr_number}")
|
||||
success_count += 1
|
||||
|
||||
except subprocess.CalledProcessError as e:
|
||||
print(f"Error processing PR #{pr_number}:")
|
||||
print(f"Command failed with exit code {e.returncode}")
|
||||
error_output = getattr(e, 'stderr', 'No error output available')
|
||||
print(f"Error output: {error_output}")
|
||||
add_pr_comment(pr_number, f"⚠️ Error during automated {target_branch} squash:\n```\n{error_output}\n```")
|
||||
continue
|
||||
except Exception as e:
|
||||
print(f"Unexpected error processing PR #{pr_number}: {str(e)}")
|
||||
continue
|
||||
|
||||
return success_count
|
||||
|
||||
except Exception as e:
|
||||
import traceback
|
||||
print(f"Error in process_pr: {str(e)}")
|
||||
print("Full traceback:")
|
||||
print(traceback.format_exc())
|
||||
return 0
|
||||
|
||||
|
||||
def main():
|
||||
parser = setup_argument_parser()
|
||||
try:
|
||||
args = parser.parse_args()
|
||||
validate_squash_script(args.squash_script_path)
|
||||
pr_data_json = json.loads(args.pr_data)
|
||||
|
||||
# Process the PRs
|
||||
success_count = process_pr(pr_data_json, args.source_branch, args.target_branch, args.squash_script_path)
|
||||
print(f"Successfully processed {success_count} PRs")
|
||||
|
||||
except Exception as e:
|
||||
print(f"Fatal error: {str(e)}", file=sys.stderr)
|
||||
return 1
|
||||
|
||||
return 0
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
sys.exit(main())
|
||||
@@ -21,7 +21,7 @@ from opendbc.car.interfaces import CarInterfaceBase, RadarInterfaceBase
|
||||
from openpilot.selfdrive.pandad import can_capnp_to_list, can_list_to_can_capnp
|
||||
from openpilot.selfdrive.car.cruise import VCruiseHelper
|
||||
from openpilot.selfdrive.car.car_specific import MockCarState
|
||||
from openpilot.selfdrive.car.helpers import convert_to_capnp
|
||||
from openpilot.selfdrive.car.helpers import convert_carControlSP, convert_to_capnp
|
||||
|
||||
from openpilot.sunnypilot.mads.mads import MadsParams
|
||||
from openpilot.sunnypilot.selfdrive.car import interfaces
|
||||
@@ -72,11 +72,8 @@ class Car:
|
||||
|
||||
def __init__(self, CI=None, RI=None) -> None:
|
||||
self.can_sock = messaging.sub_sock('can', timeout=20)
|
||||
self.sm = messaging.SubMaster(['pandaStates', 'carControl', 'onroadEvents'])
|
||||
self.pm = messaging.PubMaster(['sendcan', 'carState', 'carParams', 'carOutput', 'liveTracks'])
|
||||
|
||||
sock_services = list(self.pm.sock.keys()) + ['carParamsSP']
|
||||
self.pm = messaging.PubMaster(sock_services)
|
||||
self.sm = messaging.SubMaster(['pandaStates', 'carControl', 'onroadEvents'] + ['carControlSP'])
|
||||
self.pm = messaging.PubMaster(['sendcan', 'carState', 'carParams', 'carOutput', 'liveTracks'] + ['carParamsSP'])
|
||||
|
||||
self.can_rcv_cum_timeout_counter = 0
|
||||
|
||||
@@ -267,7 +264,7 @@ class Car:
|
||||
cp_sp_send.carParamsSP = self.CP_SP_capnp
|
||||
self.pm.send('carParamsSP', cp_sp_send)
|
||||
|
||||
def controls_update(self, CS: car.CarState, CC: car.CarControl):
|
||||
def controls_update(self, CS: car.CarState, CC: car.CarControl, CC_SP: custom.CarControlSP):
|
||||
"""control update loop, driven by carControl"""
|
||||
|
||||
if not self.initialized_prev:
|
||||
@@ -281,7 +278,7 @@ class Car:
|
||||
if self.sm.all_alive(['carControl']):
|
||||
# send car controls over can
|
||||
now_nanos = self.can_log_mono_time if REPLAY else int(time.monotonic() * 1e9)
|
||||
self.last_actuators_output, can_sends = self.CI.apply(CC, now_nanos)
|
||||
self.last_actuators_output, can_sends = self.CI.apply(CC, convert_carControlSP(CC_SP), now_nanos)
|
||||
self.pm.send('sendcan', can_list_to_can_capnp(can_sends, msgtype='sendcan', valid=CS.canValid))
|
||||
|
||||
self.CC_prev = CC
|
||||
@@ -294,7 +291,7 @@ class Car:
|
||||
initialized = (not any(e.name == EventName.selfdriveInitializing for e in self.sm['onroadEvents']) and
|
||||
self.sm.seen['onroadEvents'])
|
||||
if not self.CP.passive and initialized:
|
||||
self.controls_update(CS, self.sm['carControl'])
|
||||
self.controls_update(CS, self.sm['carControl'], self.sm['carControlSP'])
|
||||
|
||||
self.initialized_prev = initialized
|
||||
self.CS_prev = CS
|
||||
|
||||
@@ -44,3 +44,16 @@ def convert_to_capnp(struct: structs.CarParamsSP) -> capnp.lib.capnp._DynamicStr
|
||||
raise ValueError(f"Unsupported struct type: {type(struct)}")
|
||||
|
||||
return struct_capnp
|
||||
|
||||
|
||||
def convert_carControlSP(struct: capnp.lib.capnp._DynamicStructReader) -> structs.CarControlSP:
|
||||
# TODO: recursively handle any car struct as needed
|
||||
def remove_deprecated(s: dict) -> dict:
|
||||
return {k: v for k, v in s.items() if not k.endswith('DEPRECATED')}
|
||||
|
||||
struct_dict = struct.to_dict()
|
||||
struct_dataclass = structs.CarControlSP(**remove_deprecated({k: v for k, v in struct_dict.items() if not isinstance(k, dict)}))
|
||||
|
||||
struct_dataclass.mads = structs.ModularAssistiveDrivingSystem(**remove_deprecated(struct_dict.get('mads', {})))
|
||||
|
||||
return struct_dataclass
|
||||
|
||||
@@ -4,7 +4,7 @@ import hypothesis.strategies as st
|
||||
from hypothesis import Phase, given, settings
|
||||
from parameterized import parameterized
|
||||
|
||||
from cereal import car
|
||||
from cereal import car, custom
|
||||
from opendbc.car import DT_CTRL
|
||||
from opendbc.car.car_helpers import interfaces
|
||||
from opendbc.car.structs import CarParams
|
||||
@@ -12,6 +12,7 @@ from opendbc.car.tests.test_car_interfaces import get_fuzzy_car_interface_args
|
||||
from opendbc.car.fingerprints import all_known_cars
|
||||
from opendbc.car.fw_versions import FW_VERSIONS, FW_QUERY_CONFIGS
|
||||
from opendbc.car.mock.values import CAR as MOCK
|
||||
from openpilot.selfdrive.car.helpers import convert_carControlSP
|
||||
from openpilot.selfdrive.controls.lib.latcontrol_angle import LatControlAngle
|
||||
from openpilot.selfdrive.controls.lib.latcontrol_pid import LatControlPID
|
||||
from openpilot.selfdrive.controls.lib.latcontrol_torque import LatControlTorque
|
||||
@@ -40,7 +41,7 @@ class TestCarInterfaces:
|
||||
|
||||
car_params = CarInterface.get_params(car_name, args['fingerprints'], args['car_fw'],
|
||||
experimental_long=args['experimental_long'], docs=False)
|
||||
car_params, car_params_sp = CarInterface.get_params_sp(car_params, car_name, args['fingerprints'], args['car_fw'],
|
||||
car_params_sp = CarInterface.get_params_sp(car_params, car_name, args['fingerprints'], args['car_fw'],
|
||||
experimental_long=args['experimental_long'], docs=False)
|
||||
car_params = car_params.as_reader()
|
||||
car_interface = CarInterface(car_params, car_params_sp, CarController, CarState)
|
||||
@@ -72,13 +73,16 @@ class TestCarInterfaces:
|
||||
assert not math.isnan(tune.torque.friction) and tune.torque.friction > 0
|
||||
|
||||
cc_msg = FuzzyGenerator.get_random_msg(data.draw, car.CarControl, real_floats=True)
|
||||
cc_sp_msg = FuzzyGenerator.get_random_msg(data.draw, custom.CarControlSP, real_floats=True)
|
||||
# Run car interface
|
||||
now_nanos = 0
|
||||
CC = car.CarControl.new_message(**cc_msg)
|
||||
CC = CC.as_reader()
|
||||
CC_SP = custom.CarControlSP.new_message(**cc_sp_msg)
|
||||
CC_SP = convert_carControlSP(CC_SP.as_reader())
|
||||
for _ in range(10):
|
||||
car_interface.update([])
|
||||
car_interface.apply(CC, now_nanos)
|
||||
car_interface.apply(CC, CC_SP, now_nanos)
|
||||
now_nanos += DT_CTRL * 1e9 # 10 ms
|
||||
|
||||
CC = car.CarControl.new_message(**cc_msg)
|
||||
@@ -86,7 +90,7 @@ class TestCarInterfaces:
|
||||
CC = CC.as_reader()
|
||||
for _ in range(10):
|
||||
car_interface.update([])
|
||||
car_interface.apply(CC, now_nanos)
|
||||
car_interface.apply(CC, CC_SP, now_nanos)
|
||||
now_nanos += DT_CTRL * 1e9 # 10ms
|
||||
|
||||
# Test controller initialization
|
||||
|
||||
@@ -159,7 +159,7 @@ class TestCarModelBase(unittest.TestCase):
|
||||
|
||||
cls.CarInterface, cls.CarController, cls.CarState, cls.RadarInterface = interfaces[cls.platform]
|
||||
cls.CP = cls.CarInterface.get_params(cls.platform, cls.fingerprint, car_fw, experimental_long, docs=False)
|
||||
cls.CP, cls.CP_SP = cls.CarInterface.get_params_sp(cls.CP, cls.platform, cls.fingerprint, car_fw, experimental_long, docs=False)
|
||||
cls.CP_SP = cls.CarInterface.get_params_sp(cls.CP, cls.platform, cls.fingerprint, car_fw, experimental_long, docs=False)
|
||||
assert cls.CP
|
||||
assert cls.CP_SP
|
||||
assert cls.CP.carFingerprint == cls.platform
|
||||
@@ -205,10 +205,11 @@ class TestCarModelBase(unittest.TestCase):
|
||||
can_invalid_cnt = 0
|
||||
can_valid = False
|
||||
CC = structs.CarControl().as_reader()
|
||||
CC_SP = structs.CarControlSP()
|
||||
|
||||
for i, msg in enumerate(self.can_msgs):
|
||||
CS = self.CI.update(can_capnp_to_list((msg.as_builder().to_bytes(),)))
|
||||
self.CI.apply(CC, msg.logMonoTime)
|
||||
self.CI.apply(CC, CC_SP, msg.logMonoTime)
|
||||
|
||||
if CS.canValid:
|
||||
can_valid = True
|
||||
@@ -277,13 +278,13 @@ class TestCarModelBase(unittest.TestCase):
|
||||
if self.CP.notCar:
|
||||
self.skipTest("Skipping test for notCar")
|
||||
|
||||
def test_car_controller(car_control):
|
||||
def test_car_controller(car_control, car_control_sp):
|
||||
now_nanos = 0
|
||||
msgs_sent = 0
|
||||
CI = self.CarInterface(self.CP, self.CP_SP, self.CarController, self.CarState)
|
||||
for _ in range(round(10.0 / DT_CTRL)): # make sure we hit the slowest messages
|
||||
CI.update([])
|
||||
_, sendcan = CI.apply(car_control, now_nanos)
|
||||
_, sendcan = CI.apply(car_control, car_control_sp, now_nanos)
|
||||
|
||||
now_nanos += DT_CTRL * 1e9
|
||||
msgs_sent += len(sendcan)
|
||||
@@ -296,17 +297,18 @@ class TestCarModelBase(unittest.TestCase):
|
||||
|
||||
# Make sure we can send all messages while inactive
|
||||
CC = structs.CarControl()
|
||||
test_car_controller(CC.as_reader())
|
||||
CC_SP = structs.CarControlSP()
|
||||
test_car_controller(CC.as_reader(), CC_SP)
|
||||
|
||||
# Test cancel + general messages (controls_allowed=False & cruise_engaged=True)
|
||||
self.safety.set_cruise_engaged_prev(True)
|
||||
CC = structs.CarControl(cruiseControl=structs.CarControl.CruiseControl(cancel=True))
|
||||
test_car_controller(CC.as_reader())
|
||||
test_car_controller(CC.as_reader(), CC_SP)
|
||||
|
||||
# Test resume + general messages (controls_allowed=True & cruise_engaged=True)
|
||||
self.safety.set_controls_allowed(True)
|
||||
CC = structs.CarControl(cruiseControl=structs.CarControl.CruiseControl(resume=True))
|
||||
test_car_controller(CC.as_reader())
|
||||
test_car_controller(CC.as_reader(), CC_SP)
|
||||
|
||||
# Skip stdout/stderr capture with pytest, causes elevated memory usage
|
||||
@pytest.mark.nocapture
|
||||
|
||||
@@ -19,8 +19,6 @@ from openpilot.selfdrive.controls.lib.longcontrol import LongControl
|
||||
from openpilot.selfdrive.controls.lib.vehicle_model import VehicleModel
|
||||
from openpilot.selfdrive.locationd.helpers import PoseCalibrator, Pose
|
||||
|
||||
from opendbc.sunnypilot import SunnypilotParamFlags
|
||||
|
||||
State = log.SelfdriveState.OpenpilotState
|
||||
LaneChangeState = log.LaneChangeState
|
||||
LaneChangeDirection = log.LaneChangeDirection
|
||||
@@ -42,8 +40,9 @@ class Controls:
|
||||
|
||||
self.sm = messaging.SubMaster(['liveParameters', 'liveTorqueParameters', 'modelV2', 'selfdriveState',
|
||||
'liveCalibration', 'livePose', 'longitudinalPlan', 'carState', 'carOutput',
|
||||
'driverMonitoringState', 'onroadEvents', 'driverAssistance'], poll='selfdriveState')
|
||||
self.pm = messaging.PubMaster(['carControl', 'controlsState'])
|
||||
'driverMonitoringState', 'onroadEvents', 'driverAssistance'] + ['selfdriveStateSP'],
|
||||
poll='selfdriveState')
|
||||
self.pm = messaging.PubMaster(['carControl', 'controlsState'] + ['carControlSP'])
|
||||
|
||||
self.steer_limited = False
|
||||
self.desired_curvature = 0.0
|
||||
@@ -61,9 +60,6 @@ class Controls:
|
||||
elif self.CP.lateralTuning.which() == 'torque':
|
||||
self.LaC = LatControlTorque(self.CP, self.CI)
|
||||
|
||||
data_services = list(self.sm.data.keys()) + ['selfdriveStateSP']
|
||||
self.sm = messaging.SubMaster(data_services, poll='selfdriveState')
|
||||
|
||||
def update(self):
|
||||
self.sm.update(15)
|
||||
if self.sm.updated["liveCalibration"]:
|
||||
@@ -98,9 +94,7 @@ class Controls:
|
||||
standstill = abs(CS.vEgo) <= max(self.CP.minSteerSpeed, MIN_LATERAL_CONTROL_SPEED) or CS.standstill
|
||||
|
||||
ss_sp = self.sm['selfdriveStateSP']
|
||||
CC.madsEnabled = ss_sp.mads.enabled
|
||||
if ss_sp.mads.available:
|
||||
CC.sunnypilotParams |= SunnypilotParamFlags.ENABLE_MADS.value
|
||||
_lat_active = ss_sp.mads.active
|
||||
else:
|
||||
_lat_active = self.sm['selfdriveState'].active
|
||||
@@ -143,9 +137,12 @@ class Controls:
|
||||
cloudlog.error(f"actuators.{p} not finite {actuators.to_dict()}")
|
||||
setattr(actuators, p, 0.0)
|
||||
|
||||
return CC, lac_log
|
||||
CC_SP = custom.CarControlSP.new_message()
|
||||
CC_SP.mads = ss_sp.mads
|
||||
|
||||
def publish(self, CC, lac_log):
|
||||
return CC, CC_SP, lac_log
|
||||
|
||||
def publish(self, CC, CC_SP, lac_log):
|
||||
CS = self.sm['carState']
|
||||
|
||||
# Orientation and angle rates can be useful for carcontroller
|
||||
@@ -221,12 +218,18 @@ class Controls:
|
||||
cc_send.carControl = CC
|
||||
self.pm.send('carControl', cc_send)
|
||||
|
||||
# carControlSP
|
||||
cc_sp_send = messaging.new_message('carControlSP')
|
||||
cc_sp_send.valid = CS.canValid
|
||||
cc_sp_send.carControlSP = CC_SP
|
||||
self.pm.send('carControlSP', cc_sp_send)
|
||||
|
||||
def run(self):
|
||||
rk = Ratekeeper(100, print_delay_threshold=None)
|
||||
while True:
|
||||
self.update()
|
||||
CC, lac_log = self.state_control()
|
||||
self.publish(CC, lac_log)
|
||||
CC, CC_SP, lac_log = self.state_control()
|
||||
self.publish(CC, CC_SP, lac_log)
|
||||
rk.monitor_time()
|
||||
|
||||
def main():
|
||||
|
||||
@@ -141,6 +141,9 @@ class LongitudinalPlanner(LongitudinalPlannerSP):
|
||||
accel_limits = [ACCEL_MIN, ACCEL_MAX]
|
||||
accel_limits_turns = [ACCEL_MIN, ACCEL_MAX]
|
||||
|
||||
if (accel_control := self.compute_accel_limits(v_ego, sm, self.CP)):
|
||||
accel_limits, accel_limits_turns = accel_control
|
||||
|
||||
if reset_state:
|
||||
self.v_desired_filter.x = v_ego
|
||||
# Clip aEgo to cruise limits to prevent large accelerations when becoming active
|
||||
|
||||
@@ -19,7 +19,7 @@ class TestLatControl:
|
||||
def test_saturation(self, car_name, controller):
|
||||
CarInterface, CarController, CarState, RadarInterface = interfaces[car_name]
|
||||
CP = CarInterface.get_non_essential_params(car_name)
|
||||
CP, CP_SP = CarInterface.get_non_essential_params_sp(CP, car_name)
|
||||
CP_SP = CarInterface.get_non_essential_params_sp(CP, car_name)
|
||||
CI = CarInterface(CP, CP_SP, CarController, CarState)
|
||||
VM = VehicleModel(CP)
|
||||
|
||||
|
||||
@@ -1,11 +1,9 @@
|
||||
import os
|
||||
|
||||
import capnp
|
||||
import numpy as np
|
||||
from openpilot.selfdrive.controls.lib.drive_helpers import MIN_SPEED
|
||||
from openpilot.selfdrive.modeld.constants import ModelConstants, Plan
|
||||
|
||||
from cereal import log
|
||||
from openpilot.selfdrive.modeld.constants import ModelConstants, Plan
|
||||
from openpilot.selfdrive.controls.lib.drive_helpers import MIN_SPEED
|
||||
|
||||
SEND_RAW_PRED = os.getenv('SEND_RAW_PRED')
|
||||
|
||||
@@ -30,6 +28,7 @@ def get_curvature_from_output(output, vego, delay):
|
||||
|
||||
return float(get_curvature_from_plan(output['plan'][0], vego, delay))
|
||||
|
||||
|
||||
class PublishState:
|
||||
def __init__(self):
|
||||
self.disengage_buffer = np.zeros(ModelConstants.CONFIDENCE_BUFFER_LEN*ModelConstants.DISENGAGE_WIDTH, dtype=np.float32)
|
||||
@@ -86,7 +85,7 @@ def fill_model_msg(base_msg: capnp._DynamicStructBuilder, extended_msg: capnp._D
|
||||
extended_msg.valid = valid
|
||||
base_msg.valid = valid
|
||||
|
||||
desired_curv = float(get_curvature_from_output(net_output_data, v_ego, delay))
|
||||
desired_curvature = float(get_curvature_from_output(net_output_data, v_ego, delay))
|
||||
|
||||
driving_model_data = base_msg.drivingModelData
|
||||
|
||||
@@ -96,7 +95,7 @@ def fill_model_msg(base_msg: capnp._DynamicStructBuilder, extended_msg: capnp._D
|
||||
driving_model_data.modelExecutionTime = model_execution_time
|
||||
|
||||
action = driving_model_data.action
|
||||
action.desiredCurvature = desired_curv
|
||||
action.desiredCurvature = desired_curvature
|
||||
|
||||
modelV2 = extended_msg.modelV2
|
||||
modelV2.frameId = vipc_frame_id
|
||||
@@ -131,7 +130,7 @@ def fill_model_msg(base_msg: capnp._DynamicStructBuilder, extended_msg: capnp._D
|
||||
|
||||
# lateral planning
|
||||
action = modelV2.action
|
||||
action.desiredCurvature = desired_curv
|
||||
action.desiredCurvature = desired_curvature
|
||||
|
||||
# times at X_IDXS according to model plan
|
||||
PLAN_T_IDXS = [np.nan] * ModelConstants.IDX_N
|
||||
|
||||
@@ -1,8 +1,6 @@
|
||||
#!/usr/bin/env python3
|
||||
from openpilot.system.hardware import TICI
|
||||
|
||||
from openpilot.sunnypilot.modeld_v2.model_runner import ONNXRunner, TinygradRunner
|
||||
|
||||
#
|
||||
import time
|
||||
import numpy as np
|
||||
@@ -25,7 +23,8 @@ from openpilot.selfdrive.modeld.fill_model_msg import fill_model_msg, fill_pose_
|
||||
from openpilot.selfdrive.modeld.constants import ModelConstants
|
||||
from openpilot.selfdrive.modeld.models.commonmodel_pyx import DrivingModelFrame, CLContext
|
||||
|
||||
from sunnypilot.modeld_v2.meta_helper import load_meta_constants
|
||||
from openpilot.sunnypilot.modeld_v2.meta_helper import load_meta_constants
|
||||
from openpilot.sunnypilot.modeld_v2.model_runner import ONNXRunner, TinygradRunner
|
||||
|
||||
PROCESS_NAME = "selfdrive.modeld.modeld"
|
||||
|
||||
@@ -57,7 +56,6 @@ class ModelState:
|
||||
if self.model_runner.is_20hz:
|
||||
self.full_features_20Hz = np.zeros((ModelConstants.FULL_HISTORY_BUFFER_LEN, ModelConstants.FEATURE_LEN), dtype=np.float32)
|
||||
self.desire_20Hz = np.zeros((ModelConstants.FULL_HISTORY_BUFFER_LEN + 1, ModelConstants.DESIRE_LEN), dtype=np.float32)
|
||||
# Initialize model runner
|
||||
|
||||
# img buffers are managed in openCL transform code
|
||||
self.numpy_inputs = {}
|
||||
@@ -78,7 +76,7 @@ class ModelState:
|
||||
self.desire_reshape_dims = (self.numpy_inputs['desire'].shape[0], self.numpy_inputs['desire'].shape[1], -1, self.numpy_inputs['desire'].shape[2])
|
||||
|
||||
def run(self, buf: VisionBuf, wbuf: VisionBuf, transform: np.ndarray, transform_wide: np.ndarray,
|
||||
inputs: dict[str, np.ndarray], prepare_only: bool) -> dict[str, np.ndarray] | None:
|
||||
inputs: dict[str, np.ndarray], prepare_only: bool) -> dict[str, np.ndarray] | None:
|
||||
# Model decides when action is completed, so desire input is just a pulse triggered on rising edge
|
||||
inputs['desire'][0] = 0
|
||||
new_desire = np.where(inputs['desire'] - self.prev_desire > .99, inputs['desire'], 0)
|
||||
|
||||
@@ -71,7 +71,7 @@ class SelfdriveD(CruiseHelper):
|
||||
self.disengage_on_accelerator = not (self.CP.alternativeExperience & ALTERNATIVE_EXPERIENCE.DISABLE_DISENGAGE_ON_GAS)
|
||||
|
||||
# Setup sockets
|
||||
self.pm = messaging.PubMaster(['selfdriveState', 'onroadEvents'])
|
||||
self.pm = messaging.PubMaster(['selfdriveState', 'onroadEvents'] + ['selfdriveStateSP', 'onroadEventsSP'])
|
||||
|
||||
self.gps_location_service = get_gps_location_service(self.params)
|
||||
self.gps_packets = [self.gps_location_service]
|
||||
@@ -147,8 +147,6 @@ class SelfdriveD(CruiseHelper):
|
||||
self.events_sp_prev = []
|
||||
|
||||
self.mads = ModularAssistiveDrivingSystem(self)
|
||||
sock_services = list(self.pm.sock.keys()) + ['selfdriveStateSP', 'onroadEventsSP']
|
||||
self.pm = messaging.PubMaster(sock_services)
|
||||
|
||||
self.car_events_sp = CarSpecificEventsSP(self.CP, self.params)
|
||||
|
||||
|
||||
@@ -344,7 +344,7 @@ def get_car_params_callback(rc, pm, msgs, fingerprint):
|
||||
if fingerprint:
|
||||
CarInterface, _, _, _ = interfaces[fingerprint]
|
||||
CP = CarInterface.get_non_essential_params(fingerprint)
|
||||
CP, CP_SP = CarInterface.get_non_essential_params_sp(CP, fingerprint)
|
||||
CP_SP = CarInterface.get_non_essential_params_sp(CP, fingerprint)
|
||||
else:
|
||||
can = DummySocket()
|
||||
sendcan = DummySocket()
|
||||
|
||||
@@ -97,7 +97,7 @@ public:
|
||||
void setPrimeType(PrimeState::Type type);
|
||||
WifiManager* wifi = nullptr;
|
||||
|
||||
private:
|
||||
protected:
|
||||
QStackedLayout* main_layout = nullptr;
|
||||
QWidget* wifiScreen = nullptr;
|
||||
AdvancedNetworking* an = nullptr;
|
||||
|
||||
@@ -87,6 +87,16 @@ TogglesPanel::TogglesPanel(SettingsWindow *parent) : ListWidget(parent) {
|
||||
"../assets/offroad/icon_speed_limit.png",
|
||||
longi_button_texts);
|
||||
|
||||
// accel controller
|
||||
std::vector<QString> accel_personality_texts{tr("Sport"), tr("Normal"), tr("Eco"), tr("Stock")};
|
||||
accel_personality_setting = new ButtonParamControlSP("AccelPersonality", tr("Acceleration Personality"),
|
||||
tr("Normal is recommended. In sport mode, sunnypilot will provide aggressive acceleration for a dynamic driving experience. "
|
||||
"In eco mode, sunnypilot will apply smoother and more relaxed acceleration. On supported cars, you can cycle through these "
|
||||
"acceleration personality within Onroad Settings on the driving screen."),
|
||||
"",
|
||||
accel_personality_texts);
|
||||
accel_personality_setting->showDescription();
|
||||
|
||||
// set up uiState update for personality setting
|
||||
QObject::connect(uiState(), &UIState::uiUpdate, this, &TogglesPanel::updateState);
|
||||
|
||||
@@ -102,6 +112,7 @@ TogglesPanel::TogglesPanel(SettingsWindow *parent) : ListWidget(parent) {
|
||||
// insert longitudinal personality after NDOG toggle
|
||||
if (param == "DisengageOnAccelerator") {
|
||||
addItem(long_personality_setting);
|
||||
addItem(accel_personality_setting);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -127,6 +138,13 @@ void TogglesPanel::updateState(const UIState &s) {
|
||||
}
|
||||
uiState()->scene.personality = personality;
|
||||
}
|
||||
if (sm.updated("longitudinalPlanSP")) {
|
||||
auto accel_personality = sm["longitudinalPlanSP"].getLongitudinalPlanSP().getAccelPersonality();
|
||||
if (accel_personality != s.scene.accel_personality && s.scene.started && isVisible()) {
|
||||
accel_personality_setting->setCheckedButton(static_cast<int>(accel_personality));
|
||||
}
|
||||
uiState()->scene.accel_personality = accel_personality;
|
||||
}
|
||||
}
|
||||
|
||||
void TogglesPanel::expandToggleDescription(const QString ¶m) {
|
||||
@@ -169,10 +187,12 @@ void TogglesPanel::updateToggles() {
|
||||
experimental_mode_toggle->setEnabled(true);
|
||||
experimental_mode_toggle->setDescription(e2e_description);
|
||||
long_personality_setting->setEnabled(true);
|
||||
accel_personality_setting->setEnabled(true);
|
||||
} else {
|
||||
// no long for now
|
||||
experimental_mode_toggle->setEnabled(false);
|
||||
long_personality_setting->setEnabled(false);
|
||||
accel_personality_setting->setEnabled(true);
|
||||
params.remove("ExperimentalMode");
|
||||
|
||||
const QString unavailable = tr("Experimental mode is currently unavailable on this car since the car's stock ACC is used for longitudinal control.");
|
||||
|
||||
@@ -83,6 +83,7 @@ protected:
|
||||
Params params;
|
||||
std::map<std::string, ParamControl*> toggles;
|
||||
ButtonParamControl *long_personality_setting;
|
||||
ButtonParamControl *accel_personality_setting;
|
||||
|
||||
virtual void updateToggles();
|
||||
};
|
||||
|
||||
@@ -4,6 +4,7 @@ widgets_src = [
|
||||
"sunnypilot/qt/widgets/drive_stats.cc",
|
||||
"sunnypilot/qt/widgets/prime.cc",
|
||||
"sunnypilot/qt/widgets/scrollview.cc",
|
||||
"sunnypilot/qt/network/networking.cc",
|
||||
]
|
||||
|
||||
qt_util = [
|
||||
@@ -22,6 +23,7 @@ qt_src = [
|
||||
"sunnypilot/qt/offroad/settings/sunnylink_panel.cc",
|
||||
"sunnypilot/qt/offroad/settings/sunnypilot_panel.cc",
|
||||
"sunnypilot/qt/offroad/settings/trips_panel.cc",
|
||||
"sunnypilot/qt/offroad/settings/vehicle_panel.cc",
|
||||
"sunnypilot/qt/onroad/annotated_camera.cc",
|
||||
"sunnypilot/qt/onroad/buttons.cc",
|
||||
"sunnypilot/qt/onroad/hud.cc",
|
||||
|
||||
@@ -0,0 +1,45 @@
|
||||
#include "selfdrive/ui/sunnypilot/qt/network/networking.h"
|
||||
#include <QVBoxLayout>
|
||||
#include <QPushButton>
|
||||
#include <QStackedLayout>
|
||||
|
||||
NetworkingSP::NetworkingSP(QWidget *parent) : Networking(parent) {
|
||||
auto vlayout = wifiScreen->findChild<QVBoxLayout*>();
|
||||
auto hlayout = new QHBoxLayout();
|
||||
|
||||
// Create and setup scan button
|
||||
auto scanButton = new QPushButton(tr("Scan"));
|
||||
scanButton->setObjectName("scan_btn");
|
||||
scanButton->setFixedSize(400, 100);
|
||||
|
||||
connect(wifi, &WifiManager::refreshSignal, this, [=]() { scanButton->setText(tr("Scan")); scanButton->setEnabled(true); });
|
||||
connect(scanButton, &QPushButton::clicked, [=]() { scanButton->setText(tr("Scanning...")); scanButton->setEnabled(false); wifi->requestScan(); });
|
||||
|
||||
hlayout->addWidget(scanButton);
|
||||
hlayout->addStretch(1);
|
||||
|
||||
// Look for an existing Advanced button
|
||||
QPushButton* existingAdvanced = wifiScreen->findChild<QPushButton*>("advanced_btn");
|
||||
if (existingAdvanced) {
|
||||
hlayout->addWidget(existingAdvanced);
|
||||
}
|
||||
|
||||
// Insert our new layout at the top of vlayout
|
||||
vlayout->setMargin(40);
|
||||
vlayout->insertLayout(0, hlayout);
|
||||
|
||||
// Add our scan button to the existing style selectors
|
||||
auto newStyleSheet = styleSheet().replace(
|
||||
", #advanced_btn ",
|
||||
", #advanced_btn, #scan_btn "
|
||||
).replace(
|
||||
", #advanced_btn:pressed",
|
||||
", #advanced_btn:pressed, #scan_btn:pressed"
|
||||
).append(R"(
|
||||
#scan_btn:disabled {
|
||||
background-color: #121212;
|
||||
color: #33FFFFFF;
|
||||
}
|
||||
)");
|
||||
setStyleSheet(newStyleSheet);
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
/**
|
||||
* Copyright (c) 2021-, Haibin Wen, sunnypilot, and a number of other contributors.
|
||||
*
|
||||
* This file is part of sunnypilot and is licensed under the MIT License.
|
||||
* See the LICENSE.md file in the root directory for more details.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
#include "selfdrive/ui/qt/network/networking.h"
|
||||
|
||||
|
||||
class NetworkingSP : public Networking {
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
explicit NetworkingSP(QWidget *parent = nullptr);
|
||||
};
|
||||
@@ -7,15 +7,16 @@
|
||||
|
||||
#include "selfdrive/ui/sunnypilot/qt/offroad/settings/settings.h"
|
||||
|
||||
#include "selfdrive/ui/qt/network/networking.h"
|
||||
#include "selfdrive/ui/sunnypilot/qt/widgets/scrollview.h"
|
||||
#include "selfdrive/ui/qt/offroad/developer_panel.h"
|
||||
#include "selfdrive/ui/sunnypilot/qt/network/networking.h"
|
||||
|
||||
#include "selfdrive/ui/sunnypilot/qt/offroad/settings/device_panel.h"
|
||||
#include "selfdrive/ui/sunnypilot/qt/offroad/settings/software_panel.h"
|
||||
#include "selfdrive/ui/sunnypilot/qt/offroad/settings/sunnylink_panel.h"
|
||||
#include "selfdrive/ui/sunnypilot/qt/offroad/settings/sunnypilot_panel.h"
|
||||
#include "selfdrive/ui/sunnypilot/qt/offroad/settings/trips_panel.h"
|
||||
#include "selfdrive/ui/sunnypilot/qt/offroad/settings/vehicle_panel.h"
|
||||
|
||||
TogglesPanelSP::TogglesPanelSP(SettingsWindowSP *parent) : TogglesPanel(parent) {
|
||||
QObject::connect(uiStateSP(), &UIStateSP::uiUpdate, this, &TogglesPanelSP::updateState);
|
||||
@@ -66,8 +67,8 @@ SettingsWindowSP::SettingsWindowSP(QWidget *parent) : SettingsWindow(parent) {
|
||||
TogglesPanelSP *toggles = new TogglesPanelSP(this);
|
||||
QObject::connect(this, &SettingsWindowSP::expandToggleDescription, toggles, &TogglesPanel::expandToggleDescription);
|
||||
|
||||
auto networking = new Networking(this);
|
||||
QObject::connect(uiState()->prime_state, &PrimeState::changed, networking, &Networking::setPrimeType);
|
||||
auto networking = new NetworkingSP(this);
|
||||
QObject::connect(uiState()->prime_state, &PrimeState::changed, networking, &NetworkingSP::setPrimeType);
|
||||
|
||||
QList<PanelInfo> panels = {
|
||||
PanelInfo(" " + tr("Device"), device, "../../sunnypilot/selfdrive/assets/offroad/icon_home.svg"),
|
||||
@@ -77,6 +78,7 @@ SettingsWindowSP::SettingsWindowSP(QWidget *parent) : SettingsWindow(parent) {
|
||||
PanelInfo(" " + tr("Software"), new SoftwarePanelSP(this), "../../sunnypilot/selfdrive/assets/offroad/icon_software.png"),
|
||||
PanelInfo(" " + tr("sunnypilot"), new SunnypilotPanel(this), "../assets/images/button_home.png"),
|
||||
PanelInfo(" " + tr("Trips"), new TripsPanel(this), "../../sunnypilot/selfdrive/assets/offroad/icon_trips.png"),
|
||||
PanelInfo(" " + tr("Vehicle"), new VehiclePanel(this), "../../sunnypilot/selfdrive/assets/offroad/icon_vehicle.png"),
|
||||
PanelInfo(" " + tr("Developer"), new DeveloperPanel(this), "../assets/offroad/icon_shell.png"),
|
||||
};
|
||||
|
||||
|
||||
@@ -0,0 +1,11 @@
|
||||
/**
|
||||
* Copyright (c) 2021-, Haibin Wen, sunnypilot, and a number of other contributors.
|
||||
*
|
||||
* This file is part of sunnypilot and is licensed under the MIT License.
|
||||
* See the LICENSE.md file in the root directory for more details.
|
||||
*/
|
||||
|
||||
#include "selfdrive/ui/sunnypilot/qt/offroad/settings/vehicle_panel.h"
|
||||
|
||||
VehiclePanel::VehiclePanel(QWidget *parent) : QWidget(parent) {
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
/**
|
||||
* Copyright (c) 2021-, Haibin Wen, sunnypilot, and a number of other contributors.
|
||||
*
|
||||
* This file is part of sunnypilot and is licensed under the MIT License.
|
||||
* See the LICENSE.md file in the root directory for more details.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "selfdrive/ui/sunnypilot/qt/offroad/settings/settings.h"
|
||||
|
||||
class VehiclePanel : public QWidget {
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
explicit VehiclePanel(QWidget *parent = nullptr);
|
||||
};
|
||||
@@ -40,6 +40,14 @@ def setup_homescreen(click, pm: PubMaster, scroll=None):
|
||||
def setup_settings_device(click, pm: PubMaster, scroll=None):
|
||||
click(100, 100)
|
||||
|
||||
def setup_settings_network(click, pm: PubMaster, scroll=None):
|
||||
setup_settings_device(click, pm)
|
||||
click(278, 405)
|
||||
|
||||
def setup_settings_network_advanced(click, pm: PubMaster, scroll=None):
|
||||
setup_settings_network(click, pm)
|
||||
click(1913, 90)
|
||||
|
||||
def setup_settings_toggles(click, pm: PubMaster, scroll=None):
|
||||
setup_settings_device(click, pm)
|
||||
click(278, 632)
|
||||
@@ -52,7 +60,7 @@ def setup_settings_software(click, pm: PubMaster, scroll=None):
|
||||
|
||||
def setup_settings_developer(click, pm: PubMaster, scroll=None):
|
||||
setup_settings_device(click, pm)
|
||||
scroll(-100, 278, 962)
|
||||
scroll(-400, 278, 962)
|
||||
click(278, 970)
|
||||
time.sleep(UI_DELAY)
|
||||
|
||||
@@ -207,11 +215,19 @@ def setup_settings_trips(click, pm: PubMaster, scroll=None):
|
||||
click(278, 962)
|
||||
time.sleep(UI_DELAY)
|
||||
|
||||
def setup_settings_vehicle(click, pm: PubMaster, scroll=None):
|
||||
setup_settings_device(click, pm)
|
||||
scroll(-400, 278, 862)
|
||||
click(278, 862)
|
||||
time.sleep(UI_DELAY)
|
||||
|
||||
CASES = {
|
||||
"homescreen": setup_homescreen,
|
||||
"prime": setup_homescreen,
|
||||
"pair_device": setup_pair_device,
|
||||
"settings_device": setup_settings_device,
|
||||
"settings_network": setup_settings_network,
|
||||
"settings_network_advanced": setup_settings_network_advanced,
|
||||
"settings_toggles": setup_settings_toggles,
|
||||
"settings_software": setup_settings_software,
|
||||
"settings_developer": setup_settings_developer,
|
||||
@@ -237,6 +253,7 @@ CASES.update({
|
||||
"settings_sunnypilot": setup_settings_sunnypilot,
|
||||
"settings_sunnypilot_mads": setup_settings_sunnypilot_mads,
|
||||
"settings_trips": setup_settings_trips,
|
||||
"settings_vehicle": setup_settings_vehicle,
|
||||
})
|
||||
|
||||
TEST_DIR = pathlib.Path(__file__).parent
|
||||
|
||||
@@ -507,6 +507,21 @@ Pause Steering: ALC will be paused after the brake pedal is manually pressed.</s
|
||||
<translation>كلمة مرور خاطئة</translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>NetworkingSP</name>
|
||||
<message>
|
||||
<source>Advanced</source>
|
||||
<translation type="obsolete">متقدم</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scan</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scanning...</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>OffroadAlert</name>
|
||||
<message>
|
||||
@@ -843,6 +858,10 @@ This may take up to a minute.</source>
|
||||
<source>Trips</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Vehicle</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Setup</name>
|
||||
@@ -1475,6 +1494,30 @@ This may take up to a minute.</source>
|
||||
<source>Enable toggle to allow the model to determine when to use sunnypilot ACC or sunnypilot End to End Longitudinal.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Sport</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Eco</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Stock</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Acceleration Personality</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal is recommended. In sport mode, sunnypilot will provide aggressive acceleration for a dynamic driving experience. In eco mode, sunnypilot will apply smoother and more relaxed acceleration. On supported cars, you can cycle through these acceleration personality within Onroad Settings on the driving screen.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Updater</name>
|
||||
|
||||
@@ -503,6 +503,21 @@ Pause Steering: ALC will be paused after the brake pedal is manually pressed.</s
|
||||
<translation>Falsches Passwort</translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>NetworkingSP</name>
|
||||
<message>
|
||||
<source>Advanced</source>
|
||||
<translation type="obsolete">Erweitert</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scan</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scanning...</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>OffroadAlert</name>
|
||||
<message>
|
||||
@@ -825,6 +840,10 @@ This may take up to a minute.</source>
|
||||
<source>Trips</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Vehicle</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Setup</name>
|
||||
@@ -1459,6 +1478,30 @@ This may take up to a minute.</source>
|
||||
<source>Enable toggle to allow the model to determine when to use sunnypilot ACC or sunnypilot End to End Longitudinal.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Sport</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Eco</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Stock</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Acceleration Personality</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal is recommended. In sport mode, sunnypilot will provide aggressive acceleration for a dynamic driving experience. In eco mode, sunnypilot will apply smoother and more relaxed acceleration. On supported cars, you can cycle through these acceleration personality within Onroad Settings on the driving screen.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Updater</name>
|
||||
|
||||
@@ -503,6 +503,17 @@ Pause Steering: ALC will be paused after the brake pedal is manually pressed.</s
|
||||
<translation>Contraseña incorrecta</translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>NetworkingSP</name>
|
||||
<message>
|
||||
<source>Scan</source>
|
||||
<translation>Escanear</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scanning...</source>
|
||||
<translation>Escaneando...</translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>OffroadAlert</name>
|
||||
<message>
|
||||
@@ -827,6 +838,10 @@ Esto puede tardar un minuto.</translation>
|
||||
<source>Trips</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Vehicle</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Setup</name>
|
||||
@@ -1459,6 +1474,30 @@ Esto puede tardar un minuto.</translation>
|
||||
<source>Enable toggle to allow the model to determine when to use sunnypilot ACC or sunnypilot End to End Longitudinal.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Sport</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Eco</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Stock</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Acceleration Personality</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal is recommended. In sport mode, sunnypilot will provide aggressive acceleration for a dynamic driving experience. In eco mode, sunnypilot will apply smoother and more relaxed acceleration. On supported cars, you can cycle through these acceleration personality within Onroad Settings on the driving screen.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Updater</name>
|
||||
|
||||
@@ -503,6 +503,21 @@ Pause Steering: ALC will be paused after the brake pedal is manually pressed.</s
|
||||
<translation>Mot de passe incorrect</translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>NetworkingSP</name>
|
||||
<message>
|
||||
<source>Advanced</source>
|
||||
<translation type="obsolete">Avancé</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scan</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scanning...</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>OffroadAlert</name>
|
||||
<message>
|
||||
@@ -827,6 +842,10 @@ Cela peut prendre jusqu'à une minute.</translation>
|
||||
<source>Trips</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Vehicle</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Setup</name>
|
||||
@@ -1459,6 +1478,30 @@ Cela peut prendre jusqu'à une minute.</translation>
|
||||
<source>Enable toggle to allow the model to determine when to use sunnypilot ACC or sunnypilot End to End Longitudinal.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Sport</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Eco</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Stock</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Acceleration Personality</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal is recommended. In sport mode, sunnypilot will provide aggressive acceleration for a dynamic driving experience. In eco mode, sunnypilot will apply smoother and more relaxed acceleration. On supported cars, you can cycle through these acceleration personality within Onroad Settings on the driving screen.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Updater</name>
|
||||
|
||||
@@ -502,6 +502,21 @@ Pause Steering: ALC will be paused after the brake pedal is manually pressed.</s
|
||||
<translation>パスワードが間違っています</translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>NetworkingSP</name>
|
||||
<message>
|
||||
<source>Advanced</source>
|
||||
<translation type="obsolete">詳細</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scan</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scanning...</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>OffroadAlert</name>
|
||||
<message>
|
||||
@@ -821,6 +836,10 @@ This may take up to a minute.</source>
|
||||
<source>Trips</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Vehicle</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Setup</name>
|
||||
@@ -1453,6 +1472,30 @@ This may take up to a minute.</source>
|
||||
<source>Enable toggle to allow the model to determine when to use sunnypilot ACC or sunnypilot End to End Longitudinal.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Sport</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Eco</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Stock</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Acceleration Personality</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal is recommended. In sport mode, sunnypilot will provide aggressive acceleration for a dynamic driving experience. In eco mode, sunnypilot will apply smoother and more relaxed acceleration. On supported cars, you can cycle through these acceleration personality within Onroad Settings on the driving screen.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Updater</name>
|
||||
|
||||
@@ -502,6 +502,21 @@ Pause Steering: ALC will be paused after the brake pedal is manually pressed.</s
|
||||
<translation>비밀번호가 틀렸습니다</translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>NetworkingSP</name>
|
||||
<message>
|
||||
<source>Advanced</source>
|
||||
<translation type="obsolete">고급 설정</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scan</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scanning...</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>OffroadAlert</name>
|
||||
<message>
|
||||
@@ -823,6 +838,10 @@ This may take up to a minute.</source>
|
||||
<source>Trips</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Vehicle</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Setup</name>
|
||||
@@ -1455,6 +1474,30 @@ This may take up to a minute.</source>
|
||||
<source>Enable toggle to allow the model to determine when to use sunnypilot ACC or sunnypilot End to End Longitudinal.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Sport</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Eco</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Stock</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Acceleration Personality</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal is recommended. In sport mode, sunnypilot will provide aggressive acceleration for a dynamic driving experience. In eco mode, sunnypilot will apply smoother and more relaxed acceleration. On supported cars, you can cycle through these acceleration personality within Onroad Settings on the driving screen.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Updater</name>
|
||||
|
||||
@@ -503,6 +503,21 @@ Pause Steering: ALC will be paused after the brake pedal is manually pressed.</s
|
||||
<translation>Senha incorreta</translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>NetworkingSP</name>
|
||||
<message>
|
||||
<source>Advanced</source>
|
||||
<translation type="obsolete">Avançado</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scan</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scanning...</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>OffroadAlert</name>
|
||||
<message>
|
||||
@@ -827,6 +842,10 @@ Isso pode levar até um minuto.</translation>
|
||||
<source>Trips</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Vehicle</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Setup</name>
|
||||
@@ -1459,6 +1478,30 @@ Isso pode levar até um minuto.</translation>
|
||||
<source>Enable toggle to allow the model to determine when to use sunnypilot ACC or sunnypilot End to End Longitudinal.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Sport</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Eco</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Stock</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Acceleration Personality</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal is recommended. In sport mode, sunnypilot will provide aggressive acceleration for a dynamic driving experience. In eco mode, sunnypilot will apply smoother and more relaxed acceleration. On supported cars, you can cycle through these acceleration personality within Onroad Settings on the driving screen.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Updater</name>
|
||||
|
||||
@@ -502,6 +502,21 @@ Pause Steering: ALC will be paused after the brake pedal is manually pressed.</s
|
||||
<translation>รหัสผ่านผิด</translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>NetworkingSP</name>
|
||||
<message>
|
||||
<source>Advanced</source>
|
||||
<translation type="obsolete">ขั้นสูง</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scan</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scanning...</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>OffroadAlert</name>
|
||||
<message>
|
||||
@@ -823,6 +838,10 @@ This may take up to a minute.</source>
|
||||
<source>Trips</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Vehicle</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Setup</name>
|
||||
@@ -1455,6 +1474,30 @@ This may take up to a minute.</source>
|
||||
<source>Enable toggle to allow the model to determine when to use sunnypilot ACC or sunnypilot End to End Longitudinal.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Sport</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Eco</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Stock</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Acceleration Personality</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal is recommended. In sport mode, sunnypilot will provide aggressive acceleration for a dynamic driving experience. In eco mode, sunnypilot will apply smoother and more relaxed acceleration. On supported cars, you can cycle through these acceleration personality within Onroad Settings on the driving screen.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Updater</name>
|
||||
|
||||
@@ -502,6 +502,21 @@ Pause Steering: ALC will be paused after the brake pedal is manually pressed.</s
|
||||
<translation>Yalnış parola</translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>NetworkingSP</name>
|
||||
<message>
|
||||
<source>Advanced</source>
|
||||
<translation type="obsolete">Gelişmiş Seçenekler</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scan</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scanning...</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>OffroadAlert</name>
|
||||
<message>
|
||||
@@ -821,6 +836,10 @@ This may take up to a minute.</source>
|
||||
<source>Trips</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Vehicle</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Setup</name>
|
||||
@@ -1453,6 +1472,30 @@ This may take up to a minute.</source>
|
||||
<source>Enable toggle to allow the model to determine when to use sunnypilot ACC or sunnypilot End to End Longitudinal.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Sport</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Eco</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Stock</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Acceleration Personality</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal is recommended. In sport mode, sunnypilot will provide aggressive acceleration for a dynamic driving experience. In eco mode, sunnypilot will apply smoother and more relaxed acceleration. On supported cars, you can cycle through these acceleration personality within Onroad Settings on the driving screen.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Updater</name>
|
||||
|
||||
@@ -502,6 +502,21 @@ Pause Steering: ALC will be paused after the brake pedal is manually pressed.</s
|
||||
<translation>密码错误</translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>NetworkingSP</name>
|
||||
<message>
|
||||
<source>Advanced</source>
|
||||
<translation type="obsolete">高级</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scan</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scanning...</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>OffroadAlert</name>
|
||||
<message>
|
||||
@@ -823,6 +838,10 @@ This may take up to a minute.</source>
|
||||
<source>Trips</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Vehicle</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Setup</name>
|
||||
@@ -1455,6 +1474,30 @@ This may take up to a minute.</source>
|
||||
<source>Enable toggle to allow the model to determine when to use sunnypilot ACC or sunnypilot End to End Longitudinal.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Sport</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Eco</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Stock</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Acceleration Personality</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal is recommended. In sport mode, sunnypilot will provide aggressive acceleration for a dynamic driving experience. In eco mode, sunnypilot will apply smoother and more relaxed acceleration. On supported cars, you can cycle through these acceleration personality within Onroad Settings on the driving screen.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Updater</name>
|
||||
|
||||
@@ -502,6 +502,21 @@ Pause Steering: ALC will be paused after the brake pedal is manually pressed.</s
|
||||
<translation>密碼錯誤</translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>NetworkingSP</name>
|
||||
<message>
|
||||
<source>Advanced</source>
|
||||
<translation type="obsolete">進階</translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scan</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Scanning...</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>OffroadAlert</name>
|
||||
<message>
|
||||
@@ -823,6 +838,10 @@ This may take up to a minute.</source>
|
||||
<source>Trips</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Vehicle</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Setup</name>
|
||||
@@ -1455,6 +1474,30 @@ This may take up to a minute.</source>
|
||||
<source>Enable toggle to allow the model to determine when to use sunnypilot ACC or sunnypilot End to End Longitudinal.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Sport</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Eco</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Stock</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Acceleration Personality</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
<message>
|
||||
<source>Normal is recommended. In sport mode, sunnypilot will provide aggressive acceleration for a dynamic driving experience. In eco mode, sunnypilot will apply smoother and more relaxed acceleration. On supported cars, you can cycle through these acceleration personality within Onroad Settings on the driving screen.</source>
|
||||
<translation type="unfinished"></translation>
|
||||
</message>
|
||||
</context>
|
||||
<context>
|
||||
<name>Updater</name>
|
||||
|
||||
+2
-2
@@ -75,8 +75,8 @@ void UIState::updateStatus() {
|
||||
auto state = ss.getState();
|
||||
auto state_mads = mads.getState();
|
||||
if (state == cereal::SelfdriveState::OpenpilotState::PRE_ENABLED || state == cereal::SelfdriveState::OpenpilotState::OVERRIDING ||
|
||||
state_mads == cereal::SelfdriveStateSP::ModularAssistiveDrivingSystem::ModularAssistiveDrivingSystemState::PAUSED ||
|
||||
state_mads == cereal::SelfdriveStateSP::ModularAssistiveDrivingSystem::ModularAssistiveDrivingSystemState::OVERRIDING) {
|
||||
state_mads == cereal::ModularAssistiveDrivingSystem::ModularAssistiveDrivingSystemState::PAUSED ||
|
||||
state_mads == cereal::ModularAssistiveDrivingSystem::ModularAssistiveDrivingSystemState::OVERRIDING) {
|
||||
status = STATUS_OVERRIDE;
|
||||
} else {
|
||||
if (mads.getAvailable()) {
|
||||
|
||||
@@ -60,6 +60,7 @@ typedef struct UIScene {
|
||||
cereal::PandaState::PandaType pandaType;
|
||||
|
||||
cereal::LongitudinalPersonality personality;
|
||||
cereal::LongitudinalPlanSP::AccelerationPersonality accel_personality;
|
||||
|
||||
float light_sensor = -1;
|
||||
bool started, ignition, is_metric;
|
||||
|
||||
@@ -32,7 +32,7 @@ from opendbc.sunnypilot.car.hyundai.values import HyundaiFlagsSP
|
||||
from openpilot.sunnypilot.mads.helpers import MadsParams
|
||||
from openpilot.sunnypilot.mads.state import StateMachine, GEARS_ALLOW_PAUSED_SILENT
|
||||
|
||||
State = custom.SelfdriveStateSP.ModularAssistiveDrivingSystem.ModularAssistiveDrivingSystemState
|
||||
State = custom.ModularAssistiveDrivingSystem.ModularAssistiveDrivingSystemState
|
||||
ButtonType = car.CarState.ButtonEvent.Type
|
||||
EventName = log.OnroadEvent.EventName
|
||||
EventNameSP = custom.OnroadEventSP.EventName
|
||||
|
||||
@@ -31,7 +31,7 @@ from openpilot.common.realtime import DT_CTRL
|
||||
|
||||
from openpilot.sunnypilot.selfdrive.selfdrived.events import EventsSP
|
||||
|
||||
State = custom.SelfdriveStateSP.ModularAssistiveDrivingSystem.ModularAssistiveDrivingSystemState
|
||||
State = custom.ModularAssistiveDrivingSystem.ModularAssistiveDrivingSystemState
|
||||
EventName = log.OnroadEvent.EventName
|
||||
EventNameSP = custom.OnroadEventSP.EventName
|
||||
|
||||
|
||||
@@ -33,7 +33,7 @@ from openpilot.sunnypilot.mads.state import StateMachine, SOFT_DISABLE_TIME, GEA
|
||||
from openpilot.selfdrive.selfdrived.events import ET, NormalPermanentAlert
|
||||
from openpilot.sunnypilot.selfdrive.selfdrived.events import EVENTS_SP
|
||||
|
||||
State = custom.SelfdriveStateSP.ModularAssistiveDrivingSystem.ModularAssistiveDrivingSystemState
|
||||
State = custom.ModularAssistiveDrivingSystem.ModularAssistiveDrivingSystemState
|
||||
EventNameSP = custom.OnroadEventSP.EventName
|
||||
|
||||
# The event types that maintain the current state
|
||||
|
||||
@@ -1,8 +1,9 @@
|
||||
import os
|
||||
import pickle
|
||||
from abc import ABC, abstractmethod
|
||||
|
||||
import numpy as np
|
||||
|
||||
from cereal import custom
|
||||
from openpilot.selfdrive.modeld import MODEL_PATH, MODEL_PKL_PATH, METADATA_PATH
|
||||
from openpilot.selfdrive.modeld.models.commonmodel_pyx import DrivingModelFrame, CLMem
|
||||
from openpilot.selfdrive.modeld.runners.ort_helpers import make_onnx_cpu_runner, ORT_TYPES_TO_NP_TYPES
|
||||
@@ -10,9 +11,7 @@ from openpilot.selfdrive.modeld.runners.tinygrad_helpers import qcom_tensor_from
|
||||
from openpilot.system.hardware import TICI
|
||||
from openpilot.system.hardware.hw import Paths
|
||||
|
||||
from cereal import custom
|
||||
from openpilot.sunnypilot.models.helpers import get_active_bundle
|
||||
#
|
||||
from tinygrad.tensor import Tensor
|
||||
|
||||
if TICI:
|
||||
|
||||
@@ -0,0 +1,3 @@
|
||||
version https://git-lfs.github.com/spec/v1
|
||||
oid sha256:3d7726f7c6a8106c767ae974ce7395a399dbf0a934779a7710b748917c29cf6e
|
||||
size 11365
|
||||
@@ -0,0 +1,106 @@
|
||||
# The MIT License
|
||||
#
|
||||
# Copyright (c) 2019-, Rick Lan, dragonpilot community, and a number of other of contributors.
|
||||
#
|
||||
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
# of this software and associated documentation files (the "Software"), to deal
|
||||
# in the Software without restriction, including without limitation the rights
|
||||
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
# copies of the Software, and to permit persons to whom the Software is
|
||||
# furnished to do so, subject to the following conditions:
|
||||
#
|
||||
# The above copyright notice and this permission notice shall be included in
|
||||
# all copies or substantial portions of the Software.
|
||||
#
|
||||
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
# THE SOFTWARE.
|
||||
|
||||
# Last updated: August 12, 2024
|
||||
|
||||
from cereal import custom
|
||||
from openpilot.common.numpy_fast import interp
|
||||
from openpilot.common.realtime import DT_MDL
|
||||
from openpilot.common.params import Params
|
||||
#from openpilot.selfdrive.controls.lib.longitudinal_planner import limit_accel_in_turns
|
||||
from opendbc.car.interfaces import ACCEL_MIN
|
||||
|
||||
AccelPersonality = custom.LongitudinalPlanSP.AccelerationPersonality
|
||||
|
||||
# Acceleration Profiles
|
||||
_DP_CRUISE_MIN_V = {
|
||||
AccelPersonality.eco: [-0.015, -0.015, -1.2, -1.2, -1.2, -1.2, -1.2, -1.2],
|
||||
AccelPersonality.normal: [-0.018, -0.018, -1.2, -1.2, -1.2, -1.2, -1.2, -1.2],
|
||||
AccelPersonality.sport: [-0.020, -0.020, -1.2, -1.2, -1.2, -1.2, -1.2, -1.2],
|
||||
}
|
||||
_DP_CRUISE_MAX_V = {
|
||||
AccelPersonality.eco: [1.60, 1.60, 1.58, 1.58, 0.86, .532, .432, .32, .28, .085],
|
||||
AccelPersonality.normal: [1.80, 1.80, 1.75, 1.75, 0.92, .65, .56, .36, .30, .12],
|
||||
AccelPersonality.sport: [2.00, 2.00, 2.00, 2.00, 1.05, .79, .61, .42, .333, .2],
|
||||
}
|
||||
_DP_CRUISE_MIN_BP = [0., 2.0, 2.01, 15., 15.01, 20., 20.01, 40.]
|
||||
_DP_CRUISE_MAX_BP = [0., 1., 6., 8., 11., 16, 20., 25., 30., 55.]
|
||||
|
||||
|
||||
class AccelController:
|
||||
def __init__(self):
|
||||
self._params = Params()
|
||||
self._personality = AccelPersonality.stock
|
||||
self._frame = 0
|
||||
|
||||
def _read_params(self):
|
||||
""" Reads the acceleration personality setting from persistent storage. """
|
||||
if self._frame % int(1. / DT_MDL) == 0:
|
||||
personality_str = self._params.get("AccelPersonality", encoding='utf-8')
|
||||
if personality_str is not None:
|
||||
personality_int = int(personality_str)
|
||||
if personality_int in _DP_CRUISE_MIN_V:
|
||||
self._personality = personality_int
|
||||
# Print the current mode being used
|
||||
print(f"Current Acceleration Personality Mode: {self._personality}")
|
||||
|
||||
def compute_accel_limits(self, v_ego: float, sm, CP) -> tuple[list[float], list[float]]:
|
||||
""" Computes acceleration limits based on personality, turns, and DEC mode. """
|
||||
self._read_params()
|
||||
# Print the current mode being used
|
||||
print(f"Current Acceleration Personality Mode: {self._personality}")
|
||||
|
||||
if self._personality == AccelPersonality.eco:
|
||||
min_v = _DP_CRUISE_MIN_V[AccelPersonality.eco]
|
||||
max_v = _DP_CRUISE_MAX_V[AccelPersonality.eco]
|
||||
print("eco")
|
||||
elif self._personality == AccelPersonality.sport:
|
||||
min_v = _DP_CRUISE_MIN_V[AccelPersonality.sport]
|
||||
max_v = _DP_CRUISE_MAX_V[AccelPersonality.sport]
|
||||
print("sport")
|
||||
else:
|
||||
min_v = _DP_CRUISE_MIN_V[AccelPersonality.normal]
|
||||
max_v = _DP_CRUISE_MAX_V[AccelPersonality.normal]
|
||||
print("normal")
|
||||
|
||||
a_cruise_min = interp(v_ego, _DP_CRUISE_MIN_BP, min_v)
|
||||
a_cruise_max = interp(v_ego, _DP_CRUISE_MAX_BP, max_v)
|
||||
|
||||
# Determine acceleration mode
|
||||
accel_limits = [ACCEL_MIN, a_cruise_max] if CP.radarUnavailable else [a_cruise_min, a_cruise_max]
|
||||
|
||||
# Adjust acceleration for turns
|
||||
#steer_angle = sm['carState'].steeringAngleDeg - sm['liveParameters'].angleOffsetDeg
|
||||
# Ensure accel_limits_turns is a valid list/tuple here
|
||||
accel_limits_turns = accel_limits # This is temporary if limit_accel_in_turns is not defined
|
||||
|
||||
return accel_limits, accel_limits_turns
|
||||
|
||||
|
||||
|
||||
def is_enabled(self) -> bool:
|
||||
""" Returns True if AccelController is actively modifying acceleration limits. """
|
||||
return bool(self._personality != AccelPersonality.stock)
|
||||
|
||||
def update(self):
|
||||
""" Updates the internal frame counter. """
|
||||
self._frame += 1
|
||||
@@ -8,6 +8,7 @@ See the LICENSE.md file in the root directory for more details.
|
||||
from cereal import messaging, custom
|
||||
from opendbc.car import structs
|
||||
from openpilot.sunnypilot.selfdrive.controls.lib.dec.dec import DynamicExperimentalController
|
||||
from openpilot.sunnypilot.selfdrive.controls.lib.accel_personality.accel_controller import AccelController
|
||||
|
||||
DecState = custom.LongitudinalPlanSP.DynamicExperimentalControl.DynamicExperimentalControlState
|
||||
|
||||
@@ -15,19 +16,24 @@ DecState = custom.LongitudinalPlanSP.DynamicExperimentalControl.DynamicExperimen
|
||||
class LongitudinalPlannerSP:
|
||||
def __init__(self, CP: structs.CarParams, mpc):
|
||||
self.dec = DynamicExperimentalController(CP, mpc)
|
||||
self.accel_controller = AccelController()
|
||||
|
||||
def get_mpc_mode(self) -> str | None:
|
||||
if not self.dec.active():
|
||||
return None
|
||||
""" Returns the current MPC mode if DEC is active. """
|
||||
return self.dec.mode() if self.dec.active() else None
|
||||
|
||||
return self.dec.mode()
|
||||
def compute_accel_limits(self, v_ego: float, sm, CP) -> tuple[list[float], list[float]]:
|
||||
""" Delegates acceleration limit computation to AccelController. """
|
||||
return self.accel_controller.compute_accel_limits(v_ego, sm, CP)
|
||||
|
||||
def update(self, sm: messaging.SubMaster) -> None:
|
||||
""" Updates DEC and AccelController states. """
|
||||
self.dec.update(sm)
|
||||
self.accel_controller.update()
|
||||
|
||||
def publish_longitudinal_plan_sp(self, sm: messaging.SubMaster, pm: messaging.PubMaster) -> None:
|
||||
""" Publishes the longitudinal plan state to messaging. """
|
||||
plan_sp_send = messaging.new_message('longitudinalPlanSP')
|
||||
|
||||
plan_sp_send.valid = sm.all_checks(service_list=['carState', 'controlsState'])
|
||||
|
||||
longitudinalPlanSP = plan_sp_send.longitudinalPlanSP
|
||||
|
||||
@@ -5,7 +5,7 @@ import signal
|
||||
import sys
|
||||
import traceback
|
||||
|
||||
from cereal import log
|
||||
from cereal import log, custom
|
||||
import cereal.messaging as messaging
|
||||
import openpilot.system.sentry as sentry
|
||||
from openpilot.common.params import Params, ParamKeyType
|
||||
@@ -49,7 +49,8 @@ def manager_init() -> None:
|
||||
("MadsPauseLateralOnBrake", "0"),
|
||||
("MadsUnifiedEngagementMode", "1"),
|
||||
("ModelManager_LastSyncTime", "0"),
|
||||
("ModelManager_ModelsCache", "")
|
||||
("ModelManager_ModelsCache", ""),
|
||||
("AccelPersonality", str(custom.LongitudinalPlanSP.AccelerationPersonality.stock)),
|
||||
]
|
||||
|
||||
if params.get_bool("RecordFrontLock"):
|
||||
|
||||
+1
-5
@@ -116,12 +116,8 @@ def get_properties() -> tuple[str, str, str]:
|
||||
|
||||
def init(project: SentryProject) -> bool:
|
||||
build_metadata = get_build_metadata()
|
||||
# forks like to mess with this, so double check
|
||||
# comma_remote = build_metadata.openpilot.comma_remote and "commaai" in build_metadata.openpilot.git_origin
|
||||
# if not comma_remote or not is_registered_device() or PC:
|
||||
# return False
|
||||
|
||||
env = "release" if build_metadata.tested_channel else "master"
|
||||
env = build_metadata.channel_type
|
||||
dongle_id, git_username, sunnylink_dongle_id = get_properties()
|
||||
|
||||
integrations = []
|
||||
|
||||
+22
-2
@@ -10,8 +10,11 @@ from openpilot.common.basedir import BASEDIR
|
||||
from openpilot.common.swaglog import cloudlog
|
||||
from openpilot.common.git import get_commit, get_origin, get_branch, get_short_branch, get_commit_date
|
||||
|
||||
RELEASE_BRANCHES = ['release3-staging', 'release3', 'nightly']
|
||||
TESTED_BRANCHES = RELEASE_BRANCHES + ['devel', 'devel-staging', 'nightly-dev']
|
||||
RELEASE_SP_BRANCHES = ['release-c3']
|
||||
TESTED_SP_BRANCHES = ['staging-c3', 'staging-c3-new']
|
||||
MASTER_SP_BRANCHES = ['master', 'master-new']
|
||||
RELEASE_BRANCHES = ['release3-staging', 'release3', 'nightly'] + RELEASE_SP_BRANCHES
|
||||
TESTED_BRANCHES = RELEASE_BRANCHES + ['devel', 'devel-staging', 'nightly-dev'] + TESTED_SP_BRANCHES
|
||||
|
||||
BUILD_METADATA_FILENAME = "build.json"
|
||||
|
||||
@@ -110,6 +113,23 @@ class BuildMetadata:
|
||||
def ui_description(self) -> str:
|
||||
return f"{self.openpilot.version} / {self.openpilot.git_commit[:6]} / {self.channel}"
|
||||
|
||||
@property
|
||||
def master_channel(self) -> bool:
|
||||
return self.channel in MASTER_SP_BRANCHES
|
||||
|
||||
@property
|
||||
def channel_type(self) -> str:
|
||||
if self.channel.startswith("dev-"):
|
||||
return "development"
|
||||
elif self.channel.startswith("staging-"):
|
||||
return "staging"
|
||||
elif self.master_channel:
|
||||
return "master"
|
||||
elif self.tested_channel:
|
||||
return "release"
|
||||
else:
|
||||
return "feature"
|
||||
|
||||
|
||||
def build_metadata_from_dict(build_metadata: dict) -> BuildMetadata:
|
||||
channel = build_metadata.get("channel", "unknown")
|
||||
|
||||
Reference in New Issue
Block a user