diff --git a/.github/workflows/repo-maintenance.yaml b/.github/workflows/repo-maintenance.yaml index e7933dc470..c3646d326d 100644 --- a/.github/workflows/repo-maintenance.yaml +++ b/.github/workflows/repo-maintenance.yaml @@ -72,7 +72,6 @@ jobs: git add . - name: update car docs run: | - scons -j$(nproc) --minimal opendbc_repo python selfdrive/car/docs.py git add docs/CARS.md - name: Create Pull Request diff --git a/.github/workflows/tests.yaml b/.github/workflows/tests.yaml index 760b16326a..1e10418771 100644 --- a/.github/workflows/tests.yaml +++ b/.github/workflows/tests.yaml @@ -181,7 +181,7 @@ jobs: echo "${{ github.sha }}" > ref_commit git add . git commit -m "process-replay refs for ${{ github.repository }}@${{ github.sha }}" || echo "No changes to commit" - git push origin process-replay + git push origin process-replay --force - name: Run regen if: false timeout-minutes: 4 diff --git a/.gitignore b/.gitignore index ebe6ca6c9d..738a150b7e 100644 --- a/.gitignore +++ b/.gitignore @@ -13,13 +13,13 @@ venv/ a.out .hypothesis .cache/ - -/docs_site/ +bin/ *.mp4 *.dylib *.DSYM *.d +*.pem *.pyc *.pyo .*.swp @@ -39,11 +39,13 @@ a.out *.mo *_pyx.cpp *.stats +*.pkl +*.pkl* config.json -clcache compile_commands.json compare_runtime*.html +# build artifacts selfdrive/pandad/pandad cereal/services.h cereal/gen @@ -56,47 +58,30 @@ system/camerad/test/ae_gray_test .coverage* coverage.xml htmlcov -pandaextra - -.mypy_cache/ -flycheck_* - -cppcheck_report.txt -comma*.sh - -selfdrive/modeld/models/*.pkl* -sunnypilot/modeld*/models/*.pkl # openpilot log files *.bz2 *.zst +*.rlog build/ !**/.gitkeep -poetry.toml -Pipfile ### VisualStudioCode ### +*.vsix +.history +.ionide .vscode/* +.history/ !.vscode/settings.json !.vscode/tasks.json !.vscode/launch.json !.vscode/extensions.json !.vscode/*.code-snippets -# Local History for Visual Studio Code -.history/ - -# Built Visual Studio Code Extensions -*.vsix - -### VisualStudioCode Patch ### -# Ignore all local history of files -.history -.ionide - +# agents .claude/ .context/ PLAN.md diff --git a/.python-version b/.python-version new file mode 100644 index 0000000000..28d9a01b1f --- /dev/null +++ b/.python-version @@ -0,0 +1 @@ +3.12.13 diff --git a/Jenkinsfile b/Jenkinsfile index c5ebf6162b..39175d89e3 100644 --- a/Jenkinsfile +++ b/Jenkinsfile @@ -167,7 +167,7 @@ node { env.GIT_COMMIT = checkout(scm).GIT_COMMIT def excludeBranches = ['__nightly', 'devel', 'devel-staging', 'release3', 'release3-staging', - 'release-tici', 'release-tizi', 'release-tizi-staging', 'testing-closet*', 'hotfix-*'] + 'release-tici', 'release-tizi', 'release-tizi-staging', 'release-mici-staging', 'testing-closet*', 'hotfix-*'] def excludeRegex = excludeBranches.join('|').replaceAll('\\*', '.*') if (env.BRANCH_NAME != 'master' && !env.BRANCH_NAME.contains('__jenkins_loop_')) { @@ -179,7 +179,7 @@ node { try { if (env.BRANCH_NAME == 'devel-staging') { deviceStage("build release-tizi-staging", "tizi-needs-can", [], [ - step("build release-tizi-staging", "RELEASE_BRANCH=release-tizi-staging $SOURCE_DIR/release/build_release.sh"), + step("build release-tizi-staging", "RELEASE_BRANCH=release-tizi-staging $SOURCE_DIR/release/build_release.sh && git push -f origin release-tizi-staging:release-mici-staging"), ]) } @@ -218,14 +218,14 @@ node { 'camerad OX03C10': { deviceStage("OX03C10", "tizi-ox03c10", ["UNSAFE=1"], [ step("build", "cd system/manager && ./build.py"), - step("test pandad", "pytest selfdrive/pandad/tests/test_pandad.py", [diffPaths: ["panda", "selfdrive/pandad/"]]), + step("test pandad", "pytest selfdrive/pandad/tests/test_pandad.py"), step("test camerad", "pytest system/camerad/test/test_camerad.py", [timeout: 90]), ]) }, 'camerad OS04C10': { deviceStage("OS04C10", "tici-os04c10", ["UNSAFE=1"], [ step("build", "cd system/manager && ./build.py"), - step("test pandad", "pytest selfdrive/pandad/tests/test_pandad.py", [diffPaths: ["panda", "selfdrive/pandad/"]]), + step("test pandad", "pytest selfdrive/pandad/tests/test_pandad.py"), step("test camerad", "pytest system/camerad/test/test_camerad.py", [timeout: 90]), ]) }, diff --git a/RELEASES.md b/RELEASES.md index 895dcbba7a..a3a95ae6a8 100644 --- a/RELEASES.md +++ b/RELEASES.md @@ -1,8 +1,16 @@ -Version 0.10.4 (2026-02-17) +Version 0.11.1 (2026-04-08) ======================== +* New driver monitoring model +* Improved image processing pipeline for driver camera + +Version 0.11.0 (2026-03-17) +======================== +* New driving model #36798 + * Fully trained using a learned simulator + * Improved longitudinal performance in Experimental mode +* Reduce comma four standby power usage by 77% to 52 mW * Kia K7 2017 support thanks to royjr! * Lexus LS 2018 support thanks to Hacheoy! -* Reduce comma four standby power usage by 77% to 52 mW Version 0.10.3 (2025-12-17) ======================== diff --git a/SConstruct b/SConstruct index 99d5dc4b8a..5e84121fb5 100644 --- a/SConstruct +++ b/SConstruct @@ -4,9 +4,11 @@ import sys import sysconfig import platform import shlex +import importlib import numpy as np import SCons.Errors +from SCons.Defaults import _stripixes SCons.Warnings.warningAsException(True) @@ -14,9 +16,6 @@ Decider('MD5-timestamp') SetOption('num_jobs', max(1, int(os.cpu_count()/2))) -AddOption('--asan', action='store_true', help='turn on ASAN') -AddOption('--ubsan', action='store_true', help='turn on UBSan') -AddOption('--mutation', action='store_true', help='generate mutation-ready code') AddOption('--ccflags', action='store', type='string', default='', help='pass arbitrary flags over the command line') AddOption('--verbose', action='store_true', default=False, help='show full build commands') AddOption('--minimal', @@ -38,23 +37,46 @@ assert arch in [ "Darwin", # macOS arm64 (x86 not supported) ] -if arch != "larch64": - import bzip2 - import capnproto - import eigen - import ffmpeg as ffmpeg_pkg - import libjpeg - import libyuv - import ncurses - import python3_dev - import zeromq - import zstd - pkgs = [bzip2, capnproto, eigen, ffmpeg_pkg, libjpeg, libyuv, ncurses, zeromq, zstd] - py_include = python3_dev.INCLUDE_DIR -else: - # TODO: remove when AGNOS has our new vendor pkgs - pkgs = [] - py_include = sysconfig.get_paths()['include'] +pkg_names = ['bzip2', 'capnproto', 'eigen', 'ffmpeg', 'libjpeg', 'libyuv', 'ncurses', 'zeromq', 'zstd'] +pkgs = [importlib.import_module(name) for name in pkg_names] + + +# ***** enforce a whitelist of system libraries ***** +# this prevents silently relying on a 3rd party package, +# e.g. apt-installed libusb. all libraries should either +# be distributed with all Linux distros and macOS, or +# vendored in commaai/dependencies. +allowed_system_libs = { + "EGL", "GLESv2", "GL", "Qt5Charts", "Qt5Core", "Qt5Gui", "Qt5Widgets", + "dl", "drm", "gbm", "m", "pthread", +} + +def _resolve_lib(env, name): + for d in env.Flatten(env.get('LIBPATH', [])): + p = Dir(str(d)).abspath + for ext in ('.a', '.so', '.dylib'): + f = File(os.path.join(p, f'lib{name}{ext}')) + if f.exists() or f.has_builder(): + return name + if name in allowed_system_libs: + return name + raise SCons.Errors.UserError(f"Unexpected non-vendored library '{name}'") + +def _libflags(target, source, env, for_signature): + libs = [] + lp = env.subst('$LIBLITERALPREFIX') + for lib in env.Flatten(env.get('LIBS', [])): + if isinstance(lib, str): + if os.sep in lib or lib.startswith('#'): + libs.append(File(lib)) + elif lib.startswith('-') or (lp and lib.startswith(lp)): + libs.append(lib) + else: + libs.append(_resolve_lib(env, lib)) + else: + libs.append(lib) + return _stripixes(env['LIBLINKPREFIX'], libs, env['LIBLINKSUFFIX'], + env['LIBPREFIXES'], env['LIBSUFFIXES'], env, env['LIBLITERALPREFIX']) env = Environment( ENV={ @@ -107,14 +129,14 @@ env = Environment( tools=["default", "cython", "compilation_db", "rednose_filter"], toolpath=["#site_scons/site_tools", "#rednose_repo/site_scons/site_tools"], ) +if arch != "larch64": + env['_LIBFLAGS'] = _libflags # Arch-specific flags and paths if arch == "larch64": env["CC"] = "clang" env["CXX"] = "clang++" env.Append(LIBPATH=[ - "/usr/local/lib", - "/system/vendor/lib64", "/usr/lib/aarch64-linux-gnu", ]) arch_flags = ["-D__TICI__", "-mcpu=cortex-a57", "-DQCOM2"] @@ -126,19 +148,6 @@ elif arch == "Darwin": ]) env.Append(CCFLAGS=["-DGL_SILENCE_DEPRECATION"]) env.Append(CXXFLAGS=["-DGL_SILENCE_DEPRECATION"]) -else: - env.Append(LIBPATH=[ - "/usr/lib", - "/usr/local/lib", - ]) - -# Sanitizers and extra CCFLAGS from CLI -if GetOption('asan'): - env.Append(CCFLAGS=["-fsanitize=address", "-fno-omit-frame-pointer"]) - env.Append(LINKFLAGS=["-fsanitize=address"]) -elif GetOption('ubsan'): - env.Append(CCFLAGS=["-fsanitize=undefined"]) - env.Append(LINKFLAGS=["-fsanitize=undefined"]) _extra_cc = shlex.split(GetOption('ccflags') or '') if _extra_cc: @@ -176,7 +185,7 @@ if os.environ.get('SCONS_PROGRESS'): # ********** Cython build environment ********** envCython = env.Clone() -envCython["CPPPATH"] += [py_include, np.get_include()] +envCython["CPPPATH"] += [sysconfig.get_paths()['include'], np.get_include()] envCython["CCFLAGS"] += ["-Wno-#warnings", "-Wno-cpp", "-Wno-shadow", "-Wno-deprecated-declarations"] envCython["CCFLAGS"].remove("-Werror") @@ -210,7 +219,6 @@ Export('common') env_swaglog = env.Clone() env_swaglog['CXXFLAGS'].append('-DSWAGLOG="\\"common/swaglog.h\\""') SConscript(['msgq_repo/SConscript'], exports={'env': env_swaglog}) -SConscript(['opendbc_repo/SConscript'], exports={'env': env_swaglog}) SConscript(['cereal/SConscript']) @@ -236,7 +244,15 @@ if arch == "larch64": # Build openpilot SConscript(['third_party/SConscript']) -SConscript(['selfdrive/SConscript']) +# Build selfdrive +SConscript([ + 'selfdrive/pandad/SConscript', + 'selfdrive/controls/lib/lateral_mpc_lib/SConscript', + 'selfdrive/controls/lib/longitudinal_mpc_lib/SConscript', + 'selfdrive/locationd/SConscript', + 'selfdrive/modeld/SConscript', + 'selfdrive/ui/SConscript', +]) SConscript(['sunnypilot/SConscript']) diff --git a/common/.gitignore b/common/.gitignore deleted file mode 100644 index ce1da4c53c..0000000000 --- a/common/.gitignore +++ /dev/null @@ -1 +0,0 @@ -*.cpp diff --git a/common/SConscript b/common/SConscript index 15a0e5eff1..c9bd1c72d1 100644 --- a/common/SConscript +++ b/common/SConscript @@ -1,4 +1,4 @@ -Import('env', 'envCython', 'arch') +Import('env', 'envCython') common_libs = [ 'params.cc', diff --git a/common/filter_simple.py b/common/filter_simple.py index 212e1a8f40..b28c3d68f5 100644 --- a/common/filter_simple.py +++ b/common/filter_simple.py @@ -28,7 +28,7 @@ class BounceFilter(FirstOrderFilter): scale = self.dt / (1.0 / 60.0) # tuned at 60 fps self.velocity.x += (x - self.x) * self.bounce * scale * self.dt self.velocity.update(0.0) - if abs(self.velocity.x) < 1e-5: + if abs(self.velocity.x) < 1e-3: self.velocity.x = 0.0 self.x += self.velocity.x return self.x diff --git a/common/params_keys.h b/common/params_keys.h index a247798e30..3dc0222617 100644 --- a/common/params_keys.h +++ b/common/params_keys.h @@ -271,7 +271,7 @@ inline static std::unordered_map keys = { {"EnforceTorqueControl", {PERSISTENT | BACKUP, BOOL}}, {"LiveTorqueParamsToggle", {PERSISTENT | BACKUP , BOOL}}, {"LiveTorqueParamsRelaxedToggle", {PERSISTENT | BACKUP , BOOL}}, - {"TorqueControlTune", {PERSISTENT | BACKUP, FLOAT}}, + {"TorqueControlTune", {PERSISTENT | BACKUP, FLOAT, "0.0"}}, {"TorqueParamsOverrideEnabled", {PERSISTENT | BACKUP, BOOL, "0"}}, {"TorqueParamsOverrideFriction", {PERSISTENT | BACKUP, FLOAT, "0.1"}}, {"TorqueParamsOverrideLatAccelFactor", {PERSISTENT | BACKUP, FLOAT, "2.5"}}, diff --git a/common/time_helpers.py b/common/time_helpers.py index 8564e270c2..c709182d45 100644 --- a/common/time_helpers.py +++ b/common/time_helpers.py @@ -2,6 +2,7 @@ import datetime from pathlib import Path MIN_DATE = datetime.datetime(year=2025, month=2, day=21) +MAX_DATE = datetime.datetime(year=2035, month=1, day=1) def min_date(): # on systemd systems, the default time is the systemd build time @@ -12,4 +13,4 @@ def min_date(): return MIN_DATE def system_time_valid(): - return datetime.datetime.now() > min_date() + return min_date() < datetime.datetime.now() < MAX_DATE diff --git a/common/transformations/.gitignore b/common/transformations/.gitignore deleted file mode 100644 index a67290f09a..0000000000 --- a/common/transformations/.gitignore +++ /dev/null @@ -1,2 +0,0 @@ -transformations -transformations.cpp diff --git a/common/version.h b/common/version.h index 7e78d64b22..41440556c5 100644 --- a/common/version.h +++ b/common/version.h @@ -1 +1 @@ -#define COMMA_VERSION "0.10.4" +#define COMMA_VERSION "0.11.1" diff --git a/conftest.py b/conftest.py index 0bd638b87d..2f2db08d5d 100644 --- a/conftest.py +++ b/conftest.py @@ -10,7 +10,6 @@ from openpilot.system.hardware import TICI, HARDWARE # TODO: pytest-cpp doesn't support FAIL, and we need to create test translations in sessionstart # pending https://github.com/pytest-dev/pytest-cpp/pull/147 collect_ignore = [ - "selfdrive/ui/tests/test_translations", "selfdrive/test/process_replay/test_processes.py", "selfdrive/test/process_replay/test_regen.py", ] diff --git a/launch_env.sh b/launch_env.sh index 314366f429..e409a80dd4 100755 --- a/launch_env.sh +++ b/launch_env.sh @@ -16,7 +16,7 @@ export VECLIB_MAXIMUM_THREADS=1 export QCOM_PRIORITY=12 if [ -z "$AGNOS_VERSION" ]; then - export AGNOS_VERSION="16" + export AGNOS_VERSION="17.2" fi export STAGING_ROOT="/data/safe_staging" diff --git a/panda b/panda index f5f296c65c..6ddc631bdd 160000 --- a/panda +++ b/panda @@ -1 +1 @@ -Subproject commit f5f296c65c756a9b81af845cd874ee054d9c598c +Subproject commit 6ddc631bdd57583a75d5668cad53c42be21a5c4b diff --git a/pyproject.toml b/pyproject.toml index 9c43b20f12..6c84f63863 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -26,18 +26,18 @@ dependencies = [ "numpy >=2.0", # vendored native dependencies - "bzip2 @ git+https://github.com/commaai/dependencies.git@releases#subdirectory=bzip2", - "capnproto @ git+https://github.com/commaai/dependencies.git@releases#subdirectory=capnproto", - "eigen @ git+https://github.com/commaai/dependencies.git@releases#subdirectory=eigen", - "ffmpeg @ git+https://github.com/commaai/dependencies.git@releases#subdirectory=ffmpeg", - "libjpeg @ git+https://github.com/commaai/dependencies.git@releases#subdirectory=libjpeg", - "libyuv @ git+https://github.com/commaai/dependencies.git@releases#subdirectory=libyuv", - "python3-dev @ git+https://github.com/commaai/dependencies.git@releases#subdirectory=python3-dev", - "zstd @ git+https://github.com/commaai/dependencies.git@releases#subdirectory=zstd", - "ncurses @ git+https://github.com/commaai/dependencies.git@releases#subdirectory=ncurses", - "zeromq @ git+https://github.com/commaai/dependencies.git@releases#subdirectory=zeromq", - "git-lfs @ git+https://github.com/commaai/dependencies.git@releases#subdirectory=git-lfs", - "gcc-arm-none-eabi @ git+https://github.com/commaai/dependencies.git@releases#subdirectory=gcc-arm-none-eabi", + "bzip2 @ git+https://github.com/commaai/dependencies.git@release-bzip2#subdirectory=bzip2", + "capnproto @ git+https://github.com/commaai/dependencies.git@release-capnproto#subdirectory=capnproto", + "eigen @ git+https://github.com/commaai/dependencies.git@release-eigen#subdirectory=eigen", + "ffmpeg @ git+https://github.com/commaai/dependencies.git@release-ffmpeg#subdirectory=ffmpeg", + "libjpeg @ git+https://github.com/commaai/dependencies.git@release-libjpeg#subdirectory=libjpeg", + "libyuv @ git+https://github.com/commaai/dependencies.git@release-libyuv#subdirectory=libyuv", + "zstd @ git+https://github.com/commaai/dependencies.git@release-zstd#subdirectory=zstd", + "ncurses @ git+https://github.com/commaai/dependencies.git@release-ncurses#subdirectory=ncurses", + "zeromq @ git+https://github.com/commaai/dependencies.git@release-zeromq#subdirectory=zeromq", + "libusb @ git+https://github.com/commaai/dependencies.git@release-libusb#subdirectory=libusb", + "git-lfs @ git+https://github.com/commaai/dependencies.git@release-git-lfs#subdirectory=git-lfs", + "gcc-arm-none-eabi @ git+https://github.com/commaai/dependencies.git@release-gcc-arm-none-eabi#subdirectory=gcc-arm-none-eabi", # body / webrtcd "av", @@ -206,6 +206,7 @@ lint.flake8-implicit-str-concat.allow-multiline = false "pyray.is_mouse_button_pressed".msg = "This can miss events. Use Widget._handle_mouse_press" "pyray.is_mouse_button_released".msg = "This can miss events. Use Widget._handle_mouse_release" "pyray.draw_text".msg = "Use a function (such as rl.draw_font_ex) that takes font as an argument" +"pyray.draw_texture".msg = "Use rl.draw_texture_ex for float position support" [tool.ruff.format] quote-style = "preserve" @@ -249,3 +250,6 @@ unsupported-operator = "ignore" # Ignore not-subscriptable - false positives from dynamic types not-subscriptable = "ignore" # not-iterable errors are now fixed + +[tool.uv] +python-preference = "only-managed" diff --git a/release/pack.py b/release/pack.py index 8979e0e618..8831a0b34d 100755 --- a/release/pack.py +++ b/release/pack.py @@ -13,11 +13,12 @@ from openpilot.common.basedir import BASEDIR DIRS = ['cereal', 'openpilot'] EXTS = ['.png', '.py', '.ttf', '.capnp', '.json', '.fnt', '.mo', '.po'] +EXCLUDE = ['selfdrive/assets/training', 'third_party/raylib/raylib_repo/examples'] INTERPRETER = '/usr/bin/env python3' def copy(src, dest): - if any(src.endswith(ext) for ext in EXTS): + if any(src.endswith(ext) for ext in EXTS) and not any(exc in src for exc in EXCLUDE): shutil.copy2(src, dest, follow_symlinks=True) @@ -28,6 +29,8 @@ if __name__ == '__main__': parser.add_argument('module', help="the module to target, e.g. 'openpilot.system.ui.spinner'") args = parser.parse_args() + print('WARNING: copying all files! make sure to run scons and git tree is clean') + if not args.output: args.output = args.module diff --git a/selfdrive/SConscript b/selfdrive/SConscript deleted file mode 100644 index 55f347c44e..0000000000 --- a/selfdrive/SConscript +++ /dev/null @@ -1,6 +0,0 @@ -SConscript(['pandad/SConscript']) -SConscript(['controls/lib/lateral_mpc_lib/SConscript']) -SConscript(['controls/lib/longitudinal_mpc_lib/SConscript']) -SConscript(['locationd/SConscript']) -SConscript(['modeld/SConscript']) -SConscript(['ui/SConscript']) diff --git a/selfdrive/assets/.gitignore b/selfdrive/assets/.gitignore index fffd4b4ed9..2d97f8b111 100644 --- a/selfdrive/assets/.gitignore +++ b/selfdrive/assets/.gitignore @@ -1,4 +1,2 @@ -*.cc fonts/*.fnt fonts/*.png -translations_assets.qrc diff --git a/selfdrive/assets/icons_mici/onroad/bookmark_fill.png b/selfdrive/assets/icons_mici/onroad/bookmark_fill.png deleted file mode 100644 index 531d5db1cf..0000000000 --- a/selfdrive/assets/icons_mici/onroad/bookmark_fill.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:f3f57346a1cf9a66f9fd746f87bcebb23b7a403e9d6e4fd7701b126abcdd47ea -size 18476 diff --git a/selfdrive/assets/icons_mici/settings/device/language.png b/selfdrive/assets/icons_mici/settings/device/language.png deleted file mode 100644 index d2ef27de36..0000000000 --- a/selfdrive/assets/icons_mici/settings/device/language.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:f646263b26de46f79cac836ef6865b0f25ddc91e386b99311723b68bd06693c9 -size 3304 diff --git a/selfdrive/assets/icons_mici/setup/back_new.png b/selfdrive/assets/icons_mici/setup/back_new.png deleted file mode 100644 index 20e7fe3b88..0000000000 --- a/selfdrive/assets/icons_mici/setup/back_new.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:d29a9c295b33b3164c37a68ad77795595e6ac877a5b308d28112b0315ecd498f -size 1687 diff --git a/selfdrive/assets/icons_mici/setup/factory_reset.png b/selfdrive/assets/icons_mici/setup/factory_reset.png new file mode 100644 index 0000000000..bcb3ea92cb --- /dev/null +++ b/selfdrive/assets/icons_mici/setup/factory_reset.png @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:122a614d1aa26187507951f932160eebfddfebcb4293e78f8d23e350fc97bc0f +size 11489 diff --git a/selfdrive/assets/icons_mici/setup/medium_button_bg.png b/selfdrive/assets/icons_mici/setup/medium_button_bg.png deleted file mode 100644 index e79dc2eb58..0000000000 --- a/selfdrive/assets/icons_mici/setup/medium_button_bg.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:9e363a79dc35ca4c4e9efaa6a843d37ad219efa5299d3e538d8249affa230096 -size 7935 diff --git a/selfdrive/assets/icons_mici/setup/medium_button_pressed_bg.png b/selfdrive/assets/icons_mici/setup/medium_button_pressed_bg.png deleted file mode 100644 index e52fb0c17d..0000000000 --- a/selfdrive/assets/icons_mici/setup/medium_button_pressed_bg.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:cc6fb48520143b6fa1f060d8212e6d929917ab616ce943b5fab5a60665f00da5 -size 18225 diff --git a/selfdrive/assets/icons_mici/setup/reset/small_button.png b/selfdrive/assets/icons_mici/setup/reset/small_button.png deleted file mode 100644 index e3f58b1078..0000000000 --- a/selfdrive/assets/icons_mici/setup/reset/small_button.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:7a198f13f30b3dbc09f30d7fd8033a0bc07a0da9b010b7ca6ed2678430c9e5b4 -size 6949 diff --git a/selfdrive/assets/icons_mici/setup/reset/small_button_pressed.png b/selfdrive/assets/icons_mici/setup/reset/small_button_pressed.png deleted file mode 100644 index 5b502e00aa..0000000000 --- a/selfdrive/assets/icons_mici/setup/reset/small_button_pressed.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:75289d004709def2a2d6101a0330ec867895068ec3807aefc2a26d423d907a13 -size 13437 diff --git a/selfdrive/assets/icons_mici/setup/reset/wide_button.png b/selfdrive/assets/icons_mici/setup/reset/wide_button.png deleted file mode 100644 index 3892f6eb8c..0000000000 --- a/selfdrive/assets/icons_mici/setup/reset/wide_button.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:2452aaf59da18be1b74b475851d66e5c73c50aa49820419a288b1fdb7b42dee1 -size 9071 diff --git a/selfdrive/assets/icons_mici/setup/reset/wide_button_pressed.png b/selfdrive/assets/icons_mici/setup/reset/wide_button_pressed.png deleted file mode 100644 index 3a34af8846..0000000000 --- a/selfdrive/assets/icons_mici/setup/reset/wide_button_pressed.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:6478f7c1c5ef2013e94fc4218ab370889883c5c12231ba3e0975874cb0b6fec9 -size 21893 diff --git a/selfdrive/assets/icons_mici/setup/reset_failed.png b/selfdrive/assets/icons_mici/setup/reset_failed.png new file mode 100644 index 0000000000..680df97cbc --- /dev/null +++ b/selfdrive/assets/icons_mici/setup/reset_failed.png @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:8d5b8f76e5f47e77e5af3016ebdbe548ad3bc9af83a1111b3214bf4017c95a28 +size 11792 diff --git a/selfdrive/assets/icons_mici/setup/scroll_down_indicator.png b/selfdrive/assets/icons_mici/setup/scroll_down_indicator.png deleted file mode 100644 index 3cd26e5181..0000000000 --- a/selfdrive/assets/icons_mici/setup/scroll_down_indicator.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:a733c425113a7f6ff5ec3dc50ef94b5481c0f2d306e33d1485be8ee6b2798532 -size 1136 diff --git a/selfdrive/assets/icons_mici/setup/small_red_pill.png b/selfdrive/assets/icons_mici/setup/small_red_pill.png deleted file mode 100644 index 4a7db930a0..0000000000 --- a/selfdrive/assets/icons_mici/setup/small_red_pill.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:b3a336afddad80dc91caca91d54bd29897ce491f180374edf9a5ba517cbc00e9 -size 8765 diff --git a/selfdrive/assets/icons_mici/setup/small_red_pill_pressed.png b/selfdrive/assets/icons_mici/setup/small_red_pill_pressed.png deleted file mode 100644 index a8d51960c4..0000000000 --- a/selfdrive/assets/icons_mici/setup/small_red_pill_pressed.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:8eee9f10ca80a4e6100c00c02bb46aa5f253b14b086ab9982cfa85ee94eec162 -size 22512 diff --git a/selfdrive/assets/icons_mici/setup/small_slider/slider_bg.png b/selfdrive/assets/icons_mici/setup/small_slider/slider_bg.png deleted file mode 100644 index 43c10a54ad..0000000000 --- a/selfdrive/assets/icons_mici/setup/small_slider/slider_bg.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:94a86fac6ffe8a8179812cf55350ab9ca6935f36244c6f679c1cf521a842316b -size 5723 diff --git a/selfdrive/assets/icons_mici/setup/small_slider/slider_red_circle.png b/selfdrive/assets/icons_mici/setup/small_slider/slider_red_circle.png deleted file mode 100644 index 541433be76..0000000000 --- a/selfdrive/assets/icons_mici/setup/small_slider/slider_red_circle.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:6ccb5f2298389ae36df87de84d85440ee5a82c50e803c9bd362c9b89ea45aa69 -size 6611 diff --git a/selfdrive/assets/icons_mici/setup/small_slider/slider_red_circle_pressed.png b/selfdrive/assets/icons_mici/setup/small_slider/slider_red_circle_pressed.png deleted file mode 100644 index eea6eded86..0000000000 --- a/selfdrive/assets/icons_mici/setup/small_slider/slider_red_circle_pressed.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:a804da77b268f0a625f93949642ae74cdfe5b5caa5baea1c52c4605ae25c80e4 -size 12916 diff --git a/selfdrive/assets/icons_mici/setup/smaller_button.png b/selfdrive/assets/icons_mici/setup/smaller_button.png deleted file mode 100644 index 9b4851c568..0000000000 --- a/selfdrive/assets/icons_mici/setup/smaller_button.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:89ca7e6bb01dfa78300126ce828cb2a64e7a2e68e1e9152de242f57a36d0e57a -size 8604 diff --git a/selfdrive/assets/icons_mici/setup/smaller_button_disabled.png b/selfdrive/assets/icons_mici/setup/smaller_button_disabled.png deleted file mode 100644 index 6514791de7..0000000000 --- a/selfdrive/assets/icons_mici/setup/smaller_button_disabled.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:b3242a411b559f1d0308f189fe0d25b81d6c7d964ca418a0c599a1bab4bffcbb -size 5341 diff --git a/selfdrive/assets/icons_mici/setup/smaller_button_pressed.png b/selfdrive/assets/icons_mici/setup/smaller_button_pressed.png deleted file mode 100644 index 64235b3a2f..0000000000 --- a/selfdrive/assets/icons_mici/setup/smaller_button_pressed.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:d354651c0c8107dcc5f599777d260f53ef1901123315785ed8190466166cdce8 -size 17554 diff --git a/selfdrive/assets/icons_mici/setup/widish_button.png b/selfdrive/assets/icons_mici/setup/widish_button.png deleted file mode 100644 index 529b7c80cc..0000000000 --- a/selfdrive/assets/icons_mici/setup/widish_button.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:74fc21132b1e761ea54ce64617730c6ee79d01668244ab555b3b89870cfea181 -size 7112 diff --git a/selfdrive/assets/icons_mici/setup/widish_button_disabled.png b/selfdrive/assets/icons_mici/setup/widish_button_disabled.png deleted file mode 100644 index 5028a8cd21..0000000000 --- a/selfdrive/assets/icons_mici/setup/widish_button_disabled.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:9728423bd5e3197ef02d62e4bae415e6694aab875ca8630ffc9f188c38e18e5f -size 4141 diff --git a/selfdrive/assets/icons_mici/setup/widish_button_pressed.png b/selfdrive/assets/icons_mici/setup/widish_button_pressed.png deleted file mode 100644 index 1095d4fc23..0000000000 --- a/selfdrive/assets/icons_mici/setup/widish_button_pressed.png +++ /dev/null @@ -1,3 +0,0 @@ -version https://git-lfs.github.com/spec/v1 -oid sha256:0ff179f93f421edcb503ca5c22a12b37e3a2aaabc414bf90f57e20ff5255dd75 -size 15572 diff --git a/selfdrive/car/tests/.gitignore b/selfdrive/car/tests/.gitignore deleted file mode 100644 index 192fb0945e..0000000000 --- a/selfdrive/car/tests/.gitignore +++ /dev/null @@ -1 +0,0 @@ -*.bz2 diff --git a/selfdrive/controls/.gitignore b/selfdrive/controls/.gitignore deleted file mode 100644 index 22a371d8ff..0000000000 --- a/selfdrive/controls/.gitignore +++ /dev/null @@ -1,2 +0,0 @@ -calibration_param -traces diff --git a/selfdrive/locationd/.gitignore b/selfdrive/locationd/.gitignore deleted file mode 100644 index 1a8c72388a..0000000000 --- a/selfdrive/locationd/.gitignore +++ /dev/null @@ -1,2 +0,0 @@ -params_learner -paramsd diff --git a/selfdrive/locationd/lagd.py b/selfdrive/locationd/lagd.py index f432eb88bb..d037af613a 100755 --- a/selfdrive/locationd/lagd.py +++ b/selfdrive/locationd/lagd.py @@ -29,11 +29,26 @@ MIN_LAG = 0.15 MAX_LAG_STD = 0.1 MAX_LAT_ACCEL = 2.0 MAX_LAT_ACCEL_DIFF = 0.6 +MIN_LAT_ACCEL_RANGE = 0.5 MIN_CONFIDENCE = 0.7 CORR_BORDER_OFFSET = 5 LAG_CANDIDATE_CORR_THRESHOLD = 0.9 +SMOOTH_K = 5 +SMOOTH_SIGMA = 1.0 +def masked_symmetric_moving_average(x: np.ndarray, mask: np.ndarray, k: int, sigma: float) -> np.ndarray: + assert k >= 1 and k % 2 == 1, "k must be positive and odd" + pad = k // 2 + i = np.arange(k) - pad + w = np.exp(-0.5 * (i / sigma) ** 2) + w /= w.sum() + xp = np.pad(x * mask, pad, mode="edge") + mp = np.pad(mask, pad, mode="edge") + num = np.convolve(xp, w, mode="valid") + den = np.convolve(mp, w, mode="valid") + return np.divide(num, den, out=np.full_like(num, np.nan, dtype=np.float64), where=den != 0) + def masked_normalized_cross_correlation(expected_sig: np.ndarray, actual_sig: np.ndarray, mask: np.ndarray, n: int): """ References: @@ -295,11 +310,14 @@ class LateralLagEstimator: times, desired, actual, okay = self.points.get() # check if there are any new valid data points since the last update - is_valid = self.points_valid() + is_valid = self.points_valid() and (actual.max() - actual.min() >= MIN_LAT_ACCEL_RANGE) if self.last_estimate_t != 0 and times[0] <= self.last_estimate_t: new_values_start_idx = next(-i for i, t in enumerate(reversed(times)) if t <= self.last_estimate_t) is_valid = is_valid and not (new_values_start_idx == 0 or not np.any(okay[new_values_start_idx:])) + desired = masked_symmetric_moving_average(desired, okay, SMOOTH_K, SMOOTH_SIGMA) + actual = masked_symmetric_moving_average(actual, okay, SMOOTH_K, SMOOTH_SIGMA) + delay, corr, confidence = self.actuator_delay(desired, actual, okay, self.dt, MIN_LAG, MAX_LAG) if corr < self.min_ncc or confidence < self.min_confidence or not is_valid: return @@ -311,16 +329,16 @@ class LateralLagEstimator: def actuator_delay(expected_sig: np.ndarray, actual_sig: np.ndarray, mask: np.ndarray, dt: float, min_lag: float, max_lag: float) -> tuple[float, float, float]: assert len(expected_sig) == len(actual_sig) - min_lag_samples, max_lag_samples = int(round(min_lag / dt)), int(round(max_lag / dt)) - padded_size = fft_next_good_size(len(expected_sig) + max_lag_samples) + min_lag_samples, max_lag_samples, one_sec_samples = int(round(min_lag / dt)), int(round(max_lag / dt)), int(round(1.0 / dt)) + padded_size = fft_next_good_size(len(expected_sig) + max(max_lag_samples, one_sec_samples)) ncc = masked_normalized_cross_correlation(expected_sig, actual_sig, mask, padded_size) - # only consider lags from min_lag to max_lag - roi = np.s_[len(expected_sig) - 1 + min_lag_samples: len(expected_sig) - 1 + max_lag_samples] - extended_roi = np.s_[roi.start - CORR_BORDER_OFFSET: roi.stop + CORR_BORDER_OFFSET] - roi_ncc = ncc[roi] - extended_roi_ncc = ncc[extended_roi] + # only consider lags from ranges: + roi = np.s_[len(expected_sig) - 1 + min_lag_samples: len(expected_sig) - 1 + max_lag_samples] # min_lag - max_lag range + threshold_roi = np.s_[len(expected_sig) - 1: len(expected_sig) - 1 + one_sec_samples] # 0 - 1 second range + confidence_roi = np.s_[threshold_roi.start - CORR_BORDER_OFFSET: threshold_roi.stop + CORR_BORDER_OFFSET] # threshold range +/- border + roi_ncc, confidence_roi_ncc, threshold_roi_ncc = ncc[roi], ncc[confidence_roi], ncc[threshold_roi] max_corr_index = np.argmax(roi_ncc) corr = roi_ncc[max_corr_index] @@ -328,8 +346,8 @@ class LateralLagEstimator: # to estimate lag confidence, gather all high-correlation candidates and see how spread they are # if e.g. 0.8 and 0.4 are both viable, this is an ambiguous case - ncc_thresh = (roi_ncc.max() - roi_ncc.min()) * LAG_CANDIDATE_CORR_THRESHOLD + roi_ncc.min() - good_lag_candidate_mask = extended_roi_ncc >= ncc_thresh + ncc_thresh = (threshold_roi_ncc.max() - threshold_roi_ncc.min()) * LAG_CANDIDATE_CORR_THRESHOLD + threshold_roi_ncc.min() + good_lag_candidate_mask = confidence_roi_ncc >= ncc_thresh good_lag_candidate_edges = np.diff(good_lag_candidate_mask.astype(int), prepend=0, append=0) starts, ends = np.where(good_lag_candidate_edges == 1)[0], np.where(good_lag_candidate_edges == -1)[0] - 1 run_idx = np.searchsorted(starts, max_corr_index + CORR_BORDER_OFFSET, side='right') - 1 diff --git a/selfdrive/locationd/test/.gitignore b/selfdrive/locationd/test/.gitignore deleted file mode 100644 index 89f9ac04aa..0000000000 --- a/selfdrive/locationd/test/.gitignore +++ /dev/null @@ -1 +0,0 @@ -out/ diff --git a/selfdrive/locationd/test/test_lagd.py b/selfdrive/locationd/test/test_lagd.py index 4728413d9d..6249e6b04b 100644 --- a/selfdrive/locationd/test/test_lagd.py +++ b/selfdrive/locationd/test/test_lagd.py @@ -19,8 +19,8 @@ DT = 0.05 def process_messages(estimator, lag_frames, n_frames, vego=20.0, rejection_threshold=0.0): for i in range(n_frames): t = i * estimator.dt - desired_la = np.cos(10 * t) * 0.1 - actual_la = np.cos(10 * (t - lag_frames * estimator.dt)) * 0.1 + desired_la = np.cos(10 * t) * 0.3 + actual_la = np.cos(10 * (t - lag_frames * estimator.dt)) * 0.3 # if sample is masked out, set it to desired value (no lag) rejected = random.uniform(0, 1) < rejection_threshold diff --git a/selfdrive/modeld/SConscript b/selfdrive/modeld/SConscript index ff63b644d5..552a02025e 100644 --- a/selfdrive/modeld/SConscript +++ b/selfdrive/modeld/SConscript @@ -45,13 +45,17 @@ def tg_compile(flags, model_name): pkl = fn + "_tinygrad.pkl" onnx_path = fn + ".onnx" chunk_targets = get_chunk_paths(pkl, estimate_pickle_max_size(os.path.getsize(onnx_path))) + compile_node = lenv.Command( + pkl, + [onnx_path] + tinygrad_files + [chunker_file], + f'{pythonpath_string} {flags} {image_flag} python3 {Dir("#tinygrad_repo").abspath}/examples/openpilot/compile3.py {fn}.onnx {pkl}', + ) def do_chunk(target, source, env): chunk_file(pkl, chunk_targets) return lenv.Command( chunk_targets, - [onnx_path] + tinygrad_files + [chunker_file], - [f'{pythonpath_string} {flags} {image_flag} python3 {Dir("#tinygrad_repo").abspath}/examples/openpilot/compile3.py {fn}.onnx {pkl}', - do_chunk] + compile_node, + do_chunk, ) # Compile small models diff --git a/selfdrive/test/.gitignore b/selfdrive/test/.gitignore index 5801faadf4..b8c6bebd95 100644 --- a/selfdrive/test/.gitignore +++ b/selfdrive/test/.gitignore @@ -3,7 +3,7 @@ docker_out/ process_replay/diff.txt process_replay/model_diff.txt +process_replay/fakedata/ valgrind_logs.txt -*.bz2 *.hevc diff --git a/selfdrive/test/process_replay/.gitignore b/selfdrive/test/process_replay/.gitignore deleted file mode 100644 index a35cd58d41..0000000000 --- a/selfdrive/test/process_replay/.gitignore +++ /dev/null @@ -1 +0,0 @@ -fakedata/ diff --git a/selfdrive/test/test_onroad.py b/selfdrive/test/test_onroad.py index 008b8ebe7f..1129a1a2ff 100644 --- a/selfdrive/test/test_onroad.py +++ b/selfdrive/test/test_onroad.py @@ -342,10 +342,15 @@ class TestOnroad: start, end = min(first_fid), min(last_fid) for i in range(end-start): - ts = {c: round(self.ts[c]['timestampSof'][i]/1e6, 1) for c in cams} + # road and wide cameras (first two) should be synced within 2ms + ts = {c: round(self.ts[c]['timestampSof'][i]/1e6, 1) for c in cams[:2]} diff = (max(ts.values()) - min(ts.values())) assert diff < 2, f"Cameras not synced properly: frame_id={start+i}, {diff=:.1f}ms, {ts=}" + # driver camera should be staggered ~25ms from road camera + offset_ms = abs(self.ts[cams[2]]['timestampSof'][i] - self.ts[cams[0]]['timestampSof'][i]) / 1e6 + assert 20 < offset_ms < 30, f"driver camera stagger out of range at frame {start+i}: {offset_ms:.1f}ms" + def test_camera_encoder_matches(self, subtests): # sanity check that the frame metadata is consistent with the encoded frames pairs = [('roadCameraState', 'roadEncodeIdx'), diff --git a/selfdrive/ui/.gitignore b/selfdrive/ui/.gitignore index 945928f617..30ae77d885 100644 --- a/selfdrive/ui/.gitignore +++ b/selfdrive/ui/.gitignore @@ -1 +1,4 @@ installer/installers/* + +tests/diff/report +.coverage diff --git a/selfdrive/ui/SConscript b/selfdrive/ui/SConscript index 4d7448c62f..1a662e6b24 100644 --- a/selfdrive/ui/SConscript +++ b/selfdrive/ui/SConscript @@ -1,4 +1,3 @@ -import re from pathlib import Path Import('env', 'arch', 'common') @@ -19,39 +18,38 @@ env.Command( if GetOption('extras') and arch == "larch64": # build installers - if arch != "Darwin": - raylib_env = env.Clone() - raylib_env['LIBPATH'] += [f'#third_party/raylib/{arch}/'] - raylib_env['LINKFLAGS'].append('-Wl,-strip-debug') + raylib_env = env.Clone() + raylib_env['LIBPATH'] += [f'#third_party/raylib/{arch}/'] + raylib_env['LINKFLAGS'].append('-Wl,-strip-debug') - raylib_libs = common + ["raylib"] - if arch == "larch64": - raylib_libs += ["GLESv2", "EGL", "gbm", "drm"] - else: - raylib_libs += ["GL"] + raylib_libs = common + ["raylib"] + if arch == "larch64": + raylib_libs += ["GLESv2", "EGL", "gbm", "drm"] + else: + raylib_libs += ["GL"] - release = "release3" - installers = [ - ("openpilot", release), - ("openpilot_test", f"{release}-staging"), - ("openpilot_nightly", "nightly"), - ("openpilot_internal", "nightly-dev"), - ] + release = "release3" + installers = [ + ("openpilot", release), + ("openpilot_test", f"{release}-staging"), + ("openpilot_nightly", "nightly"), + ("openpilot_internal", "nightly-dev"), + ] - cont = raylib_env.Command("installer/continue_openpilot.o", "installer/continue_openpilot.sh", + cont = raylib_env.Command("installer/continue_openpilot.o", "installer/continue_openpilot.sh", + "ld -r -b binary -o $TARGET $SOURCE") + inter = raylib_env.Command("installer/inter_ttf.o", "installer/inter-ascii.ttf", + "ld -r -b binary -o $TARGET $SOURCE") + inter_bold = raylib_env.Command("installer/inter_bold.o", "../assets/fonts/Inter-Bold.ttf", "ld -r -b binary -o $TARGET $SOURCE") - inter = raylib_env.Command("installer/inter_ttf.o", "installer/inter-ascii.ttf", - "ld -r -b binary -o $TARGET $SOURCE") - inter_bold = raylib_env.Command("installer/inter_bold.o", "../assets/fonts/Inter-Bold.ttf", - "ld -r -b binary -o $TARGET $SOURCE") - inter_light = raylib_env.Command("installer/inter_light.o", "../assets/fonts/Inter-Light.ttf", - "ld -r -b binary -o $TARGET $SOURCE") - for name, branch in installers: - d = {'BRANCH': f"'\"{branch}\"'"} - if "internal" in name: - d['INTERNAL'] = "1" + inter_light = raylib_env.Command("installer/inter_light.o", "../assets/fonts/Inter-Light.ttf", + "ld -r -b binary -o $TARGET $SOURCE") + for name, branch in installers: + d = {'BRANCH': f"'\"{branch}\"'"} + if "internal" in name: + d['INTERNAL'] = "1" - obj = raylib_env.Object(f"installer/installers/installer_{name}.o", ["installer/installer.cc"], CPPDEFINES=d) - f = raylib_env.Program(f"installer/installers/installer_{name}", [obj, cont, inter, inter_bold, inter_light], LIBS=raylib_libs) - # keep installers small - assert f[0].get_size() < 2500*1e3, f[0].get_size() + obj = raylib_env.Object(f"installer/installers/installer_{name}.o", ["installer/installer.cc"], CPPDEFINES=d) + f = raylib_env.Program(f"installer/installers/installer_{name}", [obj, cont, inter, inter_bold, inter_light], LIBS=raylib_libs) + # keep installers small + assert f[0].get_size() < 2500*1e3, f[0].get_size() diff --git a/selfdrive/ui/installer/installer.cc b/selfdrive/ui/installer/installer.cc index 9c35b0465e..7599454194 100644 --- a/selfdrive/ui/installer/installer.cc +++ b/selfdrive/ui/installer/installer.cc @@ -81,14 +81,16 @@ void run(const char* cmd) { } void finishInstall() { - if (tici_device) { - BeginDrawing(); - ClearBackground(BLACK); + BeginDrawing(); + ClearBackground(BLACK); + if (tici_device) { const char *m = "Finishing install..."; int text_width = MeasureText(m, FONT_SIZE); DrawTextEx(font_display, m, (Vector2){(float)(GetScreenWidth() - text_width)/2 + FONT_SIZE, (float)(GetScreenHeight() - FONT_SIZE)/2}, FONT_SIZE, 0, WHITE); - EndDrawing(); - } + } else { + DrawTextEx(font_display, "finishing setup", (Vector2){12, 0}, 77, 0, (Color){255, 255, 255, (unsigned char)(255 * 0.9)}); + } + EndDrawing(); util::sleep_for(60 * 1000); } diff --git a/selfdrive/ui/layouts/home.py b/selfdrive/ui/layouts/home.py index bb4b868f2d..be231dcd4b 100644 --- a/selfdrive/ui/layouts/home.py +++ b/selfdrive/ui/layouts/home.py @@ -62,6 +62,7 @@ class HomeLayout(Widget): self._setup_callbacks() def show_event(self): + super().show_event() self._exp_mode_button.show_event() self.last_refresh = time.monotonic() self._refresh() diff --git a/selfdrive/ui/layouts/onboarding.py b/selfdrive/ui/layouts/onboarding.py index c53db2231a..452ed53c08 100644 --- a/selfdrive/ui/layouts/onboarding.py +++ b/selfdrive/ui/layouts/onboarding.py @@ -94,7 +94,7 @@ class TrainingGuide(Widget): def _render(self, _): # Safeguard against fast tapping step = min(self._step, len(self._textures) - 1) - rl.draw_texture(self._textures[step], 0, 0, rl.WHITE) + rl.draw_texture_ex(self._textures[step], rl.Vector2(0, 0), 0.0, 1.0, rl.WHITE) # progress bar if 0 < step < len(STEP_RECTS) - 1: diff --git a/selfdrive/ui/layouts/settings/developer.py b/selfdrive/ui/layouts/settings/developer.py index 56c2951d0d..acabb5e743 100644 --- a/selfdrive/ui/layouts/settings/developer.py +++ b/selfdrive/ui/layouts/settings/developer.py @@ -104,6 +104,7 @@ class DeveloperLayout(Widget): self._scroller.render(rect) def show_event(self): + super().show_event() self._scroller.show_event() self._update_toggles() diff --git a/selfdrive/ui/layouts/settings/device.py b/selfdrive/ui/layouts/settings/device.py index 45589af1f0..126ad22a3a 100644 --- a/selfdrive/ui/layouts/settings/device.py +++ b/selfdrive/ui/layouts/settings/device.py @@ -75,6 +75,7 @@ class DeviceLayout(Widget): self._power_off_btn.action_item.right_button.set_visible(ui_state.is_offroad()) def show_event(self): + super().show_event() self._scroller.show_event() def _render(self, rect): diff --git a/selfdrive/ui/layouts/settings/software.py b/selfdrive/ui/layouts/settings/software.py index 8086b1f635..f42682e2f7 100644 --- a/selfdrive/ui/layouts/settings/software.py +++ b/selfdrive/ui/layouts/settings/software.py @@ -82,6 +82,7 @@ class SoftwareLayout(Widget): ], line_separator=True, spacing=0) def show_event(self): + super().show_event() self._scroller.show_event() def _render(self, rect): diff --git a/selfdrive/ui/layouts/settings/toggles.py b/selfdrive/ui/layouts/settings/toggles.py index 9f704b1fb4..9923f3a356 100644 --- a/selfdrive/ui/layouts/settings/toggles.py +++ b/selfdrive/ui/layouts/settings/toggles.py @@ -152,6 +152,7 @@ class TogglesLayout(Widget): ui_state.personality = personality def show_event(self): + super().show_event() self._scroller.show_event() self._update_toggles() diff --git a/selfdrive/ui/layouts/sidebar.py b/selfdrive/ui/layouts/sidebar.py index bfa60c88ed..1dad597ca3 100644 --- a/selfdrive/ui/layouts/sidebar.py +++ b/selfdrive/ui/layouts/sidebar.py @@ -165,14 +165,14 @@ class Sidebar(Widget, SidebarSP): # Settings button settings_down = mouse_down and rl.check_collision_point_rec(mouse_pos, SETTINGS_BTN) tint = Colors.BUTTON_PRESSED if settings_down else Colors.BUTTON_NORMAL - rl.draw_texture(self._settings_img, int(SETTINGS_BTN.x), int(SETTINGS_BTN.y), tint) + rl.draw_texture_ex(self._settings_img, rl.Vector2(SETTINGS_BTN.x, SETTINGS_BTN.y), 0.0, 1.0, tint) # Home/Flag button flag_pressed = mouse_down and rl.check_collision_point_rec(mouse_pos, HOME_BTN) button_img = self._flag_img if ui_state.started else self._home_img tint = Colors.BUTTON_PRESSED if (ui_state.started and flag_pressed) else Colors.BUTTON_NORMAL - rl.draw_texture(button_img, int(HOME_BTN.x), int(HOME_BTN.y), tint) + rl.draw_texture_ex(button_img, rl.Vector2(HOME_BTN.x, HOME_BTN.y), 0.0, 1.0, tint) # Microphone button if self._recording_audio: @@ -182,8 +182,8 @@ class Sidebar(Widget, SidebarSP): bg_color = rl.Color(Colors.DANGER.r, Colors.DANGER.g, Colors.DANGER.b, int(255 * 0.65)) if mic_pressed else Colors.DANGER rl.draw_rectangle_rounded(self._mic_indicator_rect, 1, 10, bg_color) - rl.draw_texture(self._mic_img, int(self._mic_indicator_rect.x + (self._mic_indicator_rect.width - self._mic_img.width) / 2), - int(self._mic_indicator_rect.y + (self._mic_indicator_rect.height - self._mic_img.height) / 2), Colors.WHITE) + rl.draw_texture_ex(self._mic_img, rl.Vector2(self._mic_indicator_rect.x + (self._mic_indicator_rect.width - self._mic_img.width) / 2, + self._mic_indicator_rect.y + (self._mic_indicator_rect.height - self._mic_img.height) / 2), 0.0, 1.0, Colors.WHITE) def _draw_network_indicator(self, rect: rl.Rectangle): # Signal strength dots diff --git a/selfdrive/ui/mici/layouts/home.py b/selfdrive/ui/mici/layouts/home.py index 1d6d8dad2a..8200089c28 100644 --- a/selfdrive/ui/mici/layouts/home.py +++ b/selfdrive/ui/mici/layouts/home.py @@ -7,7 +7,7 @@ from collections.abc import Callable from openpilot.system.ui.widgets import Widget from openpilot.system.ui.widgets.layouts import HBoxLayout from openpilot.system.ui.widgets.icon_widget import IconWidget -from openpilot.system.ui.widgets.label import MiciLabel, UnifiedLabel +from openpilot.system.ui.widgets.label import UnifiedLabel from openpilot.system.ui.lib.application import gui_app, FontWeight, MousePos from openpilot.selfdrive.ui.ui_state import ui_state from openpilot.system.version import RELEASE_BRANCHES @@ -77,7 +77,7 @@ class NetworkIcon(Widget): # Offset by difference in height between slashless and slash icons to make center align match draw_y -= (self._wifi_slash_txt.height - self._wifi_none_txt.height) / 2 - rl.draw_texture(draw_net_txt, int(draw_x), int(draw_y), rl.Color(255, 255, 255, int(255 * 0.9))) + rl.draw_texture_ex(draw_net_txt, rl.Vector2(draw_x, draw_y), 0.0, 1.0, rl.Color(255, 255, 255, int(255 * 0.9))) class MiciHomeLayout(Widget): @@ -103,14 +103,15 @@ class MiciHomeLayout(Widget): self._mic_icon, ], spacing=18) - self._openpilot_label = MiciLabel("sunnypilot", font_size=90, color=rl.Color(255, 255, 255, int(255 * 0.9)), font_weight=FontWeight.AUDIOWIDE) - self._version_label = MiciLabel("", font_size=36, font_weight=FontWeight.ROMAN) - self._large_version_label = MiciLabel("", font_size=64, color=rl.GRAY, font_weight=FontWeight.ROMAN) - self._date_label = MiciLabel("", font_size=36, color=rl.GRAY, font_weight=FontWeight.ROMAN) + self._openpilot_label = UnifiedLabel("sunnypilot", font_size=96, font_weight=FontWeight.DISPLAY, max_width=480, wrap_text=False) + self._version_label = UnifiedLabel("", font_size=36, font_weight=FontWeight.ROMAN, max_width=480, wrap_text=False) + self._large_version_label = UnifiedLabel("", font_size=64, text_color=rl.GRAY, font_weight=FontWeight.ROMAN, max_width=480, wrap_text=False) + self._date_label = UnifiedLabel("", font_size=36, text_color=rl.GRAY, font_weight=FontWeight.ROMAN, max_width=480, wrap_text=False) self._branch_label = UnifiedLabel("", font_size=36, text_color=rl.GRAY, font_weight=FontWeight.ROMAN, scroll=True) - self._version_commit_label = MiciLabel("", font_size=36, color=rl.GRAY, font_weight=FontWeight.ROMAN) + self._version_commit_label = UnifiedLabel("", font_size=36, text_color=rl.GRAY, font_weight=FontWeight.ROMAN, max_width=480, wrap_text=False) def show_event(self): + super().show_event() self._version_text = self._get_version_text() self._update_params() @@ -182,12 +183,12 @@ class MiciHomeLayout(Widget): self._version_label.render() self._date_label.set_text(" " + self._version_text[3]) - self._date_label.set_position(version_pos.x + self._version_label.rect.width + 10, version_pos.y) + self._date_label.set_position(version_pos.x + self._version_label.text_width + 10, version_pos.y) self._date_label.render() - self._branch_label.set_max_width(gui_app.width - self._version_label.rect.width - self._date_label.rect.width - 32) + self._branch_label.set_max_width(gui_app.width - self._version_label.text_width - self._date_label.text_width - 32) self._branch_label.set_text(" " + ("release" if release_branch else self._version_text[1])) - self._branch_label.set_position(version_pos.x + self._version_label.rect.width + self._date_label.rect.width + 20, version_pos.y) + self._branch_label.set_position(version_pos.x + self._version_label.text_width + self._date_label.text_width + 20, version_pos.y) self._branch_label.render() if not release_branch: diff --git a/selfdrive/ui/mici/layouts/offroad_alerts.py b/selfdrive/ui/mici/layouts/offroad_alerts.py index 3aec5bbfed..57ddfdbc48 100644 --- a/selfdrive/ui/mici/layouts/offroad_alerts.py +++ b/selfdrive/ui/mici/layouts/offroad_alerts.py @@ -144,7 +144,7 @@ class AlertItem(Widget): bg_texture = self._bg_small_pressed if self.is_pressed else self._bg_small # Draw background - rl.draw_texture(bg_texture, int(self._rect.x), int(self._rect.y), rl.WHITE) + rl.draw_texture_ex(bg_texture, rl.Vector2(self._rect.x, self._rect.y), 0.0, 1.0, rl.WHITE) # Calculate text area (left side, avoiding icon on right) title_width = self.ALERT_WIDTH - (self.ALERT_PADDING * 2) - self.ICON_SIZE - self.ICON_MARGIN @@ -183,7 +183,7 @@ class AlertItem(Widget): icon_texture = self._icon_orange icon_x = self._rect.x + self.ALERT_WIDTH - self.ALERT_PADDING - self.ICON_SIZE icon_y = self._rect.y + self.ALERT_PADDING - rl.draw_texture(icon_texture, int(icon_x), int(icon_y), rl.WHITE) + rl.draw_texture_ex(icon_texture, rl.Vector2(icon_x, icon_y), 0.0, 1.0, rl.WHITE) class MiciOffroadAlerts(Scroller): diff --git a/selfdrive/ui/mici/layouts/onboarding.py b/selfdrive/ui/mici/layouts/onboarding.py index 043755e7a6..d6d3f70330 100644 --- a/selfdrive/ui/mici/layouts/onboarding.py +++ b/selfdrive/ui/mici/layouts/onboarding.py @@ -15,8 +15,7 @@ from openpilot.system.ui.lib.multilang import tr from openpilot.system.version import terms_version, training_version, terms_version_sp from openpilot.system.version import sunnylink_consent_version, sunnylink_consent_declined from openpilot.selfdrive.ui.ui_state import ui_state, device -from openpilot.selfdrive.ui.mici.widgets.button import BigCircleButton -from openpilot.selfdrive.ui.mici.widgets.dialog import BigConfirmationDialogV2 +from openpilot.selfdrive.ui.mici.widgets.dialog import BigConfirmationCircleButton from openpilot.selfdrive.ui.mici.onroad.driver_state import DriverStateRenderer from openpilot.selfdrive.ui.mici.onroad.driver_camera_dialog import BaseDriverCameraDialog from openpilot.selfdrive.ui.sunnypilot.mici.layouts.onboarding import SunnylinkConsentPage @@ -154,8 +153,10 @@ class TrainingGuideDMTutorial(NavWidget): def _render(self, _): self._dialog.render(self._rect) - rl.draw_rectangle_gradient_v(int(self._rect.x), int(self._rect.y + self._rect.height - 80), - int(self._rect.width), 80, rl.BLANK, rl.BLACK) + gradient_y = int(self._rect.y + self._rect.height - 80) + gradient_h = int(self._rect.y) + int(self._rect.height) - gradient_y + rl.draw_rectangle_gradient_v(int(self._rect.x), gradient_y, + int(self._rect.width), gradient_h, rl.BLANK, rl.BLACK) # draw white ring around dm icon to indicate progress ring_thickness = 8 @@ -217,26 +218,19 @@ class TrainingGuideRecordFront(NavScroller): def __init__(self, continue_callback: Callable[[], None]): super().__init__() - def show_accept_dialog(): - def on_accept(): - ui_state.params.put_bool_nonblocking("RecordFront", True) - continue_callback() + def on_accept(): + ui_state.params.put_bool_nonblocking("RecordFront", True) + continue_callback() - gui_app.push_widget(BigConfirmationDialogV2("allow data uploading", "icons_mici/setup/driver_monitoring/dm_check.png", exit_on_confirm=False, - confirm_callback=on_accept)) + def on_decline(): + ui_state.params.put_bool_nonblocking("RecordFront", False) + continue_callback() - def show_decline_dialog(): - def on_decline(): - ui_state.params.put_bool_nonblocking("RecordFront", False) - continue_callback() + self._accept_button = BigConfirmationCircleButton("allow data uploading", gui_app.texture("icons_mici/setup/driver_monitoring/dm_check.png", 64, 64), + on_accept, exit_on_confirm=False) - gui_app.push_widget(BigConfirmationDialogV2("no, don't upload", "icons_mici/setup/cancel.png", exit_on_confirm=False, confirm_callback=on_decline)) - - self._accept_button = BigCircleButton("icons_mici/setup/driver_monitoring/dm_check.png") - self._accept_button.set_click_callback(show_accept_dialog) - - self._decline_button = BigCircleButton("icons_mici/setup/cancel.png") - self._decline_button.set_click_callback(show_decline_dialog) + self._decline_button = BigConfirmationCircleButton("no, don't upload", gui_app.texture("icons_mici/setup/cancel.png", 64, 64), on_decline, + exit_on_confirm=False) self._scroller.add_widgets([ GreyBigButton("driver camera data", "do you want to share video data for training?", @@ -276,12 +270,9 @@ class TrainingGuide(NavWidget): TrainingGuideRecordFront(continue_callback=completed_callback), ] + self._child(self._steps[0]) self._steps[0].set_enabled(lambda: self.enabled and not self.is_dismissing) # for nav stack - def show_event(self): - super().show_event() - self._steps[0].show_event() - def _render(self, _): self._steps[0].render(self._rect) @@ -314,7 +305,7 @@ class QRCodeWidget(Widget): def _render(self, _): if self._qr_texture: scale = self._size / self._qr_texture.height - rl.draw_texture_ex(self._qr_texture, rl.Vector2(self._rect.x, self._rect.y), 0.0, scale, rl.WHITE) + rl.draw_texture_ex(self._qr_texture, rl.Vector2(round(self._rect.x), round(self._rect.y)), 0.0, scale, rl.WHITE) def __del__(self): if self._qr_texture and self._qr_texture.id != 0: @@ -325,27 +316,20 @@ class TermsPage(Scroller): def __init__(self, on_accept, on_decline): super().__init__() - def show_accept_dialog(): - gui_app.push_widget(BigConfirmationDialogV2("accept\nterms", "icons_mici/setup/driver_monitoring/dm_check.png", - confirm_callback=on_accept)) + self._accept_button = BigConfirmationCircleButton("accept\nterms", gui_app.texture("icons_mici/setup/driver_monitoring/dm_check.png", 64, 64), on_accept) + self._decline_button = BigConfirmationCircleButton("decline &\nuninstall", gui_app.texture("icons_mici/setup/cancel.png", 64, 64), on_decline, + red=True, exit_on_confirm=False) - def show_decline_dialog(): - gui_app.push_widget(BigConfirmationDialogV2("decline &\nuninstall", "icons_mici/setup/cancel.png", - red=True, exit_on_confirm=False, confirm_callback=on_decline)) - - self._accept_button = BigCircleButton("icons_mici/setup/driver_monitoring/dm_check.png") - self._accept_button.set_click_callback(show_accept_dialog) - - self._decline_button = BigCircleButton("icons_mici/setup/cancel.png", red=True) - self._decline_button.set_click_callback(show_decline_dialog) + self._terms_header = GreyBigButton("terms of\nservice", "scroll to continue", + gui_app.texture("icons_mici/setup/green_info.png", 64, 64)) + self._must_accept_card = GreyBigButton("", "You must accept the Terms of Service to use sunnypilot.") self._scroller.add_widgets([ - GreyBigButton("terms and\nconditions", "scroll to continue", - gui_app.texture("icons_mici/setup/green_info.png", 64, 64)), + self._terms_header, GreyBigButton("swipe for QR code", "or go to https://sunnypilot.ai/terms", gui_app.texture("icons_mici/setup/small_slider/slider_arrow.png", 64, 56, flip_x=True)), QRCodeWidget("https://sunnypilot.ai/terms"), - GreyBigButton("", "You must accept the Terms & Conditions to use sunnypilot."), + self._must_accept_card, self._accept_button, self._decline_button, ]) diff --git a/selfdrive/ui/mici/layouts/settings/developer.py b/selfdrive/ui/mici/layouts/settings/developer.py index 4e7796814e..386b468928 100644 --- a/selfdrive/ui/mici/layouts/settings/developer.py +++ b/selfdrive/ui/mici/layouts/settings/developer.py @@ -5,32 +5,37 @@ from openpilot.selfdrive.ui.mici.widgets.dialog import BigDialog, BigInputDialog from openpilot.system.ui.lib.application import gui_app from openpilot.selfdrive.ui.layouts.settings.common import restart_needed_callback from openpilot.selfdrive.ui.ui_state import ui_state -from openpilot.selfdrive.ui.widgets.ssh_key import SshKeyAction +from openpilot.selfdrive.ui.widgets.ssh_key import SshKeyFetcher class DeveloperLayoutMici(NavScroller): def __init__(self): super().__init__() + self._ssh_fetcher = SshKeyFetcher(ui_state.params) def github_username_callback(username: str): if username: - ssh_keys = SshKeyAction() - ssh_keys._fetch_ssh_key(username) - if not ssh_keys._error_message: - self._ssh_keys_btn.set_value(username) - else: - dlg = BigDialog("", ssh_keys._error_message) - gui_app.push_widget(dlg) + self._ssh_keys_btn.set_value("Loading...") + self._ssh_keys_btn.set_enabled(False) + + def on_response(error): + self._ssh_keys_btn.set_enabled(True) + if error is None: + self._ssh_keys_btn.set_value(username) + else: + self._ssh_keys_btn.set_value("Not set") + gui_app.push_widget(BigDialog("", error)) + + self._ssh_fetcher.fetch(username, on_response) else: - ui_state.params.remove("GithubUsername") - ui_state.params.remove("GithubSshKeys") + self._ssh_fetcher.clear() self._ssh_keys_btn.set_value("Not set") def ssh_keys_callback(): github_username = ui_state.params.get("GithubUsername") or "" dlg = BigInputDialog("enter GitHub username...", github_username, minimum_length=0, confirm_callback=github_username_callback) if not system_time_valid(): - dlg = BigDialog("Please connect to Wi-Fi to fetch your key", "") + dlg = BigDialog("", "Please connect to Wi-Fi to fetch your key.") gui_app.push_widget(dlg) return gui_app.push_widget(dlg) @@ -42,8 +47,8 @@ class DeveloperLayoutMici(NavScroller): # adb, ssh, ssh keys, debug mode, joystick debug mode, longitudinal maneuver mode, ip address # ******** Main Scroller ******** - self._adb_toggle = BigCircleParamControl("icons_mici/adb_short.png", "AdbEnabled", icon_size=(82, 82), icon_offset=(0, 12)) - self._ssh_toggle = BigCircleParamControl("icons_mici/ssh_short.png", "SshEnabled", icon_size=(82, 82), icon_offset=(0, 12)) + self._adb_toggle = BigCircleParamControl(gui_app.texture("icons_mici/adb_short.png", 82, 82), "AdbEnabled", icon_offset=(0, 12)) + self._ssh_toggle = BigCircleParamControl(gui_app.texture("icons_mici/ssh_short.png", 82, 82), "SshEnabled", icon_offset=(0, 12)) self._joystick_toggle = BigToggle("joystick debug mode", initial_state=ui_state.params.get_bool("JoystickDebugMode"), toggle_callback=self._on_joystick_debug_mode) @@ -99,6 +104,10 @@ class DeveloperLayoutMici(NavScroller): ui_state.add_offroad_transition_callback(self._update_toggles) + def _update_state(self): + super()._update_state() + self._ssh_fetcher.update() + def show_event(self): super().show_event() self._update_toggles() diff --git a/selfdrive/ui/mici/layouts/settings/device.py b/selfdrive/ui/mici/layouts/settings/device.py index b818872913..e0d89a5419 100644 --- a/selfdrive/ui/mici/layouts/settings/device.py +++ b/selfdrive/ui/mici/layouts/settings/device.py @@ -9,16 +9,15 @@ from openpilot.common.params import Params from openpilot.common.time_helpers import system_time_valid from openpilot.system.ui.widgets.scroller import NavRawScrollPanel, NavScroller from openpilot.selfdrive.ui.mici.widgets.button import BigButton, BigCircleButton -from openpilot.selfdrive.ui.mici.widgets.dialog import BigDialog, BigConfirmationDialogV2 +from openpilot.selfdrive.ui.mici.widgets.dialog import BigDialog, BigConfirmationDialog from openpilot.selfdrive.ui.mici.widgets.pairing_dialog import PairingDialog from openpilot.selfdrive.ui.mici.onroad.driver_camera_dialog import DriverCameraDialog from openpilot.selfdrive.ui.mici.layouts.onboarding import TrainingGuide, TermsPage -from openpilot.system.ui.mici_setup import BigPillButton from openpilot.system.ui.lib.application import gui_app, FontWeight, MousePos from openpilot.system.ui.lib.multilang import tr from openpilot.system.ui.widgets import Widget from openpilot.selfdrive.ui.ui_state import device, ui_state -from openpilot.system.ui.widgets.label import MiciLabel +from openpilot.system.ui.widgets.label import UnifiedLabel from openpilot.system.ui.widgets.html_render import HtmlModal, HtmlRenderer from openpilot.system.athena.registration import UNREGISTERED_DONGLE_ID @@ -27,13 +26,11 @@ class ReviewTermsPage(TermsPage, NavScroller): """TermsPage with NavWidget swipe-to-dismiss for reviewing in device settings.""" def __init__(self): super().__init__(on_accept=self.dismiss, on_decline=self.dismiss) + self._terms_header.set_visible(False) + self._must_accept_card.set_visible(False) self._accept_button.set_visible(False) self._decline_button.set_visible(False) - close_button = BigPillButton("close") - close_button.set_click_callback(self.dismiss) - self._scroller.add_widget(close_button) - class ReviewTrainingGuide(TrainingGuide): def show_event(self): @@ -67,34 +64,31 @@ class MiciFccModal(NavRawScrollPanel): rl.draw_texture_ex(self._fcc_logo, fcc_pos, 0.0, 1.0, rl.WHITE) -def _engaged_confirmation_callback(callback: Callable, action_text: str): +def _engaged_confirmation_click(callback: Callable, action_text: str, icon: rl.Texture, exit_on_confirm: bool = True, red: bool = False): if not ui_state.engaged: def confirm_callback(): # Check engaged again in case it changed while the dialog was open + # TODO: if true, we stay on the dialog if not exit_on_confirm until normal onroad timeout if not ui_state.engaged: callback() - red = False - if action_text == "power off": - icon = "icons_mici/settings/device/power.png" - red = True - elif action_text == "reboot": - icon = "icons_mici/settings/device/reboot.png" - elif action_text == "reset": - icon = "icons_mici/settings/device/lkas.png" - elif action_text == "uninstall": - icon = "icons_mici/settings/device/uninstall.png" - else: - # TODO: check - icon = "icons_mici/settings/comma_icon.png" - - dlg: BigConfirmationDialogV2 | BigDialog = BigConfirmationDialogV2(f"slide to\n{action_text.lower()}", icon, red=red, - exit_on_confirm=action_text == "reset", - confirm_callback=confirm_callback) - gui_app.push_widget(dlg) + gui_app.push_widget(BigConfirmationDialog(f"slide to\n{action_text.lower()}", icon, confirm_callback, exit_on_confirm=exit_on_confirm, red=red)) else: - dlg = BigDialog(f"Disengage to {action_text}", "") - gui_app.push_widget(dlg) + gui_app.push_widget(BigDialog("", f"Disengage to {action_text}")) + + +class EngagedConfirmationCircleButton(BigCircleButton): + def __init__(self, title: str, icon: rl.Texture, callback: Callable[[], None], exit_on_confirm: bool = True, + red: bool = False, icon_offset: tuple[int, int] = (0, 0)): + super().__init__(icon, red, icon_offset) + self.set_click_callback(lambda: _engaged_confirmation_click(callback, title, icon, exit_on_confirm=exit_on_confirm, red=red)) + + +class EngagedConfirmationButton(BigButton): + def __init__(self, text: str, action_text: str, icon: rl.Texture, callback: Callable[[], None], + exit_on_confirm: bool = True, red: bool = False): + super().__init__(text, "", icon) + self.set_click_callback(lambda: _engaged_confirmation_click(callback, action_text, icon, exit_on_confirm=exit_on_confirm, red=red)) class DeviceInfoLayoutMici(Widget): @@ -104,14 +98,15 @@ class DeviceInfoLayoutMici(Widget): self.set_rect(rl.Rectangle(0, 0, 360, 180)) params = Params() - header_color = rl.Color(255, 255, 255, int(255 * 0.9)) subheader_color = rl.Color(255, 255, 255, int(255 * 0.9 * 0.65)) max_width = int(self._rect.width - 20) - self._dongle_id_label = MiciLabel("device ID", 48, width=max_width, color=header_color, font_weight=FontWeight.DISPLAY) - self._dongle_id_text_label = MiciLabel(params.get("DongleId") or 'N/A', 32, width=max_width, color=subheader_color, font_weight=FontWeight.ROMAN) + self._dongle_id_label = UnifiedLabel("device ID", 48, max_width=max_width, font_weight=FontWeight.DISPLAY, wrap_text=False) + self._dongle_id_text_label = UnifiedLabel(params.get("DongleId") or 'N/A', 32, max_width=max_width, text_color=subheader_color, + font_weight=FontWeight.ROMAN, wrap_text=False) - self._serial_number_label = MiciLabel("serial", 48, color=header_color, font_weight=FontWeight.DISPLAY) - self._serial_number_text_label = MiciLabel(params.get("HardwareSerial") or 'N/A', 32, width=max_width, color=subheader_color, font_weight=FontWeight.ROMAN) + self._serial_number_label = UnifiedLabel("serial", 48, max_width=max_width, font_weight=FontWeight.DISPLAY, wrap_text=False) + self._serial_number_text_label = UnifiedLabel(params.get("HardwareSerial") or 'N/A', 32, max_width=max_width, text_color=subheader_color, + font_weight=FontWeight.ROMAN, wrap_text=False) def _render(self, _): self._dongle_id_label.set_position(self._rect.x + 20, self._rect.y - 10) @@ -135,7 +130,7 @@ class UpdaterState(IntEnum): class PairBigButton(BigButton): def __init__(self): - super().__init__("pair", "connect.comma.ai", "icons_mici/settings/comma_icon.png", icon_size=(33, 60)) + super().__init__("pair", "connect.comma.ai", gui_app.texture("icons_mici/settings/comma_icon.png", 33, 60)) def _get_label_font_size(self): return 64 @@ -161,9 +156,9 @@ class PairBigButton(BigButton): return dlg: BigDialog | PairingDialog if not system_time_valid(): - dlg = BigDialog(tr("Please connect to Wi-Fi to complete initial pairing"), "") + dlg = BigDialog("", tr("Please connect to Wi-Fi to complete initial pairing.")) elif UNREGISTERED_DONGLE_ID == (ui_state.params.get("DongleId") or UNREGISTERED_DONGLE_ID): - dlg = BigDialog(tr("Device must be registered with the comma.ai backend to pair"), "") + dlg = BigDialog("", tr("Device must be registered with the comma.ai backend to pair.")) else: dlg = PairingDialog() gui_app.push_widget(dlg) @@ -193,7 +188,7 @@ class UpdateOpenpilotBigButton(BigButton): super()._handle_mouse_release(mouse_pos) if not system_time_valid(): - dlg = BigDialog(tr("Please connect to Wi-Fi to update"), "") + dlg = BigDialog("", tr("Please connect to Wi-Fi to update.")) gui_app.push_widget(dlg) return @@ -314,33 +309,33 @@ class DeviceLayoutMici(NavScroller): def uninstall_openpilot_callback(): ui_state.params.put_bool("DoUninstall", True) - reset_calibration_btn = BigButton("reset calibration", "", "icons_mici/settings/device/lkas.png", icon_size=(114, 60)) - reset_calibration_btn.set_click_callback(lambda: _engaged_confirmation_callback(reset_calibration_callback, "reset")) + reset_calibration_btn = EngagedConfirmationButton("reset calibration", "reset", gui_app.texture("icons_mici/settings/device/lkas.png", 122, 64), + reset_calibration_callback) - uninstall_openpilot_btn = BigButton("uninstall sunnypilot", "", "icons_mici/settings/device/uninstall.png") - uninstall_openpilot_btn.set_click_callback(lambda: _engaged_confirmation_callback(uninstall_openpilot_callback, "uninstall")) + uninstall_openpilot_btn = EngagedConfirmationButton("uninstall sunnypilot", "uninstall", + gui_app.texture("icons_mici/settings/device/uninstall.png", 64, 64), + uninstall_openpilot_callback, exit_on_confirm=False) - reboot_btn = BigCircleButton("icons_mici/settings/device/reboot.png", red=False, icon_size=(64, 70)) - reboot_btn.set_click_callback(lambda: _engaged_confirmation_callback(reboot_callback, "reboot")) + reboot_btn = EngagedConfirmationCircleButton("reboot", gui_app.texture("icons_mici/settings/device/reboot.png", 64, 70), + reboot_callback, exit_on_confirm=False) - self._power_off_btn = BigCircleButton("icons_mici/settings/device/power.png", red=True, icon_size=(64, 66)) - self._power_off_btn.set_click_callback(lambda: _engaged_confirmation_callback(power_off_callback, "power off")) + self._power_off_btn = EngagedConfirmationCircleButton("power off", gui_app.texture("icons_mici/settings/device/power.png", 64, 66), + power_off_callback, exit_on_confirm=False, red=True) self._power_off_btn.set_visible(lambda: not ui_state.ignition) - regulatory_btn = BigButton("regulatory info", "", "icons_mici/settings/device/info.png") + regulatory_btn = BigButton("regulatory info", "", gui_app.texture("icons_mici/settings/device/info.png", 64, 64)) regulatory_btn.set_click_callback(self._on_regulatory) - driver_cam_btn = BigButton("driver\ncamera preview", "", "icons_mici/settings/device/cameras.png") + driver_cam_btn = BigButton("driver\ncamera preview", "", gui_app.texture("icons_mici/settings/device/cameras.png", 64, 64)) driver_cam_btn.set_click_callback(lambda: gui_app.push_widget(DriverCameraDialog())) driver_cam_btn.set_enabled(lambda: ui_state.is_offroad()) - review_training_guide_btn = BigButton("review\ntraining guide", "", "icons_mici/settings/device/info.png") + review_training_guide_btn = BigButton("review\ntraining guide", "", gui_app.texture("icons_mici/settings/device/info.png", 64, 64)) review_training_guide_btn.set_click_callback(lambda: gui_app.push_widget(ReviewTrainingGuide(completed_callback=lambda: gui_app.pop_widgets_to(self)))) review_training_guide_btn.set_enabled(lambda: ui_state.is_offroad()) - terms_btn = BigButton("terms &\nconditions", "", "icons_mici/settings/device/info.png") + terms_btn = BigButton("terms &\nconditions", "", gui_app.texture("icons_mici/settings/device/info.png", 64, 64)) terms_btn.set_click_callback(lambda: gui_app.push_widget(ReviewTermsPage())) - terms_btn.set_enabled(lambda: ui_state.is_offroad()) self._scroller.add_widgets([ DeviceInfoLayoutMici(), diff --git a/selfdrive/ui/mici/layouts/settings/firehose.py b/selfdrive/ui/mici/layouts/settings/firehose.py index 741ea9655a..5bf7426c77 100644 --- a/selfdrive/ui/mici/layouts/settings/firehose.py +++ b/selfdrive/ui/mici/layouts/settings/firehose.py @@ -81,12 +81,12 @@ class FirehoseLayoutBase(Widget): def _render(self, rect: rl.Rectangle): # compute total content height for scrolling content_height = self._measure_content_height(rect) - scroll_offset = round(self._scroll_panel.update(rect, content_height)) + scroll_offset = self._scroll_panel.update(rect, content_height) # start drawing with offset - x = int(rect.x + 40) - y = int(rect.y + 40 + scroll_offset) - w = int(rect.width - 80) + x = rect.x + 40 + y = rect.y + 40 + scroll_offset + w = rect.width - 80 # Title title_text = tr(TITLE) @@ -100,7 +100,7 @@ class FirehoseLayoutBase(Widget): y += 20 # Separator - rl.draw_rectangle(x, y, w, 2, self.GRAY) + rl.draw_rectangle_rec(rl.Rectangle(x, y, w, 2), self.GRAY) y += 20 # Status @@ -116,7 +116,7 @@ class FirehoseLayoutBase(Widget): y += 20 # Separator - rl.draw_rectangle(x, y, w, 2, self.GRAY) + rl.draw_rectangle_rec(rl.Rectangle(x, y, w, 2), self.GRAY) y += 20 # Instructions intro diff --git a/selfdrive/ui/mici/layouts/settings/network/wifi_ui.py b/selfdrive/ui/mici/layouts/settings/network/wifi_ui.py index 22d3d1d0da..006027e258 100644 --- a/selfdrive/ui/mici/layouts/settings/network/wifi_ui.py +++ b/selfdrive/ui/mici/layouts/settings/network/wifi_ui.py @@ -3,9 +3,8 @@ import numpy as np import pyray as rl from collections.abc import Callable -from openpilot.common.filter_simple import FirstOrderFilter from openpilot.common.swaglog import cloudlog -from openpilot.selfdrive.ui.mici.widgets.dialog import BigInputDialog, BigConfirmationDialogV2 +from openpilot.selfdrive.ui.mici.widgets.dialog import BigInputDialog, BigConfirmationDialog from openpilot.selfdrive.ui.mici.widgets.button import BigButton, LABEL_COLOR from openpilot.system.ui.lib.application import gui_app, MousePos, FontWeight from openpilot.system.ui.widgets import Widget @@ -14,39 +13,26 @@ from openpilot.system.ui.lib.wifi_manager import WifiManager, Network, SecurityT class LoadingAnimation(Widget): - HIDE_TIME = 4 + RADIUS = 8 + SPACING = 24 # center-to-center: diameter (16) + gap (8) + Y_MAG = 11.2 def __init__(self): super().__init__() - self._opacity_filter = FirstOrderFilter(0.0, 0.1, 1 / gui_app.target_fps) - self._opacity_target = 1.0 - self._hide_time = 0.0 - - def show_event(self): - self._opacity_target = 1.0 - self._hide_time = rl.get_time() + w = self.SPACING * 2 + self.RADIUS * 2 + h = self.RADIUS * 2 + int(self.Y_MAG) + self.set_rect(rl.Rectangle(0, 0, w, h)) def _render(self, _): - if rl.get_time() - self._hide_time > self.HIDE_TIME: - self._opacity_target = 0.0 - - self._opacity_filter.update(self._opacity_target) - - if self._opacity_filter.x < 0.01: - return - - cx = int(self._rect.x + self._rect.width / 2) - cy = int(self._rect.y + self._rect.height / 2) - - y_mag = 7 - anim_scale = 4 - spacing = 14 + # Balls rest at bottom center; bounce upward + base_x = int(self._rect.x + self._rect.width / 2) + base_y = int(self._rect.y + self._rect.height - self.RADIUS) for i in range(3): - x = cx - spacing + i * spacing - y = int(cy + min(math.sin((rl.get_time() - i * 0.2) * anim_scale) * y_mag, 0)) - alpha = int(np.interp(cy - y, [0, y_mag], [255 * 0.45, 255 * 0.9]) * self._opacity_filter.x) - rl.draw_circle(x, y, 5, rl.Color(255, 255, 255, alpha)) + x = base_x + (i - 1) * self.SPACING + y = int(base_y + min(math.sin((rl.get_time() - i * 0.2) * 4) * self.Y_MAG, 0)) + alpha = int(np.interp(base_y - y, [0, self.Y_MAG], [255 * 0.45, 255 * 0.9])) + rl.draw_circle(x, y, self.RADIUS, rl.Color(255, 255, 255, alpha)) class WifiIcon(Widget): @@ -124,6 +110,10 @@ class WifiButton(BigButton): if self._is_connected or self._is_connecting: self._wrong_password = False + @property + def network_forgetting(self) -> bool: + return self._network_forgetting + def _forget_network(self): if self._network_forgetting: return @@ -175,7 +165,7 @@ class WifiButton(BigButton): if self._is_connected and not self._network_forgetting: check_y = int(label_y - sub_label_height + (sub_label_height - self._check_txt.height) / 2) - rl.draw_texture(self._check_txt, int(sub_label_x), check_y, rl.Color(255, 255, 255, int(255 * 0.9 * 0.65))) + rl.draw_texture_ex(self._check_txt, rl.Vector2(sub_label_x, check_y), 0.0, 1.0, rl.Color(255, 255, 255, int(255 * 0.9 * 0.65))) sub_label_x += self._check_txt.width + 14 sub_label_rect = rl.Rectangle(sub_label_x, label_y - sub_label_height, sub_label_w, sub_label_height) @@ -256,8 +246,7 @@ class ForgetButton(Widget): def _handle_mouse_release(self, mouse_pos: MousePos): super()._handle_mouse_release(mouse_pos) - dlg = BigConfirmationDialogV2("slide to forget", "icons_mici/settings/network/new/trash.png", red=True, - confirm_callback=self._forget_network) + dlg = BigConfirmationDialog("slide to forget", gui_app.texture("icons_mici/settings/network/new/trash.png", 54, 64), self._forget_network, red=True) gui_app.push_widget(dlg) def _render(self, _): @@ -270,11 +259,26 @@ class ForgetButton(Widget): rl.draw_texture_ex(self._trash_txt, (trash_x, trash_y), 0, 1.0, rl.WHITE) +class ScanningButton(BigButton): + def __init__(self): + super().__init__("", "searching for networks") + self.set_enabled(False) + self._loading_animation = LoadingAnimation() + + def _draw_content(self, btn_y: float): + super()._draw_content(btn_y) + anim = self._loading_animation + x = self._rect.x + self._rect.width - anim.rect.width - 40 + y = btn_y + self._rect.height - anim.rect.height - 30 + anim.set_position(x, y) + anim.render() + + class WifiUIMici(NavScroller): def __init__(self, wifi_manager: WifiManager): super().__init__() - self._loading_animation = LoadingAnimation() + self._scanning_btn = ScanningButton() self._wifi_manager = wifi_manager self._networks: dict[str, Network] = {} @@ -285,20 +289,23 @@ class WifiUIMici(NavScroller): networks_updated=self._on_network_updated, ) + @property + def any_network_forgetting(self) -> bool: + # TODO: deactivate before forget and add DISCONNECTING state + return any(btn.network_forgetting for btn in self._scroller.items if isinstance(btn, WifiButton)) + def show_event(self): - # Clear scroller items and update from latest scan results + # Re-sort scroller items and update from latest scan results super().show_event() - self._loading_animation.show_event() self._wifi_manager.set_active(True) - self._scroller.items.clear() - # trigger button update on latest sorted networks - self._on_network_updated(self._wifi_manager.networks) + self._networks = {n.ssid: n for n in self._wifi_manager.networks} + self._update_buttons(re_sort=True) def _on_network_updated(self, networks: list[Network]): self._networks = {network.ssid: network for network in networks} self._update_buttons() - def _update_buttons(self): + def _update_buttons(self, re_sort: bool = False): # Update existing buttons, add new ones to the end existing = {btn.network.ssid: btn for btn in self._scroller.items if isinstance(btn, WifiButton)} @@ -310,10 +317,22 @@ class WifiUIMici(NavScroller): btn.set_click_callback(lambda ssid=network.ssid: self._connect_to_network(ssid)) self._scroller.add_widget(btn) - # Mark networks no longer in scan results (display handled by _update_state) - for btn in self._scroller.items: - if isinstance(btn, WifiButton) and btn.network.ssid not in self._networks: - btn.set_network_missing(True) + if re_sort: + # Remove stale buttons and sort to match scan order, preserving eager state + btn_map = {btn.network.ssid: btn for btn in self._scroller.items if isinstance(btn, WifiButton)} + self._scroller.items[:] = [btn_map[ssid] for ssid in self._networks if ssid in btn_map] + else: + # Mark networks no longer in scan results (display handled by _update_state) + for btn in self._scroller.items: + if isinstance(btn, WifiButton) and btn.network.ssid not in self._networks: + btn.set_network_missing(True) + + # Keep scanning button at the end + items = self._scroller.items + if self._scanning_btn in items: + items.append(items.pop(items.index(self._scanning_btn))) + else: + self._scroller.add_widget(self._scanning_btn) def _connect_with_password(self, ssid: str, password: str): self._wifi_manager.connect_to_network(ssid, password) @@ -370,17 +389,3 @@ class WifiUIMici(NavScroller): super()._update_state() self._move_network_to_front(self._wifi_manager.wifi_state.ssid) - - # Show loading animation near end - max_scroll = max(self._scroller.content_size - self._scroller.rect.width, 1) - progress = -self._scroller.scroll_panel.get_offset() / max_scroll - if progress > 0.8 or len(self._scroller.items) <= 1: - self._loading_animation.show_event() - - def _render(self, _): - super()._render(self._rect) - - anim_w = 90 - anim_x = self._rect.x + self._rect.width - anim_w - anim_y = self._rect.y + self._rect.height - 25 + 2 - self._loading_animation.render(rl.Rectangle(anim_x, anim_y, anim_w, 20)) diff --git a/selfdrive/ui/mici/layouts/settings/settings.py b/selfdrive/ui/mici/layouts/settings/settings.py index 8e037ccf88..4ccc5ba139 100644 --- a/selfdrive/ui/mici/layouts/settings/settings.py +++ b/selfdrive/ui/mici/layouts/settings/settings.py @@ -20,23 +20,23 @@ class SettingsLayout(NavScroller): self._params = Params() toggles_panel = TogglesLayoutMici() - toggles_btn = SettingsBigButton("toggles", "", "icons_mici/settings.png") + toggles_btn = SettingsBigButton("toggles", "", gui_app.texture("icons_mici/settings.png", 64, 64)) toggles_btn.set_click_callback(lambda: gui_app.push_widget(toggles_panel)) network_panel = NetworkLayoutMici() - network_btn = SettingsBigButton("network", "", "icons_mici/settings/network/wifi_strength_full.png", icon_size=(76, 56)) + network_btn = SettingsBigButton("network", "", gui_app.texture("icons_mici/settings/network/wifi_strength_full.png", 76, 56)) network_btn.set_click_callback(lambda: gui_app.push_widget(network_panel)) device_panel = DeviceLayoutMici() - device_btn = SettingsBigButton("device", "", "icons_mici/settings/device_icon.png", icon_size=(74, 60)) + device_btn = SettingsBigButton("device", "", gui_app.texture("icons_mici/settings/device_icon.png", 72, 58)) device_btn.set_click_callback(lambda: gui_app.push_widget(device_panel)) developer_panel = DeveloperLayoutMici() - developer_btn = SettingsBigButton("developer", "", "icons_mici/settings/developer_icon.png", icon_size=(64, 60)) + developer_btn = SettingsBigButton("developer", "", gui_app.texture("icons_mici/settings/developer_icon.png", 64, 60)) developer_btn.set_click_callback(lambda: gui_app.push_widget(developer_panel)) firehose_panel = FirehoseLayout() - firehose_btn = SettingsBigButton("firehose", "", "icons_mici/settings/firehose.png", icon_size=(52, 62)) + firehose_btn = SettingsBigButton("firehose", "", gui_app.texture("icons_mici/settings/firehose.png", 52, 62)) firehose_btn.set_click_callback(lambda: gui_app.push_widget(firehose_panel)) self._scroller.add_widgets([ diff --git a/selfdrive/ui/mici/onroad/alert_renderer.py b/selfdrive/ui/mici/onroad/alert_renderer.py index a9d4f3a48b..5b550030de 100644 --- a/selfdrive/ui/mici/onroad/alert_renderer.py +++ b/selfdrive/ui/mici/onroad/alert_renderer.py @@ -272,8 +272,8 @@ class AlertRenderer(Widget, SpeedLimitAlertRenderer): else: icon_alpha = int(min(self._turn_signal_alpha_filter.x, 255)) - rl.draw_texture(alert_layout.icon.texture, pos_x, int(self._rect.y + alert_layout.icon.margin_y), - rl.Color(255, 255, 255, int(icon_alpha * self._alpha_filter.x))) + rl.draw_texture_ex(alert_layout.icon.texture, rl.Vector2(pos_x, self._rect.y + alert_layout.icon.margin_y), 0.0, 1.0, + rl.Color(255, 255, 255, int(icon_alpha * self._alpha_filter.x))) def _draw_background(self, alert: Alert) -> None: # draw top gradient for alert text at top diff --git a/selfdrive/ui/mici/onroad/augmented_road_view.py b/selfdrive/ui/mici/onroad/augmented_road_view.py index 73dd648518..72be9cbe4d 100644 --- a/selfdrive/ui/mici/onroad/augmented_road_view.py +++ b/selfdrive/ui/mici/onroad/augmented_road_view.py @@ -130,7 +130,7 @@ class BookmarkIcon(Widget): if self._offset_filter.x > 0: icon_x = self.rect.x + self.rect.width - round(self._offset_filter.x) icon_y = self.rect.y + (self.rect.height - self._icon.height) / 2 # Vertically centered - rl.draw_texture(self._icon, int(icon_x), int(icon_y), rl.WHITE) + rl.draw_texture_ex(self._icon, rl.Vector2(icon_x, icon_y), 0.0, 1.0, rl.WHITE) class AugmentedRoadView(CameraView): diff --git a/selfdrive/ui/mici/onroad/driver_state.py b/selfdrive/ui/mici/onroad/driver_state.py index 356d7ac832..92ff07c1e9 100644 --- a/selfdrive/ui/mici/onroad/driver_state.py +++ b/selfdrive/ui/mici/onroad/driver_state.py @@ -61,7 +61,7 @@ class DriverStateRenderer(Widget): self._dm_cone = gui_app.texture("icons_mici/onroad/driver_monitoring/dm_cone.png", cone_and_person_size, cone_and_person_size) center_size = round(36 / self.BASE_SIZE * self._rect.width) self._dm_center = gui_app.texture("icons_mici/onroad/driver_monitoring/dm_center.png", center_size, center_size) - self._dm_background = gui_app.texture("icons_mici/onroad/driver_monitoring/dm_background.png", self._rect.width, self._rect.height) + self._dm_background = gui_app.texture("icons_mici/onroad/driver_monitoring/dm_background.png", int(self._rect.width), int(self._rect.height)) def set_should_draw(self, should_draw: bool): self._should_draw = should_draw @@ -88,15 +88,14 @@ class DriverStateRenderer(Widget): if DEBUG: rl.draw_rectangle_lines_ex(self._rect, 1, rl.RED) - rl.draw_texture(self._dm_background, - int(self._rect.x), - int(self._rect.y), - rl.Color(255, 255, 255, int(255 * self._fade_filter.x))) + rl.draw_texture_ex(self._dm_background, + rl.Vector2(self._rect.x, self._rect.y), 0.0, 1.0, + rl.Color(255, 255, 255, int(255 * self._fade_filter.x))) - rl.draw_texture(self._dm_person, - int(self._rect.x + (self._rect.width - self._dm_person.width) / 2), - int(self._rect.y + (self._rect.height - self._dm_person.height) / 2), - rl.Color(255, 255, 255, int(255 * 0.9 * self._fade_filter.x))) + rl.draw_texture_ex(self._dm_person, + rl.Vector2(self._rect.x + (self._rect.width - self._dm_person.width) / 2, + self._rect.y + (self._rect.height - self._dm_person.height) / 2), 0.0, 1.0, + rl.Color(255, 255, 255, int(255 * 0.9 * self._fade_filter.x))) if self.effective_active: source_rect = rl.Rectangle(0, 0, self._dm_cone.width, self._dm_cone.height) diff --git a/selfdrive/ui/mici/onroad/hud_renderer.py b/selfdrive/ui/mici/onroad/hud_renderer.py index 269b244ea0..551798863a 100644 --- a/selfdrive/ui/mici/onroad/hud_renderer.py +++ b/selfdrive/ui/mici/onroad/hud_renderer.py @@ -221,7 +221,7 @@ class HudRenderer(Widget): EXCLAMATION_POINT_SPACING = 10 exclamation_pos_x = pos_x - self._txt_exclamation_point.width / 2 + wheel_txt.width / 2 + EXCLAMATION_POINT_SPACING exclamation_pos_y = pos_y - self._txt_exclamation_point.height / 2 - rl.draw_texture(self._txt_exclamation_point, int(exclamation_pos_x), int(exclamation_pos_y), rl.WHITE) + rl.draw_texture_ex(self._txt_exclamation_point, rl.Vector2(exclamation_pos_x, exclamation_pos_y), 0.0, 1.0, rl.WHITE) def _draw_set_speed(self, rect: rl.Rectangle) -> None: """Draw the MAX speed indicator box.""" diff --git a/selfdrive/ui/mici/tests/test_widget_leaks.py b/selfdrive/ui/mici/tests/test_widget_leaks.py index ea7af84293..e35cb44776 100755 --- a/selfdrive/ui/mici/tests/test_widget_leaks.py +++ b/selfdrive/ui/mici/tests/test_widget_leaks.py @@ -10,7 +10,7 @@ from openpilot.system.ui.widgets import Widget from openpilot.selfdrive.ui.mici.layouts.onboarding import TrainingGuide as MiciTrainingGuide, OnboardingWindow as MiciOnboardingWindow from openpilot.selfdrive.ui.mici.onroad.driver_camera_dialog import DriverCameraDialog as MiciDriverCameraDialog from openpilot.selfdrive.ui.mici.widgets.pairing_dialog import PairingDialog as MiciPairingDialog -from openpilot.selfdrive.ui.mici.widgets.dialog import BigDialog, BigConfirmationDialogV2, BigInputDialog +from openpilot.selfdrive.ui.mici.widgets.dialog import BigDialog, BigConfirmationDialog, BigInputDialog from openpilot.selfdrive.ui.mici.layouts.settings.device import MiciFccModal # tici dialogs @@ -44,7 +44,7 @@ KNOWN_LEAKS = { "openpilot.system.ui.widgets.scroller_tici.Scroller", "openpilot.system.ui.widgets.label.UnifiedLabel", "openpilot.system.ui.widgets.mici_keyboard.MiciKeyboard", - "openpilot.selfdrive.ui.mici.widgets.dialog.BigConfirmationDialogV2", + "openpilot.selfdrive.ui.mici.widgets.dialog.BigConfirmationDialog", "openpilot.system.ui.widgets.keyboard.Keyboard", "openpilot.system.ui.widgets.slider.BigSlider", "openpilot.selfdrive.ui.mici.widgets.dialog.BigInputDialog", @@ -72,7 +72,7 @@ def test_dialogs_do_not_leak(): lambda: MiciTrainingGuide(lambda: None), lambda: MiciOnboardingWindow(lambda: None), lambda: BigDialog("test", "test"), - lambda: BigConfirmationDialogV2("test", "icons_mici/settings/network/new/trash.png"), + lambda: BigConfirmationDialog("test", gui_app.texture("icons_mici/settings/network/new/trash.png", 54, 64), lambda: None), lambda: BigInputDialog("test"), lambda: MiciFccModal(text="test"), # tici diff --git a/selfdrive/ui/mici/widgets/button.py b/selfdrive/ui/mici/widgets/button.py index 5559a1181c..058c351fb6 100644 --- a/selfdrive/ui/mici/widgets/button.py +++ b/selfdrive/ui/mici/widgets/button.py @@ -28,7 +28,7 @@ class ScrollState(Enum): class BigCircleButton(Widget): - def __init__(self, icon: str, red: bool = False, icon_size: tuple[int, int] = (64, 53), icon_offset: tuple[int, int] = (0, 0)): + def __init__(self, icon: rl.Texture, red: bool = False, icon_offset: tuple[int, int] = (0, 0)): super().__init__() self._red = red self._icon_offset = icon_offset @@ -39,7 +39,7 @@ class BigCircleButton(Widget): self._click_delay = 0.075 # Icons - self._txt_icon = gui_app.texture(icon, *icon_size) + self._txt_icon = icon self._txt_btn_disabled_bg = gui_app.texture("icons_mici/buttons/button_circle_disabled.png", 180, 180) self._txt_btn_bg = gui_app.texture("icons_mici/buttons/button_circle.png", 180, 180) @@ -71,8 +71,8 @@ class BigCircleButton(Widget): class BigCircleToggle(BigCircleButton): - def __init__(self, icon: str, toggle_callback: Callable | None = None, icon_size: tuple[int, int] = (64, 53), icon_offset: tuple[int, int] = (0, 0)): - super().__init__(icon, False, icon_size=icon_size, icon_offset=icon_offset) + def __init__(self, icon: rl.Texture, toggle_callback: Callable | None = None, icon_offset: tuple[int, int] = (0, 0)): + super().__init__(icon, False, icon_offset=icon_offset) self._toggle_callback = toggle_callback # State @@ -107,15 +107,13 @@ class BigButton(Widget): """A lightweight stand-in for the Qt BigButton, drawn & updated each frame.""" - def __init__(self, text: str, value: str = "", icon: Union[str, rl.Texture] = "", icon_size: tuple[int, int] = (64, 64), - scroll: bool = False): + def __init__(self, text: str, value: str = "", icon: Union[rl.Texture, None] = None, scroll: bool = False): super().__init__() self.set_rect(rl.Rectangle(0, 0, 402, 180)) self.text = text self.value = value - self._icon_size = icon_size + self._txt_icon = icon self._scroll = scroll - self.set_icon(icon) self._scale_filter = BounceFilter(1.0, 0.1, 1 / gui_app.target_fps) self._click_delay = 0.075 @@ -133,8 +131,8 @@ class BigButton(Widget): self._load_images() - def set_icon(self, icon: Union[str, rl.Texture]): - self._txt_icon = gui_app.texture(icon, *self._icon_size) if isinstance(icon, str) and len(icon) else icon + def set_icon(self, icon: Union[rl.Texture, None]): + self._txt_icon = icon def set_rotate_icon(self, rotate: bool): if rotate and self._rotate_icon_t is not None: @@ -151,7 +149,7 @@ class BigButton(Widget): def _width_hint(self) -> int: # Single line if scrolling, so hide behind icon if exists - icon_size = self._icon_size[0] if self._txt_icon and self._scroll and self.value else 0 + icon_size = self._txt_icon.width if self._txt_icon and self._scroll and self.value else 0 return int(self._rect.width - self.LABEL_HORIZONTAL_PADDING * 2 - icon_size) def _get_label_font_size(self): @@ -194,7 +192,9 @@ class BigButton(Widget): SHAKE_DURATION = 0.5 SHAKE_AMPLITUDE = 24.0 SHAKE_FREQUENCY = 32.0 - t = rl.get_time() - (self._shake_start or 0.0) + if self._shake_start is None: + return 0.0 + t = rl.get_time() - self._shake_start if t > SHAKE_DURATION: return 0.0 decay = 1.0 - t / SHAKE_DURATION @@ -335,6 +335,43 @@ class BigMultiToggle(BigToggle): y += 35 +class GreyBigButton(BigButton): + """Users should manage newlines with this class themselves""" + + LABEL_HORIZONTAL_PADDING = 30 + + def __init__(self, *args, **kwargs): + super().__init__(*args, **kwargs) + self.set_touch_valid_callback(lambda: False) + + self._rect.width = 476 + + self._label.set_font_size(36) + self._label.set_font_weight(FontWeight.BOLD) + self._label.set_line_height(1.0) + + self._sub_label.set_font_size(36) + self._sub_label.set_text_color(rl.Color(255, 255, 255, int(255 * 0.9))) + self._sub_label.set_font_weight(FontWeight.DISPLAY_REGULAR) + self._sub_label.set_alignment_vertical(rl.GuiTextAlignmentVertical.TEXT_ALIGN_MIDDLE if not self._label.text else + rl.GuiTextAlignmentVertical.TEXT_ALIGN_BOTTOM) + self._sub_label.set_line_height(0.95) + + @property + def LABEL_VERTICAL_PADDING(self): + return BigButton.LABEL_VERTICAL_PADDING if self._label.text else 18 + + def _width_hint(self) -> int: + return int(self._rect.width - self.LABEL_HORIZONTAL_PADDING * 2) + + def _get_label_font_size(self): + return 36 + + def _render(self, _): + rl.draw_rectangle_rounded(self._rect, 0.4, 10, rl.Color(255, 255, 255, int(255 * 0.15))) + self._draw_content(self._rect.y) + + class BigMultiParamToggle(BigMultiToggle): def __init__(self, text: str, param: str, options: list[str], toggle_callback: Callable | None = None, select_callback: Callable | None = None): @@ -370,9 +407,9 @@ class BigParamControl(BigToggle): # TODO: param control base class class BigCircleParamControl(BigCircleToggle): - def __init__(self, icon: str, param: str, toggle_callback: Callable | None = None, icon_size: tuple[int, int] = (64, 53), + def __init__(self, icon: rl.Texture, param: str, toggle_callback: Callable | None = None, icon_offset: tuple[int, int] = (0, 0)): - super().__init__(icon, toggle_callback, icon_size=icon_size, icon_offset=icon_offset) + super().__init__(icon, toggle_callback, icon_offset=icon_offset) self._param = param self.params = Params() self.set_checked(self.params.get_bool(self._param, False)) diff --git a/selfdrive/ui/mici/widgets/dialog.py b/selfdrive/ui/mici/widgets/dialog.py index b2662d8a3b..ed1466449b 100644 --- a/selfdrive/ui/mici/widgets/dialog.py +++ b/selfdrive/ui/mici/widgets/dialog.py @@ -4,14 +4,13 @@ import pyray as rl from typing import Union from collections.abc import Callable from openpilot.system.ui.widgets.nav_widget import NavWidget -from openpilot.system.ui.widgets.label import UnifiedLabel, gui_label +from openpilot.system.ui.widgets.label import UnifiedLabel from openpilot.system.ui.widgets.mici_keyboard import MiciKeyboard from openpilot.system.ui.lib.text_measure import measure_text_cached -from openpilot.system.ui.lib.wrap_text import wrap_text from openpilot.system.ui.lib.application import gui_app, FontWeight, MousePos from openpilot.system.ui.widgets.slider import RedBigSlider, BigSlider from openpilot.common.filter_simple import FirstOrderFilter -from openpilot.selfdrive.ui.mici.widgets.button import BigButton +from openpilot.selfdrive.ui.mici.widgets.button import BigCircleButton, BigButton, GreyBigButton DEBUG = False @@ -25,58 +24,31 @@ class BigDialogBase(NavWidget, abc.ABC): class BigDialog(BigDialogBase): - def __init__(self, - title: str, - description: str): + def __init__(self, title: str, description: str, icon: Union[rl.Texture, None] = None): super().__init__() - self._title = title - self._description = description + self._card = GreyBigButton(title, description, icon) def _render(self, _): - super()._render(_) - - # draw title - # TODO: we desperately need layouts - # TODO: coming up with these numbers manually is a pain and not scalable - # TODO: no clue what any of these numbers mean. VBox and HBox would remove all of this shite - max_width = self._rect.width - PADDING * 2 - - title_wrapped = '\n'.join(wrap_text(gui_app.font(FontWeight.BOLD), self._title, 50, int(max_width))) - title_size = measure_text_cached(gui_app.font(FontWeight.BOLD), title_wrapped, 50) - text_x_offset = 0 - title_rect = rl.Rectangle(int(self._rect.x + text_x_offset + PADDING), - int(self._rect.y + PADDING), - int(max_width), - int(title_size.y)) - gui_label(title_rect, title_wrapped, 50, font_weight=FontWeight.BOLD, - alignment=rl.GuiTextAlignment.TEXT_ALIGN_CENTER) - - # draw description - desc_wrapped = '\n'.join(wrap_text(gui_app.font(FontWeight.MEDIUM), self._description, 30, int(max_width))) - desc_size = measure_text_cached(gui_app.font(FontWeight.MEDIUM), desc_wrapped, 30) - desc_rect = rl.Rectangle(int(self._rect.x + text_x_offset + PADDING), - int(self._rect.y + self._rect.height / 3), - int(max_width), - int(desc_size.y)) - # TODO: text align doesn't seem to work properly with newlines - gui_label(desc_rect, desc_wrapped, 30, font_weight=FontWeight.MEDIUM, - alignment=rl.GuiTextAlignment.TEXT_ALIGN_CENTER) + self._card.render(rl.Rectangle( + self._rect.x + self._rect.width / 2 - self._card.rect.width / 2, + self._rect.y + self._rect.height / 2 - self._card.rect.height / 2, + self._card.rect.width, + self._card.rect.height, + )) -class BigConfirmationDialogV2(BigDialogBase): - def __init__(self, title: str, icon: str, red: bool = False, - exit_on_confirm: bool = True, - confirm_callback: Callable | None = None): +class BigConfirmationDialog(BigDialogBase): + def __init__(self, title: str, icon: rl.Texture, confirm_callback: Callable[[], None], + exit_on_confirm: bool = True, red: bool = False): super().__init__() self._confirm_callback = confirm_callback self._exit_on_confirm = exit_on_confirm - icon_txt = gui_app.texture(icon, 64, 53) self._slider: BigSlider | RedBigSlider if red: - self._slider = RedBigSlider(title, icon_txt, confirm_callback=self._on_confirm) + self._slider = self._child(RedBigSlider(title, icon, confirm_callback=self._on_confirm)) else: - self._slider = BigSlider(title, icon_txt, confirm_callback=self._on_confirm) + self._slider = self._child(BigSlider(title, icon, confirm_callback=self._on_confirm)) self._slider.set_enabled(lambda: self.enabled and not self.is_dismissing) # for nav stack + NavWidget def _on_confirm(self): @@ -158,9 +130,9 @@ class BigInputDialog(BigDialogBase): bg_block_margin = 5 text_x = PADDING / 2 + self._enter_img.width + PADDING - text_field_rect = rl.Rectangle(text_x, int(self._rect.y + PADDING) - bg_block_margin, - int(self._rect.width - text_x * 2), - int(text_size.y)) + text_field_rect = rl.Rectangle(text_x, self._rect.y + PADDING - bg_block_margin, + self._rect.width - text_x * 2, + text_size.y) # draw text input # push text left with a gradient on left side if too long @@ -181,8 +153,8 @@ class BigInputDialog(BigDialogBase): # draw gradient on left side to indicate more text if text_size.x > text_field_rect.width: - rl.draw_rectangle_gradient_h(int(text_field_rect.x), int(text_field_rect.y), 80, int(text_field_rect.height), - rl.BLACK, rl.BLANK) + rl.draw_rectangle_gradient_ex(rl.Rectangle(text_field_rect.x, text_field_rect.y, 80, text_field_rect.height), + rl.BLACK, rl.BLANK, rl.BLANK, rl.BLACK) # draw cursor blink_alpha = (math.sin(rl.get_time() * 6) + 1) / 2 @@ -190,14 +162,14 @@ class BigInputDialog(BigDialogBase): cursor_x = min(text_x + text_size.x + 3, text_field_rect.x + text_field_rect.width) else: cursor_x = text_field_rect.x - 6 - rl.draw_rectangle_rounded(rl.Rectangle(int(cursor_x), int(text_field_rect.y), 4, int(text_size.y)), + rl.draw_rectangle_rounded(rl.Rectangle(cursor_x, text_field_rect.y, 4, text_size.y), 1, 4, rl.Color(255, 255, 255, int(255 * blink_alpha))) # draw backspace icon with nice fade self._backspace_img_alpha.update(255 * bool(text)) if self._backspace_img_alpha.x > 1: color = rl.Color(255, 255, 255, int(self._backspace_img_alpha.x)) - rl.draw_texture(self._backspace_img, int(self._rect.width - self._backspace_img.width - 27), int(self._rect.y + 14), color) + rl.draw_texture_ex(self._backspace_img, rl.Vector2(self._rect.width - self._backspace_img.width - 27, self._rect.y + 14), 0.0, 1.0, color) if not text and self._hint_label.text and not candidate_char: # draw description if no text entered yet and not drawing candidate char @@ -215,9 +187,9 @@ class BigInputDialog(BigDialogBase): # draw enter button self._enter_img_alpha.update(255 if len(text) >= self._minimum_length else 0) color = rl.Color(255, 255, 255, int(self._enter_img_alpha.x)) - rl.draw_texture(self._enter_img, int(self._rect.x + PADDING / 2), int(self._rect.y), color) + rl.draw_texture_ex(self._enter_img, rl.Vector2(self._rect.x + PADDING / 2, self._rect.y), 0.0, 1.0, color) color = rl.Color(255, 255, 255, 255 - int(self._enter_img_alpha.x)) - rl.draw_texture(self._enter_disabled_img, int(self._rect.x + PADDING / 2), int(self._rect.y), color) + rl.draw_texture_ex(self._enter_disabled_img, rl.Vector2(self._rect.x + PADDING / 2, self._rect.y), 0.0, 1.0, color) # keyboard goes over everything self._keyboard.render(self._rect) @@ -254,3 +226,15 @@ class BigDialogButton(BigButton): dlg = BigDialog(self.text, self._description) gui_app.push_widget(dlg) + + +class BigConfirmationCircleButton(BigCircleButton): + def __init__(self, title: str, icon: rl.Texture, confirm_callback: Callable[[], None], exit_on_confirm: bool = True, + red: bool = False, icon_offset: tuple[int, int] = (0, 0)): + super().__init__(icon, red, icon_offset) + + def show_confirm_dialog(): + gui_app.push_widget(BigConfirmationDialog(title, icon, confirm_callback, + exit_on_confirm=exit_on_confirm, red=red)) + + self.set_click_callback(show_confirm_dialog) diff --git a/selfdrive/ui/mici/widgets/pairing_dialog.py b/selfdrive/ui/mici/widgets/pairing_dialog.py index 991cb05a8c..a18b26ec02 100644 --- a/selfdrive/ui/mici/widgets/pairing_dialog.py +++ b/selfdrive/ui/mici/widgets/pairing_dialog.py @@ -9,7 +9,7 @@ from openpilot.common.params import Params from openpilot.selfdrive.ui.ui_state import ui_state from openpilot.system.ui.widgets.nav_widget import NavWidget from openpilot.system.ui.lib.application import FontWeight, gui_app -from openpilot.system.ui.widgets.label import MiciLabel +from openpilot.system.ui.widgets.label import UnifiedLabel class PairingDialog(NavWidget): @@ -24,8 +24,7 @@ class PairingDialog(NavWidget): self._last_qr_generation = float("-inf") self._txt_pair = gui_app.texture("icons_mici/settings/device/pair.png", 33, 60) - self._pair_label = MiciLabel("pair with comma connect", 48, font_weight=FontWeight.BOLD, - color=rl.Color(255, 255, 255, int(255 * 0.9)), line_height=40, wrap_text=True) + self._pair_label = UnifiedLabel("pair with comma connect", font_size=48, font_weight=FontWeight.BOLD, line_height=0.8) def _get_pairing_url(self) -> str: try: @@ -77,7 +76,7 @@ class PairingDialog(NavWidget): self._render_qr_code() label_x = self._rect.x + 8 + self._rect.height + 24 - self._pair_label.set_width(int(self._rect.width - label_x)) + self._pair_label.set_max_width(int(self._rect.width - label_x)) self._pair_label.set_position(label_x, self._rect.y + 16) self._pair_label.render() @@ -93,7 +92,7 @@ class PairingDialog(NavWidget): return scale = self._rect.height / self._qr_texture.height - pos = rl.Vector2(self._rect.x + 8, self._rect.y) + pos = rl.Vector2(round(self._rect.x + 8), round(self._rect.y)) rl.draw_texture_ex(self._qr_texture, pos, 0.0, scale, rl.WHITE) def __del__(self): diff --git a/selfdrive/ui/onroad/exp_button.py b/selfdrive/ui/onroad/exp_button.py index e5d8171413..9a92ebc3c3 100644 --- a/selfdrive/ui/onroad/exp_button.py +++ b/selfdrive/ui/onroad/exp_button.py @@ -50,7 +50,7 @@ class ExpButton(Widget): texture = self._txt_exp if self._held_or_actual_mode() else self._txt_wheel rl.draw_circle(center_x, center_y, self._rect.width / 2, self._black_bg) - rl.draw_texture(texture, center_x - texture.width // 2, center_y - texture.height // 2, self._white_color) + rl.draw_texture_ex(texture, rl.Vector2(center_x - texture.width / 2, center_y - texture.height / 2), 0.0, 1.0, self._white_color) def _held_or_actual_mode(self): now = time.monotonic() diff --git a/selfdrive/ui/sunnypilot/layouts/onboarding.py b/selfdrive/ui/sunnypilot/layouts/onboarding.py index eed3cfd6b3..7e532678b0 100644 --- a/selfdrive/ui/sunnypilot/layouts/onboarding.py +++ b/selfdrive/ui/sunnypilot/layouts/onboarding.py @@ -20,7 +20,7 @@ class SunnylinkConsentPage(Widget): self._done_callback = done_callback self._step = 0 - self._title = Label(tr("sunnylink"), font_size=90, font_weight=FontWeight.BOLD, text_alignment=rl.GuiTextAlignment.TEXT_ALIGN_LEFT) + self._title = self._child(Label(tr("sunnylink"), font_size=90, font_weight=FontWeight.BOLD, text_alignment=rl.GuiTextAlignment.TEXT_ALIGN_LEFT)) self._content = [ { @@ -40,9 +40,10 @@ class SunnylinkConsentPage(Widget): } ] - self._primary_btn = Button("", button_style=ButtonStyle.PRIMARY, click_callback=lambda: self._handle_choice("enable")) - self._secondary_btn = Button("", button_style=ButtonStyle.NORMAL, click_callback=lambda: self._handle_choice("secondary")) - self._danger_btn = Button("", button_style=ButtonStyle.DANGER, click_callback=lambda: self._handle_choice("disable")) + self._primary_btn = self._child(Button("", button_style=ButtonStyle.PRIMARY, click_callback=lambda: self._handle_choice("enable"))) + self._secondary_btn = self._child(Button("", button_style=ButtonStyle.NORMAL, click_callback=lambda: self._handle_choice("secondary"))) + self._danger_btn = self._child(Button("", button_style=ButtonStyle.DANGER, click_callback=lambda: self._handle_choice("disable"))) + self._desc = self._child(Label("", font_size=90, font_weight=FontWeight.MEDIUM, text_alignment=rl.GuiTextAlignment.TEXT_ALIGN_LEFT)) def _handle_choice(self, choice): if choice == "enable": @@ -73,8 +74,8 @@ class SunnylinkConsentPage(Widget): desc_y = welcome_y + 120 desc_rect = rl.Rectangle(desc_x, desc_y, self._rect.width - desc_x, self._rect.height - desc_y - 250) - desc_label = Label(step_data["text"], font_size=90, font_weight=FontWeight.MEDIUM, text_alignment=rl.GuiTextAlignment.TEXT_ALIGN_LEFT) - desc_label.render(desc_rect) + self._desc.set_text(step_data["text"]) + self._desc.render(desc_rect) btn_y = self._rect.y + self._rect.height - 160 - 45 diff --git a/selfdrive/ui/sunnypilot/layouts/settings/settings.py b/selfdrive/ui/sunnypilot/layouts/settings/settings.py index e379a77104..4917c9a157 100644 --- a/selfdrive/ui/sunnypilot/layouts/settings/settings.py +++ b/selfdrive/ui/sunnypilot/layouts/settings/settings.py @@ -82,8 +82,7 @@ class NavButton(Widget): if self.panel_info.icon: icon_texture = gui_app.texture(self.panel_info.icon, ICON_SIZE, ICON_SIZE, keep_aspect_ratio=True) - rl.draw_texture(icon_texture, int(content_x), int(rect.y + (OP.NAV_BTN_HEIGHT - icon_texture.height) / 2), - rl.WHITE) + rl.draw_texture_ex(icon_texture, rl.Vector2(content_x, rect.y + (OP.NAV_BTN_HEIGHT - icon_texture.height) / 2), 0.0, 1.0, rl.WHITE) content_x += ICON_SIZE + 20 # Draw button text (right-aligned) diff --git a/selfdrive/ui/sunnypilot/layouts/settings/sunnylink.py b/selfdrive/ui/sunnypilot/layouts/settings/sunnylink.py index 5edd2e5b89..1d9b99d5fd 100644 --- a/selfdrive/ui/sunnypilot/layouts/settings/sunnylink.py +++ b/selfdrive/ui/sunnypilot/layouts/settings/sunnylink.py @@ -41,7 +41,7 @@ class SunnylinkHeader(Widget): self._description = UnifiedLabel( text=tr("For secure backup, restore, and remote configuration"), font_size=40, - font_weight=FontWeight.LIGHT, + font_weight=FontWeight.NORMAL, text_color=rl.Color(0, 255, 0, 255), # Green alignment=rl.GuiTextAlignment.TEXT_ALIGN_CENTER, alignment_vertical=rl.GuiTextAlignmentVertical.TEXT_ALIGN_TOP, @@ -53,7 +53,7 @@ class SunnylinkHeader(Widget): text=tr("Sponsorship isn't required for basic backup/restore") + "\n" + tr("Click the Sponsor button for more details"), font_size=35, - font_weight=FontWeight.LIGHT, + font_weight=FontWeight.NORMAL, text_color=rl.Color(255, 165, 0, 255), # Orange alignment=rl.GuiTextAlignment.TEXT_ALIGN_CENTER, alignment_vertical=rl.GuiTextAlignmentVertical.TEXT_ALIGN_TOP, @@ -107,7 +107,7 @@ class SunnylinkDescriptionItem(Widget): self._description = UnifiedLabel( text="", font_size=40, - font_weight=FontWeight.LIGHT, + font_weight=FontWeight.NORMAL, text_color=rl.WHITE, alignment=rl.GuiTextAlignment.TEXT_ALIGN_LEFT, alignment_vertical=rl.GuiTextAlignmentVertical.TEXT_ALIGN_TOP, diff --git a/selfdrive/ui/sunnypilot/layouts/settings/trips.py b/selfdrive/ui/sunnypilot/layouts/settings/trips.py index da9eb42d29..066f52507f 100644 --- a/selfdrive/ui/sunnypilot/layouts/settings/trips.py +++ b/selfdrive/ui/sunnypilot/layouts/settings/trips.py @@ -93,7 +93,7 @@ class TripsLayout(Widget): # Values number_font = gui_app.font(FontWeight.BOLD) - unit_font = gui_app.font(FontWeight.LIGHT) + unit_font = gui_app.font(FontWeight.NORMAL) number_base_size = 92 unit_base_size = 55 number_size = number_base_size * FONT_SCALE @@ -112,9 +112,9 @@ class TripsLayout(Widget): center_x = col_x + (col_width / 2) # Icon - icon_x = int(center_x - (icon.width / 2)) - icon_y = int(content_y + 60) - rl.draw_texture(icon, icon_x, icon_y, rl.WHITE) + icon_x = center_x - (icon.width / 2) + icon_y = content_y + 60 + rl.draw_texture_ex(icon, rl.Vector2(icon_x, icon_y), 0.0, 1.0, rl.WHITE) # Value val_size = measure_text_cached(number_font, value, number_base_size) diff --git a/selfdrive/ui/sunnypilot/mici/layouts/models.py b/selfdrive/ui/sunnypilot/mici/layouts/models.py index 5d8de4381a..d8da750fe1 100644 --- a/selfdrive/ui/sunnypilot/mici/layouts/models.py +++ b/selfdrive/ui/sunnypilot/mici/layouts/models.py @@ -20,10 +20,10 @@ class ModelsLayoutMici(NavScroller): self.original_back_callback = back_callback self.focused_widget = None - self.current_model_btn = BigButton(tr("current model"), "", "") + self.current_model_btn = BigButton(tr("current model")) self.current_model_btn.set_click_callback(self._show_folders) - self.cancel_download_btn = BigButton(tr("cancel download"), "", "") + self.cancel_download_btn = BigButton(tr("cancel download")) self.cancel_download_btn.set_click_callback(lambda: ui_state.params.remove("ModelManager_DownloadIndex")) self.main_items = [self.current_model_btn, self.cancel_download_btn] @@ -52,13 +52,13 @@ class ModelsLayoutMici(NavScroller): self.focused_widget = self.current_model_btn folders = self._get_grouped_bundles() folder_buttons = [] - default_btn = BigButton(tr("default model"), "", "") + default_btn = BigButton(tr("default model")) default_btn.set_click_callback(self._select_default) folder_buttons.append(default_btn) for folder in sorted(folders.keys(), key=lambda f: max((bundle.index for bundle in folders[f]), default=-1), reverse=True): if folder.lower() in ["release models", "master models"]: - btn = BigButton(folder.lower(), "", "") + btn = BigButton(folder.lower()) btn.set_click_callback(lambda f=folder: self._select_folder(f)) folder_buttons.append(btn) self._show_selection_view(folder_buttons, self._reset_main_view) @@ -78,7 +78,7 @@ class ModelsLayoutMici(NavScroller): btns = [] for bundle in bundles: txt = bundle.displayName.lower() - btn = BigButton(txt, "", "") + btn = BigButton(txt) btn.set_click_callback(lambda b=bundle: self._select_model(b)) btns.append(btn) self._show_selection_view(btns, self._show_folders) diff --git a/selfdrive/ui/sunnypilot/mici/layouts/onboarding.py b/selfdrive/ui/sunnypilot/mici/layouts/onboarding.py index 9fa2df0e8b..a98f5a2e2e 100644 --- a/selfdrive/ui/sunnypilot/mici/layouts/onboarding.py +++ b/selfdrive/ui/sunnypilot/mici/layouts/onboarding.py @@ -6,8 +6,7 @@ See the LICENSE.md file in the root directory for more details. """ from collections.abc import Callable -from openpilot.selfdrive.ui.mici.widgets.button import BigCircleButton -from openpilot.selfdrive.ui.mici.widgets.dialog import BigConfirmationDialogV2 +from openpilot.selfdrive.ui.mici.widgets.dialog import BigConfirmationCircleButton from openpilot.system.ui.lib.application import gui_app from openpilot.system.ui.mici_setup import GreyBigButton from openpilot.system.ui.widgets.scroller import NavScroller @@ -17,19 +16,11 @@ class SunnylinkConsentPage(NavScroller): def __init__(self, on_accept: Callable | None = None, on_decline: Callable | None = None): super().__init__() - def show_accept_dialog(): - gui_app.push_widget(BigConfirmationDialogV2("enable\nsunnylink", "icons_mici/setup/driver_monitoring/dm_check.png", - confirm_callback=on_accept)) + self._accept_button = BigConfirmationCircleButton("enable\nsunnylink", gui_app.texture("icons_mici/setup/driver_monitoring/dm_check.png", 64, 64), + on_accept, exit_on_confirm=False) - def show_decline_dialog(): - gui_app.push_widget(BigConfirmationDialogV2("disable\nsunnylink", "icons_mici/setup/cancel.png", - red=True, confirm_callback=on_decline)) - - self._accept_button = BigCircleButton("icons_mici/setup/driver_monitoring/dm_check.png") - self._accept_button.set_click_callback(show_accept_dialog) - - self._decline_button = BigCircleButton("icons_mici/setup/cancel.png", red=True) - self._decline_button.set_click_callback(show_decline_dialog) + self._decline_button = BigConfirmationCircleButton("disable\nsunnylink", gui_app.texture("icons_mici/setup/cancel.png", 64, 64), + on_decline, red=True, exit_on_confirm=False) self._scroller.add_widgets([ GreyBigButton("sunnylink", "scroll to continue", diff --git a/selfdrive/ui/sunnypilot/mici/layouts/settings.py b/selfdrive/ui/sunnypilot/mici/layouts/settings.py index 43d0bd2cef..9e160521c7 100644 --- a/selfdrive/ui/sunnypilot/mici/layouts/settings.py +++ b/selfdrive/ui/sunnypilot/mici/layouts/settings.py @@ -18,11 +18,11 @@ class SettingsLayoutSP(OP.SettingsLayout): OP.SettingsLayout.__init__(self) sunnylink_panel = SunnylinkLayoutMici(back_callback=gui_app.pop_widget) - sunnylink_btn = BigButton("sunnylink", "", "icons_mici/settings/developer/ssh.png") + sunnylink_btn = BigButton("sunnylink", "", gui_app.texture("icons_mici/settings/developer/ssh.png", ICON_SIZE, ICON_SIZE)) sunnylink_btn.set_click_callback(lambda: gui_app.push_widget(sunnylink_panel)) models_panel = ModelsLayoutMici(back_callback=gui_app.pop_widget) - models_btn = BigButton("models", "", "../../sunnypilot/selfdrive/assets/offroad/icon_models.png") + models_btn = BigButton("models", "", gui_app.texture("../../sunnypilot/selfdrive/assets/offroad/icon_models.png", ICON_SIZE, ICON_SIZE)) models_btn.set_click_callback(lambda: gui_app.push_widget(models_panel)) items = self._scroller._items.copy() diff --git a/selfdrive/ui/sunnypilot/mici/layouts/sunnylink.py b/selfdrive/ui/sunnypilot/mici/layouts/sunnylink.py index c892db9960..43ea07643e 100644 --- a/selfdrive/ui/sunnypilot/mici/layouts/sunnylink.py +++ b/selfdrive/ui/sunnypilot/mici/layouts/sunnylink.py @@ -8,7 +8,7 @@ from collections.abc import Callable from cereal import custom from openpilot.selfdrive.ui.mici.widgets.button import BigButton, BigToggle -from openpilot.selfdrive.ui.mici.widgets.dialog import BigDialog, BigConfirmationDialogV2 +from openpilot.selfdrive.ui.mici.widgets.dialog import BigDialog, BigConfirmationDialog from openpilot.selfdrive.ui.sunnypilot.mici.layouts.onboarding import SunnylinkConsentPage from openpilot.selfdrive.ui.sunnypilot.mici.widgets.sunnylink_pairing_dialog import SunnylinkPairingDialog from openpilot.selfdrive.ui.ui_state import ui_state @@ -32,9 +32,9 @@ class SunnylinkLayoutMici(NavScroller): toggle_callback=self._sunnylink_toggle_callback) self._sunnylink_sponsor_button = SunnylinkPairBigButton(sponsor_pairing=False) self._sunnylink_pair_button = SunnylinkPairBigButton(sponsor_pairing=True) - self._backup_btn = BigButton(tr("backup settings"), "", "") + self._backup_btn = BigButton(tr("backup settings"), "") self._backup_btn.set_click_callback(lambda: self._handle_backup_restore_btn(restore=False)) - self._restore_btn = BigButton(tr("restore settings"), "", "") + self._restore_btn = BigButton(tr("restore settings"), "") self._restore_btn.set_click_callback(lambda: self._handle_backup_restore_btn(restore=True)) self._sunnylink_uploader_toggle = BigToggle(text=tr("sunnylink uploader"), initial_state=False, toggle_callback=self._sunnylink_uploader_callback) @@ -105,8 +105,8 @@ class SunnylinkLayoutMici(NavScroller): def _handle_backup_restore_btn(self, restore: bool = False): lbl = tr("slide to restore") if restore else tr("slide to backup") - icon = "icons_mici/settings/device/update.png" - dlg = BigConfirmationDialogV2(lbl, icon, confirm_callback=self._restore_handler if restore else self._backup_handler) + icon = gui_app.texture("icons_mici/settings/device/update.png", 64, 64) + dlg = BigConfirmationDialog(lbl, icon, confirm_callback=self._restore_handler if restore else self._backup_handler) gui_app.push_widget(dlg) def _backup_handler(self): @@ -169,8 +169,8 @@ class SunnylinkLayoutMici(NavScroller): elif (restore_status == custom.BackupManagerSP.Status.completed or (restore_status == custom.BackupManagerSP.Status.idle and restore_progress == 100.0)): self._restore_in_progress = False - gui_app.push_widget(BigConfirmationDialogV2( - title="slide to restart", icon="icons_mici/settings/device/reboot.png", + gui_app.push_widget(BigConfirmationDialog( + title="slide to restart", icon=gui_app.texture("icons_mici/settings/device/reboot.png", 64, 64), confirm_callback=lambda: gui_app.request_close())) else: @@ -186,7 +186,7 @@ class SunnylinkLayoutMici(NavScroller): class SunnylinkPairBigButton(BigButton): def __init__(self, sponsor_pairing: bool = False): self.sponsor_pairing = sponsor_pairing - super().__init__("", "", "") + super().__init__("") def _update_state(self): super()._update_state() diff --git a/selfdrive/ui/sunnypilot/mici/widgets/sunnylink_pairing_dialog.py b/selfdrive/ui/sunnypilot/mici/widgets/sunnylink_pairing_dialog.py index eb3c2bddfe..c727e4fc1c 100644 --- a/selfdrive/ui/sunnypilot/mici/widgets/sunnylink_pairing_dialog.py +++ b/selfdrive/ui/sunnypilot/mici/widgets/sunnylink_pairing_dialog.py @@ -13,7 +13,7 @@ from openpilot.sunnypilot.sunnylink.api import SunnylinkApi, UNREGISTERED_SUNNYL from openpilot.system.ui.lib.application import FontWeight, gui_app from openpilot.system.ui.lib.multilang import tr from openpilot.system.ui.widgets.nav_widget import NavWidget -from openpilot.system.ui.widgets.label import MiciLabel +from openpilot.system.ui.widgets.label import UnifiedLabel class SunnylinkPairingDialog(PairingDialog): @@ -23,8 +23,8 @@ class SunnylinkPairingDialog(PairingDialog): PairingDialog.__init__(self) self._sponsor_pairing = sponsor_pairing label_text = tr("pair with sunnylink") if sponsor_pairing else tr("become a sunnypilot sponsor") - self._pair_label = MiciLabel(label_text, 48, font_weight=FontWeight.BOLD, - color=rl.Color(255, 255, 255, int(255 * 0.9)), line_height=40, wrap_text=True) + self._pair_label = UnifiedLabel(label_text, font_size=48, font_weight=FontWeight.BOLD, + text_color=rl.Color(255, 255, 255, int(255 * 0.9)), line_height=0.8) def _get_pairing_url(self) -> str: qr_string = "https://github.com/sponsors/sunnyhaibin" diff --git a/selfdrive/ui/sunnypilot/onroad/blind_spot_indicators.py b/selfdrive/ui/sunnypilot/onroad/blind_spot_indicators.py index 4e1d748117..2efda17a2b 100644 --- a/selfdrive/ui/sunnypilot/onroad/blind_spot_indicators.py +++ b/selfdrive/ui/sunnypilot/onroad/blind_spot_indicators.py @@ -42,11 +42,11 @@ class BlindSpotIndicators: pos_y = int(rect.y + BLIND_SPOT_Y_OFFSET) alpha = int(255 * self._blind_spot_left_alpha_filter.x) color = rl.Color(255, 255, 255, alpha) - rl.draw_texture(self._txt_blind_spot_left, pos_x, pos_y, color) + rl.draw_texture_ex(self._txt_blind_spot_left, rl.Vector2(pos_x, pos_y), 0.0, 1.0, color) if self._blind_spot_right_alpha_filter.x > 0.01: pos_x = int(rect.x + rect.width - BLIND_SPOT_MARGIN_X - self._txt_blind_spot_right.width) pos_y = int(rect.y + BLIND_SPOT_Y_OFFSET) alpha = int(255 * self._blind_spot_right_alpha_filter.x) color = rl.Color(255, 255, 255, alpha) - rl.draw_texture(self._txt_blind_spot_right, pos_x, pos_y, color) + rl.draw_texture_ex(self._txt_blind_spot_right, rl.Vector2(pos_x, pos_y), 0.0, 1.0, color) diff --git a/selfdrive/ui/sunnypilot/onroad/circular_alerts.py b/selfdrive/ui/sunnypilot/onroad/circular_alerts.py index 9c9ab7ac84..f90fc81914 100644 --- a/selfdrive/ui/sunnypilot/onroad/circular_alerts.py +++ b/selfdrive/ui/sunnypilot/onroad/circular_alerts.py @@ -101,9 +101,9 @@ class CircularAlertsRenderer: # Draw Image if self._alert_img and self._e2e_alert_display_timer > 0: - img_x = int(center.x - self._alert_img.width / 2) - img_y = int(center.y - self._alert_img.height / 2) - rl.draw_texture(self._alert_img, img_x, img_y, rl.WHITE) + img_x = center.x - self._alert_img.width / 2 + img_y = center.y - self._alert_img.height / 2 + rl.draw_texture_ex(self._alert_img, rl.Vector2(img_x, img_y), 0.0, 1.0, rl.WHITE) # Draw Text txt_color = rl.Color(255, 255, 255, 255) if is_pulsing else rl.Color(0, 255, 0, 190) diff --git a/selfdrive/ui/sunnypilot/onroad/speed_limit.py b/selfdrive/ui/sunnypilot/onroad/speed_limit.py index 1b03e9a204..98f5b29087 100644 --- a/selfdrive/ui/sunnypilot/onroad/speed_limit.py +++ b/selfdrive/ui/sunnypilot/onroad/speed_limit.py @@ -227,7 +227,7 @@ class SpeedLimitRenderer(Widget, SpeedLimitAlertRenderer): arrow_x = sign_rect.x + sign_rect.width + arrow_spacing arrow_y = sign_rect.y + (sign_rect.height - txt_icon.height) / 2 color = rl.Color(255, 255, 255, int(icon_alpha)) - rl.draw_texture(txt_icon, int(arrow_x), int(arrow_y), color) + rl.draw_texture_ex(txt_icon, rl.Vector2(arrow_x, arrow_y), 0.0, 1.0, color) def _render_vienna(self, rect, val, sub, color, has_limit, alpha=1.0): center = rl.Vector2(rect.x + rect.width / 2, rect.y + rect.height / 2) diff --git a/selfdrive/ui/sunnypilot/onroad/turn_signal.py b/selfdrive/ui/sunnypilot/onroad/turn_signal.py index e285009364..fc6f7eb915 100644 --- a/selfdrive/ui/sunnypilot/onroad/turn_signal.py +++ b/selfdrive/ui/sunnypilot/onroad/turn_signal.py @@ -55,10 +55,10 @@ class TurnSignalWidget(Widget): self._texture = self._blind_spot_texture if self._type == 'blind_spot' else self._signal_texture if self._texture: - pos_x = int(self._rect.x + (self._rect.width - self._texture.width) / 2) - pos_y = int(self._rect.y + (self._rect.height - self._texture.height) / 2) + pos_x = self._rect.x + (self._rect.width - self._texture.width) / 2 + pos_y = self._rect.y + (self._rect.height - self._texture.height) / 2 color = rl.Color(255, 255, 255, icon_alpha) - rl.draw_texture(self._texture, pos_x, pos_y, color) + rl.draw_texture_ex(self._texture, rl.Vector2(pos_x, pos_y), 0.0, 1.0, color) def activate(self, _type: str = 'signal'): if not self._active or self._type != _type: diff --git a/selfdrive/ui/tests/.gitignore b/selfdrive/ui/tests/.gitignore deleted file mode 100644 index 74ab2675db..0000000000 --- a/selfdrive/ui/tests/.gitignore +++ /dev/null @@ -1,2 +0,0 @@ -test -test_translations diff --git a/selfdrive/ui/tests/diff/.gitignore b/selfdrive/ui/tests/diff/.gitignore deleted file mode 100644 index e21a8d896e..0000000000 --- a/selfdrive/ui/tests/diff/.gitignore +++ /dev/null @@ -1,2 +0,0 @@ -report -.coverage diff --git a/selfdrive/ui/tests/diff/replay.py b/selfdrive/ui/tests/diff/replay.py index 08c45b7b7f..fd82e325a3 100755 --- a/selfdrive/ui/tests/diff/replay.py +++ b/selfdrive/ui/tests/diff/replay.py @@ -4,12 +4,16 @@ import argparse import coverage import pyray as rl +from tqdm import tqdm from typing import Literal from collections.abc import Callable from cereal.messaging import PubMaster +from openpilot.common.api import Api +from openpilot.common.basedir import BASEDIR from openpilot.common.params import Params from openpilot.common.prefix import OpenpilotPrefix from openpilot.selfdrive.ui.tests.diff.diff import DIFF_OUT_DIR +from openpilot.system.updated.updated import parse_release_notes from openpilot.system.version import terms_version, training_version, terms_version_sp, sunnylink_consent_version LayoutVariant = Literal["mici", "tizi"] @@ -25,6 +29,7 @@ def setup_state(): params.put("DongleId", "test123456789") # Combined description for layouts that still use it (BIG home, settings/software) params.put("UpdaterCurrentDescription", "0.10.1 / test-branch / abc1234 / Nov 30") + params.put("UpdaterCurrentReleaseNotes", parse_release_notes(BASEDIR)) params.put("HasAcceptedTermsSP", terms_version_sp) params.put("CompletedSunnylinkConsentVersion", sunnylink_consent_version) @@ -34,6 +39,9 @@ def setup_state(): params.put("GitCommit", "abc12340ff9131237ba23a1d0fbd8edf9c80e87") params.put("GitCommitDate", "'1732924800 2024-11-30 00:00:00 +0000'") + # Patch Api.get_token to return a static token so the pairing QR code is deterministic across runs + Api.get_token = lambda self, payload_extra=None, expiry_hours=0: "test_token" + def run_replay(variant: LayoutVariant) -> None: if HEADLESS: @@ -43,7 +51,7 @@ def run_replay(variant: LayoutVariant) -> None: setup_state() os.makedirs(DIFF_OUT_DIR, exist_ok=True) - from openpilot.selfdrive.ui.ui_state import ui_state # Import within OpenpilotPrefix context so param values are setup correctly + from openpilot.selfdrive.ui.ui_state import ui_state, device # Import within OpenpilotPrefix context so param values are setup correctly from openpilot.system.ui.lib.application import gui_app # Import here for accurate coverage from openpilot.selfdrive.ui.tests.diff.replay_script import build_script @@ -56,6 +64,10 @@ def run_replay(variant: LayoutVariant) -> None: from openpilot.selfdrive.ui.layouts.main import MainLayout main_layout = MainLayout() + # Disable interactive timeout — replay clicks use left_down=False so they never reset the timer, + # and after 30s of real wall-clock time the settings panel would close automatically. + device.set_override_interactive_timeout(99999) + pm = PubMaster(["deviceState", "pandaStates", "driverStateV2", "selfdriveState"]) script = build_script(pm, main_layout, variant) script_index = 0 @@ -67,33 +79,35 @@ def run_replay(variant: LayoutVariant) -> None: rl.get_time = lambda: frame / FPS # Main loop to replay events and render frames - for _ in gui_app.render(): - # Handle all events for the current frame - while script_index < len(script) and script[script_index][0] == frame: - _, event = script[script_index] - # Call setup function, if any - if event.setup: - event.setup() - # Send mouse events to the application - if event.mouse_events: - with gui_app._mouse._lock: - gui_app._mouse._events.extend(event.mouse_events) - # Update persistent send function - if event.send_fn is not None: - send_fn = event.send_fn - # Move to next script event - script_index += 1 + with tqdm(total=script[-1][0] + 1, desc="Replaying", unit="frame", disable=bool(os.getenv("CI"))) as pbar: + for _ in gui_app.render(): + # Handle all events for the current frame + while script_index < len(script) and script[script_index][0] == frame: + _, event = script[script_index] + # Call setup function, if any + if event.setup: + event.setup() + # Send mouse events to the application + if event.mouse_events: + with gui_app._mouse._lock: + gui_app._mouse._events.extend(event.mouse_events) + # Update persistent send function + if event.send_fn is not None: + send_fn = event.send_fn + # Move to next script event + script_index += 1 - # Keep sending cereal messages for persistent states (onroad, alerts) - if send_fn: - send_fn() + # Keep sending cereal messages for persistent states (onroad, alerts) + if send_fn: + send_fn() - ui_state.update() + ui_state.update() - frame += 1 + frame += 1 + pbar.update(1) - if script_index >= len(script): - break + if script_index >= len(script): + break gui_app.close() diff --git a/selfdrive/ui/tests/diff/replay_script.py b/selfdrive/ui/tests/diff/replay_script.py index 9f2104ec49..c53d2f116b 100644 --- a/selfdrive/ui/tests/diff/replay_script.py +++ b/selfdrive/ui/tests/diff/replay_script.py @@ -3,15 +3,27 @@ from typing import TYPE_CHECKING from collections.abc import Callable from dataclasses import dataclass +import math + from cereal import car, log, messaging from cereal.messaging import PubMaster from openpilot.common.basedir import BASEDIR from openpilot.common.params import Params from openpilot.selfdrive.selfdrived.alertmanager import set_offroad_alert +from openpilot.selfdrive.ui.lib.prime_state import PrimeType from openpilot.selfdrive.ui.tests.diff.replay import FPS, LayoutVariant from openpilot.system.updated.updated import parse_release_notes -WAIT = int(FPS * 0.5) # Default frames to wait after events +# Default frames to wait after events +WAIT_LONG = FPS +WAIT_SHORT = FPS // 2 +FAST_CLICK = FPS // 6 + +# Direction vectors for drag gestures +DIR_LEFT = (-1, 0) +DIR_RIGHT = (1, 0) +DIR_UP = (0, -1) +DIR_DOWN = (0, 1) AlertSize = log.SelfdriveState.AlertSize AlertStatus = log.SelfdriveState.AlertStatus @@ -56,49 +68,92 @@ class Script: """Add a delay for the given number of frames followed by an empty event.""" self.add(ScriptEvent(), before=frames) - def setup(self, fn: Callable, wait_after: int = WAIT) -> None: + def setup(self, fn: Callable, wait_after: int = WAIT_SHORT) -> None: """Add a setup function to be called immediately followed by a delay of the given number of frames.""" self.add(ScriptEvent(setup=fn), after=wait_after) - def set_send(self, fn: Callable, wait_after: int = WAIT) -> None: + def set_send(self, fn: Callable, wait_after: int = WAIT_SHORT) -> None: """Set a new persistent send function to be called every frame.""" self.add(ScriptEvent(send_fn=fn), after=wait_after) - # TODO: Also add more complex gestures, like swipe or drag - def click(self, x: int, y: int, wait_after: int = WAIT, wait_between: int = 2) -> None: + def click(self, x: int, y: int, wait_after: int = WAIT_SHORT, wait_between: int = 2) -> None: """Add a click event to the script for the given position and specify frames to wait between mouse events or after the click.""" # NOTE: By default we wait a couple frames between mouse events so pressed states will be rendered from openpilot.system.ui.lib.application import MouseEvent, MousePos - # TODO: Add support for long press (left_down=True) mouse_down = MouseEvent(pos=MousePos(x, y), slot=0, left_pressed=True, left_released=False, left_down=False, t=self.get_frame_time()) self.add(ScriptEvent(mouse_events=[mouse_down]), after=wait_between) mouse_up = MouseEvent(pos=MousePos(x, y), slot=0, left_pressed=False, left_released=True, left_down=False, t=self.get_frame_time()) self.add(ScriptEvent(mouse_events=[mouse_up]), after=wait_after) + def drag(self, start_x: int, start_y: int, direction: tuple[int, int], distance: int, duration_frames: int, wait_after: int = WAIT_LONG) -> None: + """Add a drag gesture to the script from start position in the specified direction by the given distance over the given number of frames.""" + from openpilot.system.ui.lib.application import MouseEvent, MousePos + + # Calculate delta and end position based on direction and distance + delta_x, delta_y = direction[0] * distance, direction[1] * distance + end_x, end_y = start_x + delta_x, start_y + delta_y + + # Mouse down at start + mouse_down = MouseEvent(pos=MousePos(start_x, start_y), slot=0, left_pressed=True, left_released=False, left_down=True, t=self.get_frame_time()) + self.add(ScriptEvent(mouse_events=[mouse_down]), after=1) + + # Interpolate positions over duration_frames + for i in range(1, duration_frames): + t = i / duration_frames + x, y = int(start_x + delta_x * t), int(start_y + delta_y * t) + mouse_move = MouseEvent(pos=MousePos(x, y), slot=0, left_pressed=False, left_released=False, left_down=True, t=self.get_frame_time()) + self.add(ScriptEvent(mouse_events=[mouse_move]), after=1) + + # Mouse up at end + mouse_up = MouseEvent(pos=MousePos(end_x, end_y), slot=0, left_pressed=False, left_released=True, left_down=False, t=self.get_frame_time()) + self.add(ScriptEvent(mouse_events=[mouse_up]), after=wait_after) + # --- Setup functions --- -def put_update_params(params: Params | None = None) -> None: - if params is None: - params = Params() - params.put("UpdaterCurrentReleaseNotes", parse_release_notes(BASEDIR)) - params.put("UpdaterNewReleaseNotes", parse_release_notes(BASEDIR)) - params.put("UpdaterTargetBranch", BRANCH_NAME) + +def set_prime_state(prime_type: PrimeType) -> None: + from openpilot.selfdrive.ui.ui_state import ui_state + ui_state.prime_state.set_type(prime_type) def setup_offroad_alerts() -> None: - put_update_params(Params()) set_offroad_alert("Offroad_TemperatureTooHigh", True, extra_text='99C') set_offroad_alert("Offroad_ExcessiveActuation", True, extra_text='longitudinal') set_offroad_alert("Offroad_IsTakingSnapshot", True) -def setup_update_available() -> None: +def setup_update_available(available: bool = True) -> None: params = Params() - params.put_bool("UpdateAvailable", True) - params.put("UpdaterNewDescription", f"0.10.2 / {BRANCH_NAME} / 0a1b2c3 / Jan 01") - put_update_params(params) + params.put_bool("UpdateAvailable", available) + params.put("UpdaterAvailableBranches", ",".join(["test-branch", "test-branch-2", BRANCH_NAME])) + if available: + params.put("UpdaterNewDescription", f"0.10.2 / {BRANCH_NAME} / 0a1b2c3 / Jan 01") + params.put("UpdaterNewReleaseNotes", parse_release_notes(BASEDIR)) + params.put("UpdaterTargetBranch", BRANCH_NAME) + else: + params.remove("UpdaterNewDescription") + params.remove("UpdaterNewReleaseNotes") + params.remove("UpdaterTargetBranch") + + +def setup_calibration_params() -> None: + params = Params() + # live calibration + calib = messaging.new_message('liveCalibration') + calib.liveCalibration.calStatus = log.LiveCalibrationData.Status.calibrated + calib.liveCalibration.rpyCalib = [0.0, math.radians(2.5), math.radians(-1.2)] + params.put("CalibrationParams", calib.to_bytes()) + # live delay + delay = messaging.new_message('liveDelay') + delay.liveDelay.calPerc = 75 + params.put("LiveDelay", delay.to_bytes()) + # live torque parameters + torque = messaging.new_message('liveTorqueParameters') + torque.liveTorqueParameters.useParams = True + torque.liveTorqueParameters.calPerc = 60 + params.put("LiveTorqueParameters", torque.to_bytes()) def setup_developer_params() -> None: @@ -132,7 +187,6 @@ def make_network_state_setup(pm: PubMaster, network_type) -> Callable: def make_alert_setup(pm: PubMaster, size, text1, text2, status) -> Callable: def _send() -> None: - send_onroad(pm) alert = messaging.new_message('selfdriveState') ss = alert.selfdriveState ss.alertSize = size @@ -143,18 +197,181 @@ def make_alert_setup(pm: PubMaster, size, text1, text2, status) -> Callable: return _send +def test_onroad_alerts(script: Script, pm: PubMaster) -> None: + """Go through various alert types and sizes and add them to the script to test alert rendering. + Each alert is sent as a separate event with a delay in between.""" + # Small alert (normal) + script.set_send(make_alert_setup(pm, AlertSize.small, "Small Alert", "This is a small alert", AlertStatus.normal)) + # Medium alert (userPrompt) + script.set_send(make_alert_setup(pm, AlertSize.mid, "Medium Alert", "This is a medium alert", AlertStatus.userPrompt)) + # Full alert (critical) + script.set_send(make_alert_setup(pm, AlertSize.full, "DISENGAGE IMMEDIATELY", "Driver Distracted", AlertStatus.critical)) + # Full alert multiline + script.set_send(make_alert_setup(pm, AlertSize.full, "Reverse\nGear", "", AlertStatus.normal)) + # Full alert long text + script.set_send(make_alert_setup(pm, AlertSize.full, "TAKE CONTROL IMMEDIATELY", "Calibration Invalid: Remount Device & Recalibrate", AlertStatus.userPrompt)) + + # --- Script builders --- def build_mici_script(pm: PubMaster, main_layout, script: Script) -> None: """Build the replay script for the mici layout.""" from openpilot.system.ui.lib.application import gui_app - center = (gui_app.width // 2, gui_app.height // 2) + width, height = gui_app.width, gui_app.height + center = (width // 2, height // 2) + right = (width * 4 // 5, height // 2) + left = (width // 5, height // 2) + top = (width // 2, height // 10) + bottom = (width // 2, height * 9 // 10) + + DURATION = 5 + SWIPE_WAIT = FPS * 3 // 4 + + def click(times: int = 1, wait_after: int = WAIT_SHORT) -> None: + """Click at the center of the screen the given number of times with optional delay after.""" + for _ in range(times): + script.click(*center, wait_after=wait_after) + + def press(x: int, y: int, duration_frames: int = DURATION, wait_after: int = WAIT_SHORT) -> None: + """Perform a drag with no movement to simulate a left_down mouse event at the given position for the specified duration and delay after.""" + script.drag(x, y, (0, 0), 0, duration_frames, wait_after=wait_after) + + def swipe_left(distance: int = right[0] - left[0], duration_frames: int = DURATION, wait_after: int = SWIPE_WAIT) -> None: + """Drag from right edge to left (scroll right / slide confirmation).""" + script.drag(*right, DIR_LEFT, distance, duration_frames, wait_after) + + def swipe_right(distance: int = right[0] - left[0], duration_frames: int = DURATION, wait_after: int = SWIPE_WAIT) -> None: + """Drag from left edge to right (scroll left).""" + script.drag(*left, DIR_RIGHT, distance, duration_frames, wait_after) + + def swipe_down(distance: int = bottom[1] - top[1], duration_frames: int = DURATION, wait_after: int = SWIPE_WAIT) -> None: + """Drag from top edge to bottom (scroll up / go back).""" + script.drag(*top, DIR_DOWN, distance, duration_frames, wait_after) + + def swipe_up(distance: int = bottom[1] - top[1], duration_frames: int = DURATION, wait_after: int = SWIPE_WAIT) -> None: + """Drag from bottom edge to top (scroll down).""" + script.drag(*bottom, DIR_UP, distance, duration_frames, wait_after) + + ActionFn = Callable[[], None] | None + Cases = list[ActionFn] + + def run_actions(*actions: ActionFn, after_each: ActionFn = None) -> None: + """Helper function to run a sequence of actions in order for interaction tests, calling after_each callback after each action if provided.""" + for action in actions: + if action is not None: + action() + if after_each is not None: + after_each() + + def explore_setting(*actions: ActionFn) -> None: + """Helper function to open a settings item, run the given actions, and go back.""" + run_actions(click, *actions, swipe_down) # open, interact, go back + + def scroll_through_cases(cases: Cases) -> None: + """Helper function to explore a panel by calling the interaction callbacks for each item/page before swiping to the next one.""" + run_actions(*cases, after_each=lambda: swipe_left(210, 10)) # swipe to roughly the center of the next toggle after each case + + def interact_keyboard() -> None: + """Interact with the keyboard in various ways to test different actions and states. + Assumes it's a password keyboard with 8 characters required. Closes by pressing confirm at the end.""" + KEY = (250, 160) # key in the middle of the keyboard ('G') + SHIFT = (50, 210) + NUMBERS = (480, 210) + SPACE = (500, 160) + BACKSPACE = (490, 30) + CONFIRM = (50, 30) + # Begin interactions + press(*CONFIRM, wait_after=FAST_CLICK) # confirm while disabled should do nothing + swipe_left(duration_frames=FPS // 2) # swipe to type + swipe_up(duration_frames=FPS // 2) # swipe out of keyboard (nothing typed) + # press various keys to test different states: + for key in [ + SHIFT, KEY, KEY, SHIFT, SHIFT, KEY, KEY, # test casing (upper, lower, caps lock) + SPACE, SPACE, BACKSPACE, BACKSPACE, # test multiple space and backspace + NUMBERS, KEY, center, SHIFT, KEY # test numbers and symbols + ]: + press(*key, wait_after=FAST_CLICK) + # press confirm to close + script.wait(WAIT_SHORT) # wait for confirm to enable + press(*CONFIRM) + + toggle_cases: Cases = [ + lambda: click(times=3, wait_after=FAST_CLICK), # first toggle is personality, which has 3 states + None, None, None, None, None, None, # skip other toggles to save time + lambda: click(times=2, wait_after=FAST_CLICK), # test final toggle (enable openpilot) + ] + + network_cases: Cases = [ + explore_setting, # select wifi (just open and close) + None, None, + lambda: run_actions(click, interact_keyboard), # tether password keyboard + ] + + device_cases: Cases = [ + None, + click, # update + explore_setting, # pairing (just open and close) + lambda: explore_setting( + # training guide + lambda: swipe_left(width * 2), click, # first page, click next + lambda: swipe_left(width * 2), swipe_down # second page, go back (TODO: make driver cam preview work) + ), + None, # TODO: preview driver camera; enabling this causes MultiplePublishersError later in onroad alert tests + lambda: explore_setting(swipe_left), # terms & conditions (swipe to view QR code) + lambda: explore_setting(lambda: swipe_up(height * 3), lambda: swipe_down(height * 3)), # regulatory info + lambda: run_actions(click, lambda: swipe_left(width)), # reset calibration confirm (goes back automatically) + lambda: explore_setting(lambda: swipe_left(width)), # uninstall + lambda: run_actions( + lambda: explore_setting(lambda: swipe_left(width)), # reboot + lambda: script.click(430, 120), lambda: swipe_left(width), swipe_down, # shutdown + ), + ] + + developer_cases: Cases = [ + lambda: click(times=2, wait_after=FAST_CLICK), # toggle ssh mode + explore_setting, # SSH keys keyboard (just open and close) + None, # joystick mode + lambda: click(wait_after=FAST_CLICK), # longitudinal maneuver mode (disabled; should do nothing) + lambda: click(times=2, wait_after=FAST_CLICK), # toggle UI debug mode + ] + + settings_cases: Cases = [ + lambda: scroll_through_cases(toggle_cases), + lambda: scroll_through_cases(network_cases), + lambda: scroll_through_cases(device_cases), + lambda: script.wait(WAIT_SHORT), # pairing + lambda: run_actions(lambda: swipe_up(height * 3), lambda: swipe_down(height * 3)), # firehose (scroll down and back up) + lambda: scroll_through_cases(developer_cases), + ] + + # === Homescreen === # + script.wait(WAIT_SHORT) + swipe_left(width, wait_after=WAIT_SHORT) # onroad screen + swipe_right(width, wait_after=WAIT_SHORT) # back to home + + # === Offroad Alerts === + def setup_offroad_alerts_and_refresh() -> None: + """Setup function to trigger offroad alerts and force a refresh on the alerts layout.""" + setup_offroad_alerts() + main_layout._alerts_layout.refresh() + + swipe_right(width, wait_after=WAIT_SHORT) # open alerts + script.setup(setup_offroad_alerts_and_refresh) # show alerts + swipe_up(height) # scroll alerts + swipe_left(width, wait_after=WAIT_SHORT) # close alerts + + # === Settings === # + click() # open settings + scroll_through_cases([lambda case=case: explore_setting(case) for case in settings_cases]) # explore settings + swipe_down() # back to home + + # === Onroad === + script.set_send(lambda: send_onroad(pm)) + swipe_left(width, wait_after=WAIT_SHORT) # onroad screen + test_onroad_alerts(script, pm) + swipe_right(width) # back to home - # TODO: Explore more - script.wait(FPS) - script.click(*center, FPS) # Open settings - script.click(*center, FPS) # Open toggles script.end() @@ -171,34 +388,104 @@ def build_tizi_script(pm: PubMaster, main_layout, script: Script) -> None: return setup + def add_prime_state_setup(prime_type: PrimeType) -> None: + script.set_send(lambda: set_prime_state(prime_type)) + + def do_onboarding() -> None: + """Click through the training guide and close.""" + from openpilot.selfdrive.ui.layouts.onboarding import STEP_RECTS + step = 0 + for step_rect in STEP_RECTS: + if step < len(STEP_RECTS) - 1: + script.click(int(step_rect.x), int(step_rect.y), wait_after=FAST_CLICK) + else: + script.click(950, 900) # On the last step, click Finish instead of restart + step += 1 + + def type_keyboard() -> None: + """Types 8 characters using the big keyboard to test different layouts and interactions.""" + KEY = (150, 430) # e.g. 'Q' key + SHIFT = (150, 750) # also symbols key in number mode + NUMBERS = (150, 950) + SPACE = (1060, 950) + BACKSPACE = (2000, 780) + for key in [ + SHIFT, KEY, KEY, SHIFT, SHIFT, KEY, KEY, # test casing (upper, lower, caps lock) + SPACE, SPACE, BACKSPACE, BACKSPACE, # test multiple space and backspace + NUMBERS, KEY, KEY, SHIFT, KEY, KEY # test numbers and symbols + ]: + script.click(*key, wait_after=FAST_CLICK) + # TODO: Better way of organizing the events # === Homescreen === script.set_send(make_network_state_setup(pm, log.DeviceState.NetworkType.wifi)) - - # === Offroad Alerts (auto-transitions via HomeLayout refresh) === - script.setup(make_home_refresh_setup(setup_offroad_alerts)) + # Go through different prime state layouts + add_prime_state_setup(PrimeType.LITE) + add_prime_state_setup(PrimeType.NONE) + add_prime_state_setup(PrimeType.UNPAIRED) # === Update Available (auto-transitions via HomeLayout refresh) === script.setup(make_home_refresh_setup(setup_update_available)) - # === Settings - Device (click sidebar settings button) === + # === Offroad Alerts (auto-transitions via HomeLayout refresh, overrides update) === + script.setup(make_home_refresh_setup(setup_offroad_alerts)) + script.click(620, 950) # close alerts + + # === Settings (click sidebar settings button) === script.click(150, 90) - script.click(1985, 790) # reset calibration confirmation - script.click(650, 750) # cancel + + # === Settings - Device === + # pair device + script.click(2000, 450) # pair device + script.click(110, 110) # close pairing dialog + add_prime_state_setup(PrimeType.NONE) # changed from unpaired to hide pair device button + # calibration + script.setup(setup_calibration_params, wait_after=0) + script.click(1000, 620) # expand calibration description + script.click(2000, 620) # reset calibration confirmation + script.click(1500, 750) # confirm reset + script.click(1000, 620) # collapse calibration description + # training guide + script.click(2000, 800) # open training guide + do_onboarding() + # regulatory info + script.click(2000, 970) # regulatory button + script.click(2000, 970) # OK # === Settings - Network === script.click(278, 450) + # TODO: mock networks script.click(1880, 100) # advanced network settings - script.click(630, 80) # back + + # Keyboard (tethering password) + script.click(2000, 420, wait_after=FAST_CLICK) # open tether password keyboard + script.click(2000, 950, wait_after=FAST_CLICK) # click confirm (disabled, should not close) + script.click(2000, 115) # cancel (close without typing) + script.click(2000, 420, wait_after=FAST_CLICK) # open keyboard again + type_keyboard() # test various keyboard layouts and interactions + script.click(2050, 250, wait_after=FAST_CLICK) # toggle show/hide password + script.click(2000, 950) # confirm (close keyboard) + + script.click(630, 80) # back from advanced network # === Settings - Toggles === script.click(278, 600) - script.click(1200, 280) # experimental mode description + script.click(1200, 280) # expand experimental mode description # === Settings - Software === - script.setup(put_update_params, wait_after=0) - script.click(278, 720) + script.setup(lambda: setup_update_available(False), wait_after=0) # start with no update available + script.click(278, 720) # software + for _ in range(2): + script.click(720, 120) # toggle current release notes + script.setup(setup_update_available) # set update available + for _ in range(2): + script.click(720, 450) # toggle new release notes + script.click(2000, 630) # open select branch dialog + script.click(1000, 300) # select 1st option + script.click(1600, 900) # confirm selection + script.click(2000, 800) # uninstall + script.click(650, 750) # cancel uninstall # === Settings - Firehose === script.click(278, 845) @@ -206,31 +493,18 @@ def build_tizi_script(pm: PubMaster, main_layout, script: Script) -> None: # === Settings - Developer (set CarParamsPersistent first) === script.setup(setup_developer_params, wait_after=0) script.click(278, 950) + script.click(1930, 470) # SSH keys (keyboard) + script.click(1930, 115) # click cancel on keyboard script.click(2000, 960) # toggle alpha long script.click(1500, 875) # confirm - # === Keyboard modal (SSH keys button in developer panel) === - script.click(1930, 470) # click SSH keys - script.click(1930, 115) # click cancel on keyboard - # === Close settings === script.click(250, 160) # === Onroad === script.set_send(lambda: send_onroad(pm)) script.click(1000, 500) # click onroad to toggle sidebar - - # === Onroad alerts === - # Small alert (normal) - script.set_send(make_alert_setup(pm, AlertSize.small, "Small Alert", "This is a small alert", AlertStatus.normal)) - # Medium alert (userPrompt) - script.set_send(make_alert_setup(pm, AlertSize.mid, "Medium Alert", "This is a medium alert", AlertStatus.userPrompt)) - # Full alert (critical) - script.set_send(make_alert_setup(pm, AlertSize.full, "DISENGAGE IMMEDIATELY", "Driver Distracted", AlertStatus.critical)) - # Full alert multiline - script.set_send(make_alert_setup(pm, AlertSize.full, "Reverse\nGear", "", AlertStatus.normal)) - # Full alert long text - script.set_send(make_alert_setup(pm, AlertSize.full, "TAKE CONTROL IMMEDIATELY", "Calibration Invalid: Remount Device & Recalibrate", AlertStatus.userPrompt)) + test_onroad_alerts(script, pm) # End script.end() diff --git a/selfdrive/ui/translations/app.pot b/selfdrive/ui/translations/app.pot index abb6940a54..468ff35fd9 100644 --- a/selfdrive/ui/translations/app.pot +++ b/selfdrive/ui/translations/app.pot @@ -8,7 +8,7 @@ msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2025-10-23 00:51-0700\n" +"POT-Creation-Date: 2026-03-09 14:21+0000\n" "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" "Last-Translator: FULL NAME \n" "Language-Team: LANGUAGE \n" @@ -18,1113 +18,1018 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=INTEGER; plural=EXPRESSION;\n" -#: system/ui/widgets/html_render.py:263 system/ui/widgets/confirm_dialog.py:93 -#: selfdrive/ui/layouts/sidebar.py:127 -#, python-format -msgid "OK" -msgstr "" - -#: system/ui/widgets/confirm_dialog.py:23 system/ui/widgets/option_dialog.py:35 -#: system/ui/widgets/keyboard.py:81 system/ui/widgets/network.py:318 -#, python-format -msgid "Cancel" -msgstr "" - -#: system/ui/widgets/option_dialog.py:36 -#, python-format -msgid "Select" -msgstr "" - -#: system/ui/widgets/network.py:74 system/ui/widgets/network.py:95 +#: system/ui/widgets/network.py:92 +#: system/ui/widgets/network.py:74 #, python-format msgid "Advanced" msgstr "" -#: system/ui/widgets/network.py:99 selfdrive/ui/layouts/onboarding.py:147 +#: system/ui/widgets/network.py:96 +#: openpilot/selfdrive/ui/layouts/onboarding.py:151 #, python-format msgid "Back" msgstr "" -#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:201 +#, python-format +msgid "Enter APN" +msgstr "" + +#: system/ui/widgets/network.py:201 +#, python-format +msgid "leave blank for automatic configuration" +msgstr "" + +#: system/ui/widgets/network.py:243 +#, python-format +msgid "Enter SSID" +msgstr "" + +#: system/ui/widgets/network.py:257 +#, python-format +msgid "Enter new tethering password" +msgstr "" + +#: system/ui/widgets/network.py:117 #, python-format msgid "Enable Tethering" msgstr "" -#: system/ui/widgets/network.py:123 system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:136 #, python-format msgid "EDIT" msgstr "" -#: system/ui/widgets/network.py:124 +#: system/ui/widgets/network.py:121 #, python-format msgid "Tethering Password" msgstr "" -#: system/ui/widgets/network.py:129 +#: system/ui/widgets/network.py:126 #, python-format msgid "Enable Roaming" msgstr "" -#: system/ui/widgets/network.py:134 +#: system/ui/widgets/network.py:131 #, python-format msgid "Cellular Metered" msgstr "" -#: system/ui/widgets/network.py:135 +#: system/ui/widgets/network.py:136 +#, python-format +msgid "APN Setting" +msgstr "" + +#: system/ui/widgets/network.py:141 +#, python-format +msgid "Wi-Fi Network Metered" +msgstr "" + +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:320 +#, python-format +msgid "Enter password" +msgstr "" + +#: system/ui/widgets/network.py:316 +#, python-format +msgid "Scanning Wi-Fi networks..." +msgstr "" + +#: system/ui/widgets/network.py:376 +#, python-format +msgid "CONNECTING..." +msgstr "" + +#: system/ui/widgets/network.py:458 +#: system/ui/widgets/network.py:326 +#, python-format +msgid "Forget" +msgstr "" + +#: system/ui/widgets/network.py:132 #, python-format msgid "Prevent large data uploads when on a metered cellular connection" msgstr "" #: system/ui/widgets/network.py:139 #, python-format -msgid "APN Setting" -msgstr "" - -#: system/ui/widgets/network.py:142 -#, python-format msgid "default" msgstr "" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "metered" msgstr "" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "unmetered" msgstr "" -#: system/ui/widgets/network.py:144 -#, python-format -msgid "Wi-Fi Network Metered" -msgstr "" - -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Prevent large data uploads when on a metered Wi-Fi connection" msgstr "" -#: system/ui/widgets/network.py:150 +#: system/ui/widgets/network.py:147 #, python-format msgid "IP Address" msgstr "" -#: system/ui/widgets/network.py:155 +#: system/ui/widgets/network.py:152 #, python-format msgid "Hidden Network" msgstr "" -#: system/ui/widgets/network.py:155 selfdrive/ui/layouts/sidebar.py:73 -#: selfdrive/ui/layouts/sidebar.py:134 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:138 +#: system/ui/widgets/network.py:152 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 #, python-format msgid "CONNECT" msgstr "" -#: system/ui/widgets/network.py:204 -#, python-format -msgid "Enter APN" -msgstr "" - -#: system/ui/widgets/network.py:204 -#, python-format -msgid "leave blank for automatic configuration" -msgstr "" - -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 -#, python-format -msgid "Enter password" -msgstr "" - -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 -#, python-format -msgid "for \"{}\"" -msgstr "" - -#: system/ui/widgets/network.py:241 -#, python-format -msgid "Enter SSID" -msgstr "" - -#: system/ui/widgets/network.py:254 -#, python-format -msgid "Enter new tethering password" -msgstr "" - -#: system/ui/widgets/network.py:310 -#, python-format -msgid "Scanning Wi-Fi networks..." -msgstr "" - -#: system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:320 #, python-format msgid "Wrong password" msgstr "" -#: system/ui/widgets/network.py:318 system/ui/widgets/network.py:451 +#: system/ui/widgets/network.py:326 +#: system/ui/widgets/confirm_dialog.py:24 +#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/keyboard.py:83 #, python-format -msgid "Forget" +msgid "Cancel" msgstr "" -#: system/ui/widgets/network.py:319 -#, python-format -msgid "Forget Wi-Fi Network \"{}\"?" -msgstr "" - -#: system/ui/widgets/network.py:369 -#, python-format -msgid "CONNECTING..." -msgstr "" - -#: system/ui/widgets/network.py:373 +#: system/ui/widgets/network.py:380 #, python-format msgid "FORGETTING..." msgstr "" -#: system/ui/widgets/list_view.py:123 system/ui/widgets/list_view.py:160 +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:321 +#, python-format +msgid "for \"{}\"" +msgstr "" + +#: system/ui/widgets/network.py:327 +#, python-format +msgid "Forget Wi-Fi Network \"{}\"?" +msgstr "" + +#: system/ui/widgets/confirm_dialog.py:93 +#: system/ui/widgets/html_render.py:263 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 +#, python-format +msgid "OK" +msgstr "" + +#: system/ui/widgets/option_dialog.py:37 +#, python-format +msgid "Select" +msgstr "" + +#: system/ui/widgets/list_view.py:123 +#: system/ui/widgets/list_view.py:160 #, python-format msgid "Error" msgstr "" -#: selfdrive/ui/widgets/pairing_dialog.py:103 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:92 #, python-format msgid "Pair your device to your comma account" msgstr "" -#: selfdrive/ui/widgets/pairing_dialog.py:128 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:117 #, python-format msgid "Go to https://connect.comma.ai on your phone" msgstr "" -#: selfdrive/ui/widgets/pairing_dialog.py:129 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:118 #, python-format msgid "Click \"add new device\" and scan the QR code on the right" msgstr "" -#: selfdrive/ui/widgets/pairing_dialog.py:130 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:119 #, python-format msgid "Bookmark connect.comma.ai to your home screen to use it like an app" msgstr "" -#: selfdrive/ui/widgets/pairing_dialog.py:161 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:150 #, python-format msgid "QR Code Error" msgstr "" -#: selfdrive/ui/widgets/ssh_key.py:29 -msgid "LOADING" -msgstr "" - -#: selfdrive/ui/widgets/ssh_key.py:30 -msgid "ADD" -msgstr "" - -#: selfdrive/ui/widgets/ssh_key.py:31 -msgid "REMOVE" -msgstr "" - -#: selfdrive/ui/widgets/ssh_key.py:89 +#: openpilot/selfdrive/ui/widgets/setup.py:47 +#: openpilot/selfdrive/ui/layouts/settings/device.py:23 #, python-format -msgid "Enter your GitHub username" +msgid "Pair your device with comma connect (connect.comma.ai) and claim your comma prime offer." msgstr "" -#: selfdrive/ui/widgets/ssh_key.py:114 +#: openpilot/selfdrive/ui/widgets/setup.py:74 #, python-format -msgid "No SSH keys found" +msgid "Maximize your training data uploads to improve openpilot's driving models." msgstr "" -#: selfdrive/ui/widgets/ssh_key.py:123 -#, python-format -msgid "Request timed out" -msgstr "" - -#: selfdrive/ui/widgets/ssh_key.py:126 -#, python-format -msgid "No SSH keys found for user '{}'" -msgstr "" - -#: selfdrive/ui/widgets/prime.py:33 -#, python-format -msgid "Upgrade Now" -msgstr "" - -#: selfdrive/ui/widgets/prime.py:38 -#, python-format -msgid "Become a comma prime member at connect.comma.ai" -msgstr "" - -#: selfdrive/ui/widgets/prime.py:44 -#, python-format -msgid "PRIME FEATURES:" -msgstr "" - -#: selfdrive/ui/widgets/prime.py:47 -#, python-format -msgid "Remote access" -msgstr "" - -#: selfdrive/ui/widgets/prime.py:47 -#, python-format -msgid "24/7 LTE connectivity" -msgstr "" - -#: selfdrive/ui/widgets/prime.py:47 -#, python-format -msgid "1 year of drive storage" -msgstr "" - -#: selfdrive/ui/widgets/prime.py:47 -#, python-format -msgid "Remote snapshots" -msgstr "" - -#: selfdrive/ui/widgets/prime.py:62 -#, python-format -msgid "✓ SUBSCRIBED" -msgstr "" - -#: selfdrive/ui/widgets/prime.py:63 -#, python-format -msgid "comma prime" -msgstr "" - -#: selfdrive/ui/widgets/exp_mode_button.py:50 -#, python-format -msgid "EXPERIMENTAL MODE ON" -msgstr "" - -#: selfdrive/ui/widgets/exp_mode_button.py:50 -#, python-format -msgid "CHILL MODE ON" -msgstr "" - -#: selfdrive/ui/widgets/offroad_alerts.py:104 -#, python-format -msgid "Close" -msgstr "" - -#: selfdrive/ui/widgets/offroad_alerts.py:106 -#, python-format -msgid "Snooze Update" -msgstr "" - -#: selfdrive/ui/widgets/offroad_alerts.py:109 -#, python-format -msgid "Acknowledge Excessive Actuation" -msgstr "" - -#: selfdrive/ui/widgets/offroad_alerts.py:112 -#, python-format -msgid "Reboot and Update" -msgstr "" - -#: selfdrive/ui/widgets/offroad_alerts.py:320 -#, python-format -msgid "No release notes available." -msgstr "" - -#: selfdrive/ui/widgets/setup.py:19 -#, python-format -msgid "Pair device" -msgstr "" - -#: selfdrive/ui/widgets/setup.py:20 -#, python-format -msgid "Open" -msgstr "" - -#: selfdrive/ui/widgets/setup.py:22 -#, python-format -msgid "🔥 Firehose Mode 🔥" -msgstr "" - -#: selfdrive/ui/widgets/setup.py:44 +#: openpilot/selfdrive/ui/widgets/setup.py:43 #, python-format msgid "Finish Setup" msgstr "" -#: selfdrive/ui/widgets/setup.py:48 selfdrive/ui/layouts/settings/device.py:24 +#: openpilot/selfdrive/ui/widgets/setup.py:18 #, python-format -msgid "" -"Pair your device with comma connect (connect.comma.ai) and claim your comma " -"prime offer." +msgid "Pair device" msgstr "" -#: selfdrive/ui/widgets/setup.py:75 +#: openpilot/selfdrive/ui/widgets/setup.py:19 #, python-format -msgid "" -"Maximize your training data uploads to improve openpilot's driving models." +msgid "Open" msgstr "" -#: selfdrive/ui/widgets/setup.py:91 +#: openpilot/selfdrive/ui/widgets/setup.py:21 +#, python-format +msgid "🔥 Firehose Mode 🔥" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/setup.py:91 #, python-format msgid "Please connect to Wi-Fi to complete initial pairing" msgstr "" -#: selfdrive/ui/layouts/home.py:155 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:29 +msgid "LOADING" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/ssh_key.py:30 +msgid "ADD" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/ssh_key.py:31 +msgid "REMOVE" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/ssh_key.py:89 +#, python-format +msgid "Enter your GitHub username" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/ssh_key.py:124 +#, python-format +msgid "Request timed out" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/ssh_key.py:115 +#, python-format +msgid "No SSH keys found" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/ssh_key.py:127 +#, python-format +msgid "No SSH keys found for user '{}'" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:33 +#, python-format +msgid "Upgrade Now" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:44 +#, python-format +msgid "PRIME FEATURES:" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:47 +#, python-format +msgid "Remote access" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:47 +#, python-format +msgid "24/7 LTE connectivity" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:47 +#, python-format +msgid "1 year of drive storage" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:47 +#, python-format +msgid "Remote snapshots" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:62 +#, python-format +msgid "✓ SUBSCRIBED" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:63 +#, python-format +msgid "comma prime" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:38 +#, python-format +msgid "Become a comma prime member at connect.comma.ai" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 +#, python-format +msgid "EXPERIMENTAL MODE ON" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 +#, python-format +msgid "CHILL MODE ON" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:104 +#, python-format +msgid "Close" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:106 +#, python-format +msgid "Snooze Update" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:109 +#, python-format +msgid "Acknowledge Excessive Actuation" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:112 +#, python-format +msgid "Reboot and Update" +msgstr "" + +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:321 +#, python-format +msgid "No release notes available." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:43 +msgid "--" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:44 +msgid "Wi-Fi" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:45 +msgid "ETH" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:46 +msgid "2G" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:47 +msgid "3G" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:48 +msgid "LTE" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:49 +msgid "5G" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 +msgid "TEMP" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 +msgid "GOOD" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 +msgid "VEHICLE" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 +msgid "ONLINE" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 +msgid "OFFLINE" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:117 +msgid "Unknown" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 +msgid "NO" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 +msgid "PANDA" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 +msgid "HIGH" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 +msgid "ERROR" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/home.py:155 #, python-format msgid "UPDATE" msgstr "" -#: selfdrive/ui/layouts/home.py:169 +#: openpilot/selfdrive/ui/layouts/home.py:169 #, python-format msgid "{} ALERT" msgid_plural "{} ALERTS" msgstr[0] "" msgstr[1] "" -#: selfdrive/ui/layouts/sidebar.py:43 -msgid "--" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:44 -msgid "Wi-Fi" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:45 -msgid "ETH" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:46 -msgid "2G" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:47 -msgid "3G" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:48 -msgid "LTE" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:49 -msgid "5G" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 -#: selfdrive/ui/layouts/sidebar.py:127 selfdrive/ui/layouts/sidebar.py:129 -msgid "TEMP" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 -msgid "GOOD" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:144 -msgid "VEHICLE" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:144 -msgid "ONLINE" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:73 selfdrive/ui/layouts/sidebar.py:134 -msgid "OFFLINE" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:117 -msgid "Unknown" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:129 -msgid "HIGH" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:138 -msgid "ERROR" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:142 -msgid "NO" -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:142 -msgid "PANDA" -msgstr "" - -#: selfdrive/ui/layouts/onboarding.py:111 +#: openpilot/selfdrive/ui/layouts/onboarding.py:115 #, python-format msgid "Welcome to openpilot" msgstr "" -#: selfdrive/ui/layouts/onboarding.py:112 +#: openpilot/selfdrive/ui/layouts/onboarding.py:116 #, python-format -msgid "" -"You must accept the Terms and Conditions to use openpilot. Read the latest " -"terms at https://comma.ai/terms before continuing." +msgid "You must accept the Terms and Conditions to use openpilot. Read the latest terms at https://comma.ai/terms before continuing." msgstr "" -#: selfdrive/ui/layouts/onboarding.py:115 +#: openpilot/selfdrive/ui/layouts/onboarding.py:119 #, python-format msgid "Decline" msgstr "" -#: selfdrive/ui/layouts/onboarding.py:116 +#: openpilot/selfdrive/ui/layouts/onboarding.py:120 #, python-format msgid "Agree" msgstr "" -#: selfdrive/ui/layouts/onboarding.py:145 +#: openpilot/selfdrive/ui/layouts/onboarding.py:149 #, python-format msgid "You must accept the Terms and Conditions in order to use openpilot." msgstr "" -#: selfdrive/ui/layouts/onboarding.py:148 +#: openpilot/selfdrive/ui/layouts/onboarding.py:152 #, python-format msgid "Decline, uninstall openpilot" msgstr "" -#: selfdrive/ui/layouts/settings/firehose.py:18 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:20 +msgid "When enabled, pressing the accelerator pedal will disengage openpilot." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:30 +msgid "Enable driver monitoring even when openpilot is not engaged." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:31 +msgid "Upload data from the driver facing camera and help improve the driver monitoring algorithm." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:32 +msgid "Display speed in km/h instead of mph." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:33 +msgid "Record and store microphone audio while driving. The audio will be included in the dashcam video in comma connect." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:96 +#, python-format +msgid "Driving Personality" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:125 +#, python-format +msgid "Changing this setting will restart openpilot if the car is powered on." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:182 +#, python-format +msgid "Experimental mode is currently unavailable on this car since the car's stock ACC is used for longitudinal control." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:229 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:180 +#, python-format +msgid "Enable" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:46 +#, python-format +msgid "Enable openpilot" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:52 +#, python-format +msgid "Experimental Mode" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:58 +#, python-format +msgid "Disengage on Accelerator Pedal" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:64 +#, python-format +msgid "Enable Lane Departure Warnings" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:70 +#, python-format +msgid "Always-On Driver Monitoring" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:76 +#, python-format +msgid "Record and Upload Driver Camera" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:82 +#, python-format +msgid "Record and Upload Microphone Audio" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:88 +#, python-format +msgid "Use Metric System" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:184 +#, python-format +msgid "openpilot longitudinal control may come in a future update." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 +#, python-format +msgid "Aggressive" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 +#, python-format +msgid "Standard" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 +#, python-format +msgid "Relaxed" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:190 +#, python-format +msgid "Enable the openpilot longitudinal control (alpha) toggle to allow Experimental mode." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/settings.py:59 +msgid "Device" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/settings.py:60 +msgid "Network" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/settings.py:61 +msgid "Toggles" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/settings.py:62 +msgid "Software" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/settings.py:63 +msgid "Firehose" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/settings.py:64 +msgid "Developer" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:24 +msgid "Preview the driver facing camera to ensure that driver monitoring has good visibility. (vehicle must be off)" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:25 +msgid "openpilot requires the device to be mounted within 4° left or right and within 5° up or 9° down." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:26 +msgid "Review the rules, features, and limitations of openpilot" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:89 +#, python-format +msgid "Select a language" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 +#, python-format +msgid "Are you sure you want to reset calibration?" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 +#, python-format +msgid "Reset" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:140 +#, python-format +msgid "

Steering lag calibration is complete." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 +#, python-format +msgid "Are you sure you want to reboot?" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 +#, python-format +msgid "Reboot" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 +#, python-format +msgid "Are you sure you want to power off?" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 +#, python-format +msgid "Power Off" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 +#, python-format +msgid "Pair Device" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 +#, python-format +msgid "PAIR" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 +#, python-format +msgid "Reset Calibration" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 +#, python-format +msgid "RESET" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 +#, python-format +msgid "Dongle ID" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 +#, python-format +msgid "Serial" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 +#, python-format +msgid "Driver Camera" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 +#, python-format +msgid "PREVIEW" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 +#, python-format +msgid "Review Training Guide" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 +#, python-format +msgid "REVIEW" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 +#, python-format +msgid "Regulatory" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 +#, python-format +msgid "VIEW" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 +#, python-format +msgid "Change Language" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 +#, python-format +msgid "CHANGE" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:95 +#, python-format +msgid "Disengage to Reset Calibration" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:138 +#, python-format +msgid "

Steering lag calibration is {}% complete." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:164 +#, python-format +msgid "Disengage to Reboot" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:176 +#, python-format +msgid "Disengage to Power Off" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 +#, python-format +msgid "N/A" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:152 +#, python-format +msgid " Steering torque response calibration is complete." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 +#, python-format +msgid " Your device is pointed {:.1f}° {} and {:.1f}° {}." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 +#, python-format +msgid "down" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 +#, python-format +msgid "up" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 +#, python-format +msgid "left" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 +#, python-format +msgid "right" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/device.py:150 +#, python-format +msgid " Steering torque response calibration is {}% complete." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:10 msgid "Firehose Mode" msgstr "" -#: selfdrive/ui/layouts/settings/firehose.py:20 -msgid "" -"openpilot learns to drive by watching humans, like you, drive.\n" -"\n" -"Firehose Mode allows you to maximize your training data uploads to improve " -"openpilot's driving models. More data means bigger models, which means " -"better Experimental Mode." -msgstr "" - -#: selfdrive/ui/layouts/settings/firehose.py:25 -msgid "" -"For maximum effectiveness, bring your device inside and connect to a good " -"USB-C adapter and Wi-Fi weekly.\n" -"\n" -"Firehose Mode can also work while you're driving if connected to a hotspot " -"or unlimited SIM card.\n" -"\n" -"\n" -"Frequently Asked Questions\n" -"\n" -"Does it matter how or where I drive? Nope, just drive as you normally " -"would.\n" -"\n" -"Do all of my segments get pulled in Firehose Mode? No, we selectively pull a " -"subset of your segments.\n" -"\n" -"What's a good USB-C adapter? Any fast phone or laptop charger should be " -"fine.\n" -"\n" -"Does it matter which software I run? Yes, only upstream openpilot (and " -"particular forks) are able to be used for training." -msgstr "" - -#: selfdrive/ui/layouts/settings/firehose.py:111 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:70 #, python-format msgid "{} segment of your driving is in the training dataset so far." msgid_plural "{} segments of your driving is in the training dataset so far." msgstr[0] "" msgstr[1] "" -#: selfdrive/ui/layouts/settings/firehose.py:138 +#: openpilot/selfdrive/ui/layouts/settings/software.py:19 #, python-format -msgid "ACTIVE" +msgid "checking..." msgstr "" -#: selfdrive/ui/layouts/settings/firehose.py:140 +#: openpilot/selfdrive/ui/layouts/settings/software.py:20 #, python-format -msgid "INACTIVE: connect to an unmetered network" +msgid "downloading..." msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:15 -msgid "" -"ADB (Android Debug Bridge) allows connecting to your device over USB or over " -"the network. See https://docs.comma.ai/how-to/connect-to-comma for more info." -msgstr "" - -#: selfdrive/ui/layouts/settings/developer.py:19 -msgid "" -"Warning: This grants SSH access to all public keys in your GitHub settings. " -"Never enter a GitHub username other than your own. A comma employee will " -"NEVER ask you to add their GitHub username." -msgstr "" - -#: selfdrive/ui/layouts/settings/developer.py:23 -msgid "" -"WARNING: openpilot longitudinal control is in alpha for this car and will " -"disable Automatic Emergency Braking (AEB).

On this car, openpilot " -"defaults to the car's built-in ACC instead of openpilot's longitudinal " -"control. Enable this to switch to openpilot longitudinal control. Enabling " -"Experimental mode is recommended when enabling openpilot longitudinal " -"control alpha. Changing this setting will restart openpilot if the car is " -"powered on." -msgstr "" - -#: selfdrive/ui/layouts/settings/developer.py:39 +#: openpilot/selfdrive/ui/layouts/settings/software.py:21 #, python-format -msgid "Enable ADB" +msgid "finalizing update..." msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:48 -#, python-format -msgid "Enable SSH" -msgstr "" - -#: selfdrive/ui/layouts/settings/developer.py:53 -#, python-format -msgid "SSH Keys" -msgstr "" - -#: selfdrive/ui/layouts/settings/developer.py:56 -#, python-format -msgid "Joystick Debug Mode" -msgstr "" - -#: selfdrive/ui/layouts/settings/developer.py:64 -#, python-format -msgid "Longitudinal Maneuver Mode" -msgstr "" - -#: selfdrive/ui/layouts/settings/developer.py:71 -#, python-format -msgid "openpilot Longitudinal Control (Alpha)" -msgstr "" - -#: selfdrive/ui/layouts/settings/developer.py:166 -#: selfdrive/ui/layouts/settings/toggles.py:228 -#, python-format -msgid "Enable" -msgstr "" - -#: selfdrive/ui/layouts/settings/software.py:20 +#: openpilot/selfdrive/ui/layouts/settings/software.py:27 #, python-format msgid "never" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:31 +#: openpilot/selfdrive/ui/layouts/settings/software.py:38 #, python-format msgid "now" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:34 +#: openpilot/selfdrive/ui/layouts/settings/software.py:157 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 +#: openpilot/selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:128 +#, python-format +msgid "CHECK" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 +#, python-format +msgid "Are you sure you want to uninstall?" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 +#, python-format +msgid "Uninstall" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:203 +#, python-format +msgid "Select a branch" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:41 #, python-format msgid "{} minute ago" msgid_plural "{} minutes ago" msgstr[0] "" msgstr[1] "" -#: selfdrive/ui/layouts/settings/software.py:37 +#: openpilot/selfdrive/ui/layouts/settings/software.py:44 #, python-format msgid "{} hour ago" msgid_plural "{} hours ago" msgstr[0] "" msgstr[1] "" -#: selfdrive/ui/layouts/settings/software.py:40 +#: openpilot/selfdrive/ui/layouts/settings/software.py:47 #, python-format msgid "{} day ago" msgid_plural "{} days ago" msgstr[0] "" msgstr[1] "" -#: selfdrive/ui/layouts/settings/software.py:48 +#: openpilot/selfdrive/ui/layouts/settings/software.py:55 #, python-format msgid "Updates are only downloaded while the car is off." msgstr "" -#: selfdrive/ui/layouts/settings/software.py:49 +#: openpilot/selfdrive/ui/layouts/settings/software.py:56 #, python-format msgid "Current Version" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:50 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 #, python-format msgid "Download" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:50 -#: selfdrive/ui/layouts/settings/software.py:107 -#: selfdrive/ui/layouts/settings/software.py:118 -#: selfdrive/ui/layouts/settings/software.py:147 -#, python-format -msgid "CHECK" -msgstr "" - -#: selfdrive/ui/layouts/settings/software.py:53 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 #, python-format msgid "Install Update" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:53 -#: selfdrive/ui/layouts/settings/software.py:136 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 +#: openpilot/selfdrive/ui/layouts/settings/software.py:146 #, python-format msgid "INSTALL" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "Target Branch" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "SELECT" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:72 -#: selfdrive/ui/layouts/settings/software.py:163 -#, python-format -msgid "Uninstall" -msgstr "" - -#: selfdrive/ui/layouts/settings/software.py:72 -#, python-format -msgid "UNINSTALL" -msgstr "" - -#: selfdrive/ui/layouts/settings/software.py:106 +#: openpilot/selfdrive/ui/layouts/settings/software.py:116 #, python-format msgid "failed to check for update" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:109 +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 +#, python-format +msgid "UNINSTALL" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:119 #, python-format msgid "update available" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:110 +#: openpilot/selfdrive/ui/layouts/settings/software.py:120 #, python-format msgid "DOWNLOAD" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:115 -#, python-format -msgid "up to date, last checked {}" -msgstr "" - -#: selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:127 #, python-format msgid "up to date, last checked never" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:125 #, python-format -msgid "Are you sure you want to uninstall?" +msgid "up to date, last checked {}" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:183 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:39 #, python-format -msgid "Select a branch" +msgid "Enable ADB" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:25 -msgid "" -"Preview the driver facing camera to ensure that driver monitoring has good " -"visibility. (vehicle must be off)" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:26 -msgid "" -"openpilot requires the device to be mounted within 4° left or right and " -"within 5° up or 9° down." -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:27 -msgid "Review the rules, features, and limitations of openpilot" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:48 #, python-format -msgid "Pair Device" +msgid "Enable SSH" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:53 #, python-format -msgid "PAIR" +msgid "SSH Keys" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:56 #, python-format -msgid "Reset Calibration" +msgid "Joystick Debug Mode" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:64 #, python-format -msgid "RESET" +msgid "Longitudinal Maneuver Mode" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:71 #, python-format -msgid "Reboot" +msgid "openpilot Longitudinal Control (Alpha)" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:79 #, python-format -msgid "Power Off" +msgid "UI Debug Mode" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:59 -#, python-format -msgid "Dongle ID" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:59 -#: selfdrive/ui/layouts/settings/device.py:60 -#, python-format -msgid "N/A" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:60 -#, python-format -msgid "Serial" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:62 -#, python-format -msgid "Driver Camera" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:62 -#, python-format -msgid "PREVIEW" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:65 -#, python-format -msgid "Review Training Guide" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:65 -#, python-format -msgid "REVIEW" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:67 -#, python-format -msgid "Regulatory" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:67 -#, python-format -msgid "VIEW" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:68 -#, python-format -msgid "Change Language" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:68 -#, python-format -msgid "CHANGE" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:91 -#, python-format -msgid "Select a language" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:103 -#, python-format -msgid "Disengage to Reset Calibration" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:119 -#, python-format -msgid "Are you sure you want to reset calibration?" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:119 -#, python-format -msgid "Reset" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:133 -#, python-format -msgid " Your device is pointed {:.1f}° {} and {:.1f}° {}." -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:133 -#, python-format -msgid "down" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:133 -#, python-format -msgid "up" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:134 -#, python-format -msgid "left" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:134 -#, python-format -msgid "right" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:146 -#, python-format -msgid "

Steering lag calibration is {}% complete." -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:148 -#, python-format -msgid "

Steering lag calibration is complete." -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:158 -#, python-format -msgid " Steering torque response calibration is {}% complete." -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:160 -#, python-format -msgid " Steering torque response calibration is complete." -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:165 -#, python-format -msgid "" -"openpilot is continuously calibrating, resetting is rarely required. " -"Resetting calibration will restart openpilot if the car is powered on." -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:172 -#, python-format -msgid "Disengage to Reboot" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:175 -#, python-format -msgid "Are you sure you want to reboot?" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:184 -#, python-format -msgid "Disengage to Power Off" -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:187 -#, python-format -msgid "Are you sure you want to power off?" -msgstr "" - -#: selfdrive/ui/layouts/settings/settings.py:62 -msgid "Device" -msgstr "" - -#: selfdrive/ui/layouts/settings/settings.py:63 -msgid "Network" -msgstr "" - -#: selfdrive/ui/layouts/settings/settings.py:64 -msgid "Toggles" -msgstr "" - -#: selfdrive/ui/layouts/settings/settings.py:65 -msgid "Software" -msgstr "" - -#: selfdrive/ui/layouts/settings/settings.py:66 -msgid "Firehose" -msgstr "" - -#: selfdrive/ui/layouts/settings/settings.py:67 -msgid "Developer" -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:17 -msgid "" -"Use the openpilot system for adaptive cruise control and lane keep driver " -"assistance. Your attention is required at all times to use this feature." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:20 -msgid "When enabled, pressing the accelerator pedal will disengage openpilot." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:22 -msgid "" -"Standard is recommended. In aggressive mode, openpilot will follow lead cars " -"closer and be more aggressive with the gas and brake. In relaxed mode " -"openpilot will stay further away from lead cars. On supported cars, you can " -"cycle through these personalities with your steering wheel distance button." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:27 -msgid "" -"Receive alerts to steer back into the lane when your vehicle drifts over a " -"detected lane line without a turn signal activated while driving over 31 mph " -"(50 km/h)." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:30 -msgid "Enable driver monitoring even when openpilot is not engaged." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:31 -msgid "" -"Upload data from the driver facing camera and help improve the driver " -"monitoring algorithm." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:32 -msgid "Display speed in km/h instead of mph." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:33 -msgid "" -"Record and store microphone audio while driving. The audio will be included " -"in the dashcam video in comma connect." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:46 -#, python-format -msgid "Enable openpilot" -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:52 -#, python-format -msgid "Experimental Mode" -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:58 -#, python-format -msgid "Disengage on Accelerator Pedal" -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:64 -#, python-format -msgid "Enable Lane Departure Warnings" -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:70 -#, python-format -msgid "Always-On Driver Monitoring" -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:76 -#, python-format -msgid "Record and Upload Driver Camera" -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:82 -#, python-format -msgid "Record and Upload Microphone Audio" -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:88 -#, python-format -msgid "Use Metric System" -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:96 -#, python-format -msgid "Driving Personality" -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:98 -#, python-format -msgid "Aggressive" -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:98 -#, python-format -msgid "Standard" -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:98 -#, python-format -msgid "Relaxed" -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:125 -#, python-format -msgid "Changing this setting will restart openpilot if the car is powered on." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:158 -#, python-format -msgid "" -"openpilot defaults to driving in chill mode. Experimental mode enables alpha-" -"level features that aren't ready for chill mode. Experimental features are " -"listed below:

End-to-End Longitudinal Control


Let the driving " -"model control the gas and brakes. openpilot will drive as it thinks a human " -"would, including stopping for red lights and stop signs. Since the driving " -"model decides the speed to drive, the set speed will only act as an upper " -"bound. This is an alpha quality feature; mistakes should be expected." -"

New Driving Visualization


The driving visualization will " -"transition to the road-facing wide-angle camera at low speeds to better show " -"some turns. The Experimental mode logo will also be shown in the top right " -"corner." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:181 -#, python-format -msgid "" -"Experimental mode is currently unavailable on this car since the car's stock " -"ACC is used for longitudinal control." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:183 -#, python-format -msgid "openpilot longitudinal control may come in a future update." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:186 -#, python-format -msgid "" -"An alpha version of openpilot longitudinal control can be tested, along with " -"Experimental mode, on non-release branches." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:189 -#, python-format -msgid "" -"Enable the openpilot longitudinal control (alpha) toggle to allow " -"Experimental mode." -msgstr "" - -#: selfdrive/ui/onroad/hud_renderer.py:148 -#, python-format -msgid "MAX" -msgstr "" - -#: selfdrive/ui/onroad/hud_renderer.py:177 -#, python-format -msgid "km/h" -msgstr "" - -#: selfdrive/ui/onroad/hud_renderer.py:177 -#, python-format -msgid "mph" -msgstr "" - -#: selfdrive/ui/onroad/driver_camera_dialog.py:34 -#, python-format -msgid "camera starting" -msgstr "" - -#: selfdrive/ui/onroad/alert_renderer.py:51 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:51 #, python-format msgid "openpilot Unavailable" msgstr "" -#: selfdrive/ui/onroad/alert_renderer.py:52 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:52 #, python-format msgid "Waiting to start" msgstr "" -#: selfdrive/ui/onroad/alert_renderer.py:58 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:58 #, python-format msgid "TAKE CONTROL IMMEDIATELY" msgstr "" -#: selfdrive/ui/onroad/alert_renderer.py:59 -#: selfdrive/ui/onroad/alert_renderer.py:65 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:59 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:65 #, python-format msgid "System Unresponsive" msgstr "" -#: selfdrive/ui/onroad/alert_renderer.py:66 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:66 #, python-format msgid "Reboot Device" msgstr "" + +#: openpilot/selfdrive/ui/onroad/driver_camera_dialog.py:38 +#, python-format +msgid "camera starting" +msgstr "" + +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:148 +#, python-format +msgid "MAX" +msgstr "" + +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 +#, python-format +msgid "km/h" +msgstr "" + +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 +#, python-format +msgid "mph" +msgstr "" + diff --git a/selfdrive/ui/translations/app_de.po b/selfdrive/ui/translations/app_de.po index f32c27a9ef..9888bb718e 100644 --- a/selfdrive/ui/translations/app_de.po +++ b/selfdrive/ui/translations/app_de.po @@ -17,1205 +17,1018 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1);\n" -#: selfdrive/ui/layouts/settings/device.py:160 +#: openpilot/selfdrive/ui/layouts/settings/device.py:152 #, python-format msgid " Steering torque response calibration is complete." msgstr " Die Lenkmoment-Reaktionskalibrierung ist abgeschlossen." -#: selfdrive/ui/layouts/settings/device.py:158 +#: openpilot/selfdrive/ui/layouts/settings/device.py:150 #, python-format msgid " Steering torque response calibration is {}% complete." msgstr " Die Lenkmoment-Reaktionskalibrierung ist zu {}% abgeschlossen." -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid " Your device is pointed {:.1f}° {} and {:.1f}° {}." msgstr " Ihr Gerät ist um {:.1f}° {} und {:.1f}° {} ausgerichtet." -#: selfdrive/ui/layouts/sidebar.py:43 +#: openpilot/selfdrive/ui/layouts/sidebar.py:43 msgid "--" msgstr "--" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "1 year of drive storage" msgstr "1 Jahr Fahrtdatenspeicherung" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "24/7 LTE connectivity" msgstr "24/7 LTE‑Verbindung" -#: selfdrive/ui/layouts/sidebar.py:46 +#: openpilot/selfdrive/ui/layouts/sidebar.py:46 msgid "2G" msgstr "2G" -#: selfdrive/ui/layouts/sidebar.py:47 +#: openpilot/selfdrive/ui/layouts/sidebar.py:47 msgid "3G" msgstr "3G" -#: selfdrive/ui/layouts/sidebar.py:49 +#: openpilot/selfdrive/ui/layouts/sidebar.py:49 msgid "5G" msgstr "5G" -#: selfdrive/ui/layouts/settings/developer.py:23 -msgid "" -"WARNING: openpilot longitudinal control is in alpha for this car and will " -"disable Automatic Emergency Braking (AEB).

On this car, openpilot " -"defaults to the car's built-in ACC instead of openpilot's longitudinal " -"control. Enable this to switch to openpilot longitudinal control. Enabling " -"Experimental mode is recommended when enabling openpilot longitudinal " -"control alpha. Changing this setting will restart openpilot if the car is " -"powered on." -msgstr "" -"WARNUNG: Die Längsregelung von openpilot befindet sich für dieses " -"Fahrzeug in der Alpha-Phase und deaktiviert das automatische Notbremssystem " -"(AEB).

Auf diesem Fahrzeug verwendet openpilot standardmäßig den " -"integrierten ACC statt der openpilot-Längsregelung. Aktivieren Sie dies, um " -"auf die openpilot-Längsregelung umzuschalten. Das Aktivieren des " -"Experimentalmodus wird empfohlen, wenn Sie die openpilot-Längsregelung " -"(Alpha) aktivieren." - -#: selfdrive/ui/layouts/settings/device.py:148 +#: openpilot/selfdrive/ui/layouts/settings/device.py:140 #, python-format msgid "

Steering lag calibration is complete." msgstr "

Kalibrierung der Lenkverzögerung abgeschlossen." -#: selfdrive/ui/layouts/settings/device.py:146 +#: openpilot/selfdrive/ui/layouts/settings/device.py:138 #, python-format msgid "

Steering lag calibration is {}% complete." msgstr "

Kalibrierung der Lenkverzögerung zu {}% abgeschlossen." -#: selfdrive/ui/layouts/settings/firehose.py:138 -#, python-format -msgid "ACTIVE" -msgstr "AKTIV" - -#: selfdrive/ui/layouts/settings/developer.py:15 -msgid "" -"ADB (Android Debug Bridge) allows connecting to your device over USB or over " -"the network. See https://docs.comma.ai/how-to/connect-to-comma for more info." -msgstr "" -"ADB (Android Debug Bridge) ermöglicht die Verbindung mit Ihrem Gerät über " -"USB oder über das Netzwerk. Siehe https://docs.comma.ai/how-to/connect-to-" -"comma für weitere Informationen." - -#: selfdrive/ui/widgets/ssh_key.py:30 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:30 msgid "ADD" msgstr "HINZUFÜGEN" -#: system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:136 #, python-format msgid "APN Setting" msgstr "APN‑Einstellung" -#: selfdrive/ui/widgets/offroad_alerts.py:109 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:109 #, python-format msgid "Acknowledge Excessive Actuation" msgstr "Übermäßige Betätigung bestätigen" -#: system/ui/widgets/network.py:74 system/ui/widgets/network.py:95 +#: system/ui/widgets/network.py:92 +#: system/ui/widgets/network.py:74 #, python-format msgid "Advanced" msgstr "Erweitert" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Aggressive" msgstr "Aggressiv" -#: selfdrive/ui/layouts/onboarding.py:116 +#: openpilot/selfdrive/ui/layouts/onboarding.py:120 #, python-format msgid "Agree" msgstr "Zustimmen" -#: selfdrive/ui/layouts/settings/toggles.py:70 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:70 #, python-format msgid "Always-On Driver Monitoring" msgstr "Immer aktive Fahrerüberwachung" -#: selfdrive/ui/layouts/settings/toggles.py:186 -#, python-format -msgid "" -"An alpha version of openpilot longitudinal control can be tested, along with " -"Experimental mode, on non-release branches." -msgstr "" -"Eine Alpha-Version der openpilot-Längsregelung kann zusammen mit dem " -"Experimentalmodus auf Nicht-Release-Zweigen getestet werden." - -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 #, python-format msgid "Are you sure you want to power off?" msgstr "Sind Sie sicher, dass Sie ausschalten möchten?" -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 #, python-format msgid "Are you sure you want to reboot?" msgstr "Sind Sie sicher, dass Sie neu starten möchten?" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Are you sure you want to reset calibration?" msgstr "Sind Sie sicher, dass Sie die Kalibrierung zurücksetzen möchten?" -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 #, python-format msgid "Are you sure you want to uninstall?" msgstr "Sind Sie sicher, dass Sie deinstallieren möchten?" -#: system/ui/widgets/network.py:99 selfdrive/ui/layouts/onboarding.py:147 +#: system/ui/widgets/network.py:96 +#: openpilot/selfdrive/ui/layouts/onboarding.py:151 #, python-format msgid "Back" msgstr "Zurück" -#: selfdrive/ui/widgets/prime.py:38 +#: openpilot/selfdrive/ui/widgets/prime.py:38 #, python-format msgid "Become a comma prime member at connect.comma.ai" msgstr "Werden Sie comma prime Mitglied auf connect.comma.ai" -#: selfdrive/ui/widgets/pairing_dialog.py:130 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:119 #, python-format msgid "Bookmark connect.comma.ai to your home screen to use it like an app" -msgstr "" -"Fügen Sie connect.comma.ai Ihrem Startbildschirm hinzu, um es wie eine App " -"zu verwenden" +msgstr "Fügen Sie connect.comma.ai Ihrem Startbildschirm hinzu, um es wie eine App zu verwenden" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "CHANGE" msgstr "ÄNDERN" -#: selfdrive/ui/layouts/settings/software.py:50 -#: selfdrive/ui/layouts/settings/software.py:107 -#: selfdrive/ui/layouts/settings/software.py:118 -#: selfdrive/ui/layouts/settings/software.py:147 +#: openpilot/selfdrive/ui/layouts/settings/software.py:157 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 +#: openpilot/selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:128 #, python-format msgid "CHECK" msgstr "PRÜFEN" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "CHILL MODE ON" msgstr "CHILL‑MODUS AKTIV" -#: system/ui/widgets/network.py:155 selfdrive/ui/layouts/sidebar.py:73 -#: selfdrive/ui/layouts/sidebar.py:134 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:138 +#: system/ui/widgets/network.py:152 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 #, python-format msgid "CONNECT" msgstr "VERBINDUNG" -#: system/ui/widgets/network.py:369 +#: system/ui/widgets/network.py:376 #, python-format msgid "CONNECTING..." msgstr "VERBINDUNG" -#: system/ui/widgets/confirm_dialog.py:23 system/ui/widgets/option_dialog.py:35 -#: system/ui/widgets/keyboard.py:81 system/ui/widgets/network.py:318 +#: system/ui/widgets/network.py:326 +#: system/ui/widgets/confirm_dialog.py:24 +#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/keyboard.py:83 #, python-format msgid "Cancel" msgstr "Abbrechen" -#: system/ui/widgets/network.py:134 +#: system/ui/widgets/network.py:131 #, python-format msgid "Cellular Metered" msgstr "Getaktete Mobilfunkverbindung" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "Change Language" msgstr "Sprache ändern" -#: selfdrive/ui/layouts/settings/toggles.py:125 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:125 #, python-format msgid "Changing this setting will restart openpilot if the car is powered on." -msgstr "" -" Durch Ändern dieser Einstellung wird openpilot neu gestartet, wenn das Auto " -"eingeschaltet ist." +msgstr " Durch Ändern dieser Einstellung wird openpilot neu gestartet, wenn das Auto eingeschaltet ist." -#: selfdrive/ui/widgets/pairing_dialog.py:129 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:118 #, python-format msgid "Click \"add new device\" and scan the QR code on the right" msgstr "Klicken Sie auf \"add new device\" und scannen Sie den QR‑Code rechts" -#: selfdrive/ui/widgets/offroad_alerts.py:104 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:104 #, python-format msgid "Close" msgstr "Schließen" -#: selfdrive/ui/layouts/settings/software.py:49 +#: openpilot/selfdrive/ui/layouts/settings/software.py:56 #, python-format msgid "Current Version" msgstr "Aktuelle Version" -#: selfdrive/ui/layouts/settings/software.py:110 +#: openpilot/selfdrive/ui/layouts/settings/software.py:120 #, python-format msgid "DOWNLOAD" msgstr "HERUNTERLADEN" -#: selfdrive/ui/layouts/onboarding.py:115 +#: openpilot/selfdrive/ui/layouts/onboarding.py:119 #, python-format msgid "Decline" msgstr "Ablehnen" -#: selfdrive/ui/layouts/onboarding.py:148 +#: openpilot/selfdrive/ui/layouts/onboarding.py:152 #, python-format msgid "Decline, uninstall openpilot" msgstr "Ablehnen, openpilot deinstallieren" -#: selfdrive/ui/layouts/settings/settings.py:67 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:64 msgid "Developer" msgstr "Entwickler" -#: selfdrive/ui/layouts/settings/settings.py:62 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:59 msgid "Device" msgstr "Gerät" -#: selfdrive/ui/layouts/settings/toggles.py:58 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:58 #, python-format msgid "Disengage on Accelerator Pedal" msgstr "Beim Gaspedal deaktivieren" -#: selfdrive/ui/layouts/settings/device.py:184 +#: openpilot/selfdrive/ui/layouts/settings/device.py:176 #, python-format msgid "Disengage to Power Off" msgstr "Zum Ausschalten deaktivieren" -#: selfdrive/ui/layouts/settings/device.py:172 +#: openpilot/selfdrive/ui/layouts/settings/device.py:164 #, python-format msgid "Disengage to Reboot" msgstr "Zum Neustart deaktivieren" -#: selfdrive/ui/layouts/settings/device.py:103 +#: openpilot/selfdrive/ui/layouts/settings/device.py:95 #, python-format msgid "Disengage to Reset Calibration" msgstr "Zum Zurücksetzen der Kalibrierung deaktivieren" -#: selfdrive/ui/layouts/settings/toggles.py:32 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:32 msgid "Display speed in km/h instead of mph." msgstr "Geschwindigkeit in km/h statt mph anzeigen." -#: selfdrive/ui/layouts/settings/device.py:59 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 #, python-format msgid "Dongle ID" msgstr "Dongle-ID" -#: selfdrive/ui/layouts/settings/software.py:50 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 #, python-format msgid "Download" msgstr "Herunterladen" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "Driver Camera" msgstr "Fahrerkamera" -#: selfdrive/ui/layouts/settings/toggles.py:96 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:96 #, python-format msgid "Driving Personality" msgstr "Fahrstil" -#: system/ui/widgets/network.py:123 system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:136 #, python-format msgid "EDIT" msgstr "BEARBEITEN" -#: selfdrive/ui/layouts/sidebar.py:138 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 msgid "ERROR" msgstr "FEHLER" -#: selfdrive/ui/layouts/sidebar.py:45 +#: openpilot/selfdrive/ui/layouts/sidebar.py:45 msgid "ETH" msgstr "ETH" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "EXPERIMENTAL MODE ON" msgstr "EXPERIMENTALMODUS AKTIV" -#: selfdrive/ui/layouts/settings/developer.py:166 -#: selfdrive/ui/layouts/settings/toggles.py:228 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:229 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:180 #, python-format msgid "Enable" msgstr "Aktivieren" -#: selfdrive/ui/layouts/settings/developer.py:39 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:39 #, python-format msgid "Enable ADB" msgstr "ADB aktivieren" -#: selfdrive/ui/layouts/settings/toggles.py:64 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:64 #, python-format msgid "Enable Lane Departure Warnings" msgstr "Spurverlassenswarnungen aktivieren" -#: system/ui/widgets/network.py:129 +#: system/ui/widgets/network.py:126 #, python-format msgid "Enable Roaming" msgstr "openpilot aktivieren" -#: selfdrive/ui/layouts/settings/developer.py:48 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:48 #, python-format msgid "Enable SSH" msgstr "SSH aktivieren" -#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:117 #, python-format msgid "Enable Tethering" msgstr "Spurverlassenswarnungen aktivieren" -#: selfdrive/ui/layouts/settings/toggles.py:30 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:30 msgid "Enable driver monitoring even when openpilot is not engaged." msgstr "Fahrerüberwachung auch aktivieren, wenn openpilot nicht aktiv ist." -#: selfdrive/ui/layouts/settings/toggles.py:46 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:46 #, python-format msgid "Enable openpilot" msgstr "openpilot aktivieren" -#: selfdrive/ui/layouts/settings/toggles.py:189 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:190 #, python-format -msgid "" -"Enable the openpilot longitudinal control (alpha) toggle to allow " -"Experimental mode." -msgstr "" -"Den Schalter für die openpilot-Längsregelung (Alpha) aktivieren, um den " -"Experimentalmodus zu erlauben." +msgid "Enable the openpilot longitudinal control (alpha) toggle to allow Experimental mode." +msgstr "Den Schalter für die openpilot-Längsregelung (Alpha) aktivieren, um den Experimentalmodus zu erlauben." -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "Enter APN" msgstr "APN eingeben" -#: system/ui/widgets/network.py:241 +#: system/ui/widgets/network.py:243 #, python-format msgid "Enter SSID" msgstr "SSID eingeben" -#: system/ui/widgets/network.py:254 +#: system/ui/widgets/network.py:257 #, python-format msgid "Enter new tethering password" msgstr "Neues Tethering‑Passwort eingeben" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:320 #, python-format msgid "Enter password" msgstr "Passwort eingeben" -#: selfdrive/ui/widgets/ssh_key.py:89 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:89 #, python-format msgid "Enter your GitHub username" msgstr "Geben Sie Ihren GitHub‑Benutzernamen ein" -#: system/ui/widgets/list_view.py:123 system/ui/widgets/list_view.py:160 +#: system/ui/widgets/list_view.py:123 +#: system/ui/widgets/list_view.py:160 #, python-format msgid "Error" msgstr "Fehler" -#: selfdrive/ui/layouts/settings/toggles.py:52 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:52 #, python-format msgid "Experimental Mode" msgstr "Experimentalmodus" -#: selfdrive/ui/layouts/settings/toggles.py:181 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:182 #, python-format -msgid "" -"Experimental mode is currently unavailable on this car since the car's stock " -"ACC is used for longitudinal control." -msgstr "" -"Der Experimentalmodus ist derzeit auf diesem Fahrzeug nicht verfügbar, da " -"der serienmäßige ACC für die Längsregelung verwendet wird." +msgid "Experimental mode is currently unavailable on this car since the car's stock ACC is used for longitudinal control." +msgstr "Der Experimentalmodus ist derzeit auf diesem Fahrzeug nicht verfügbar, da der serienmäßige ACC für die Längsregelung verwendet wird." -#: system/ui/widgets/network.py:373 +#: system/ui/widgets/network.py:380 #, python-format msgid "FORGETTING..." msgstr "WIRD VERGESSEN..." -#: selfdrive/ui/widgets/setup.py:44 +#: openpilot/selfdrive/ui/widgets/setup.py:43 #, python-format msgid "Finish Setup" msgstr "Einrichtung abschließen" -#: selfdrive/ui/layouts/settings/settings.py:66 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:63 msgid "Firehose" msgstr "Firehose" -#: selfdrive/ui/layouts/settings/firehose.py:18 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:10 msgid "Firehose Mode" msgstr "Firehose‑Modus" -#: selfdrive/ui/layouts/settings/firehose.py:25 -msgid "" -"For maximum effectiveness, bring your device inside and connect to a good " -"USB-C adapter and Wi-Fi weekly.\n" -"\n" -"Firehose Mode can also work while you're driving if connected to a hotspot " -"or unlimited SIM card.\n" -"\n" -"\n" -"Frequently Asked Questions\n" -"\n" -"Does it matter how or where I drive? Nope, just drive as you normally " -"would.\n" -"\n" -"Do all of my segments get pulled in Firehose Mode? No, we selectively pull a " -"subset of your segments.\n" -"\n" -"What's a good USB-C adapter? Any fast phone or laptop charger should be " -"fine.\n" -"\n" -"Does it matter which software I run? Yes, only upstream openpilot (and " -"particular forks) are able to be used for training." -msgstr "" -"Für maximale Wirksamkeit bringen Sie Ihr Gerät regelmäßig ins Haus und " -"verbinden es wöchentlich mit einem guten USB‑C‑Adapter und WLAN.\n" -"\n" -"Der Firehose‑Modus kann auch während der Fahrt funktionieren, wenn eine " -"Verbindung zu einem Hotspot oder einer unbegrenzten SIM besteht.\n" -"\n" -"\n" -"Häufig gestellte Fragen\n" -"\n" -"Spielt es eine Rolle, wie oder wo ich fahre? Nein, fahren Sie einfach wie " -"gewöhnlich.\n" -"\n" -"Werden alle meine Segmente im Firehose‑Modus abgeholt? Nein, wir ziehen " -"selektiv eine Teilmenge Ihrer Segmente.\n" -"\n" -"Was ist ein guter USB‑C‑Adapter? Jeder schnelle Telefon‑ oder Laptoplader " -"sollte ausreichen.\n" -"\n" -"Spielt es eine Rolle, welche Software ich verwende? Ja, nur " -"Upstream‑openpilot (und bestimmte Forks) können für das Training verwendet " -"werden." - -#: system/ui/widgets/network.py:318 system/ui/widgets/network.py:451 +#: system/ui/widgets/network.py:458 +#: system/ui/widgets/network.py:326 #, python-format msgid "Forget" msgstr "Vergessen" -#: system/ui/widgets/network.py:319 +#: system/ui/widgets/network.py:327 #, python-format msgid "Forget Wi-Fi Network \"{}\"?" msgstr "WLAN‑Netz „{}“ vergessen?" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 msgid "GOOD" msgstr "GUT" -#: selfdrive/ui/widgets/pairing_dialog.py:128 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:117 #, python-format msgid "Go to https://connect.comma.ai on your phone" msgstr "Gehen Sie auf Ihrem Telefon zu https://connect.comma.ai" -#: selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "HIGH" msgstr "HOCH" -#: system/ui/widgets/network.py:155 +#: system/ui/widgets/network.py:152 #, python-format msgid "Hidden Network" msgstr "Netzwerk" -#: selfdrive/ui/layouts/settings/firehose.py:140 -#, python-format -msgid "INACTIVE: connect to an unmetered network" -msgstr "INAKTIV: Mit einem unlimitierten Netzwerk verbinden" - -#: selfdrive/ui/layouts/settings/software.py:53 -#: selfdrive/ui/layouts/settings/software.py:136 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 +#: openpilot/selfdrive/ui/layouts/settings/software.py:146 #, python-format msgid "INSTALL" msgstr "INSTALLIEREN" -#: system/ui/widgets/network.py:150 +#: system/ui/widgets/network.py:147 #, python-format msgid "IP Address" msgstr "IP‑Adresse" -#: selfdrive/ui/layouts/settings/software.py:53 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 #, python-format msgid "Install Update" msgstr "Update installieren" -#: selfdrive/ui/layouts/settings/developer.py:56 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:56 #, python-format msgid "Joystick Debug Mode" msgstr "Joystick‑Debugmodus" -#: selfdrive/ui/widgets/ssh_key.py:29 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:29 msgid "LOADING" msgstr "LADEN" -#: selfdrive/ui/layouts/sidebar.py:48 +#: openpilot/selfdrive/ui/layouts/sidebar.py:48 msgid "LTE" msgstr "LTE" -#: selfdrive/ui/layouts/settings/developer.py:64 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:64 #, python-format msgid "Longitudinal Maneuver Mode" msgstr "Längsmanövermodus" -#: selfdrive/ui/onroad/hud_renderer.py:148 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:148 #, python-format msgid "MAX" msgstr "MAX" -#: selfdrive/ui/widgets/setup.py:75 +#: openpilot/selfdrive/ui/widgets/setup.py:74 #, python-format -msgid "" -"Maximize your training data uploads to improve openpilot's driving models." -msgstr "" -"Maximieren Sie Ihre Trainingsdaten‑Uploads, um die Fahrmodelle von openpilot " -"zu verbessern." +msgid "Maximize your training data uploads to improve openpilot's driving models." +msgstr "Maximieren Sie Ihre Trainingsdaten‑Uploads, um die Fahrmodelle von openpilot zu verbessern." -#: selfdrive/ui/layouts/settings/device.py:59 -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "N/A" msgstr "k. A." -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "NO" msgstr "KEIN" -#: selfdrive/ui/layouts/settings/settings.py:63 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:60 msgid "Network" msgstr "Netzwerk" -#: selfdrive/ui/widgets/ssh_key.py:114 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:115 #, python-format msgid "No SSH keys found" msgstr "Keine SSH‑Schlüssel gefunden" -#: selfdrive/ui/widgets/ssh_key.py:126 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:127 #, python-format msgid "No SSH keys found for user '{}'" msgstr "Keine SSH‑Schlüssel für Benutzer '{username}' gefunden" -#: selfdrive/ui/widgets/offroad_alerts.py:320 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:321 #, python-format msgid "No release notes available." msgstr "Keine Versionshinweise verfügbar." -#: selfdrive/ui/layouts/sidebar.py:73 selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 msgid "OFFLINE" msgstr "OFFLINE" -#: system/ui/widgets/html_render.py:263 system/ui/widgets/confirm_dialog.py:93 -#: selfdrive/ui/layouts/sidebar.py:127 +#: system/ui/widgets/confirm_dialog.py:93 +#: system/ui/widgets/html_render.py:263 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 #, python-format msgid "OK" msgstr "OK" -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 msgid "ONLINE" msgstr "ONLINE" -#: selfdrive/ui/widgets/setup.py:20 +#: openpilot/selfdrive/ui/widgets/setup.py:19 #, python-format msgid "Open" msgstr "Öffnen" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "PAIR" msgstr "KOPPELN" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "PANDA" msgstr "PANDA" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "PREVIEW" msgstr "VORSCHAU" -#: selfdrive/ui/widgets/prime.py:44 +#: openpilot/selfdrive/ui/widgets/prime.py:44 #, python-format msgid "PRIME FEATURES:" msgstr "PRIME‑FUNKTIONEN:" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "Pair Device" msgstr "Gerät koppeln" -#: selfdrive/ui/widgets/setup.py:19 +#: openpilot/selfdrive/ui/widgets/setup.py:18 #, python-format msgid "Pair device" msgstr "Gerät koppeln" -#: selfdrive/ui/widgets/pairing_dialog.py:103 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:92 #, python-format msgid "Pair your device to your comma account" msgstr "Koppeln Sie Ihr Gerät mit Ihrem comma‑Konto" -#: selfdrive/ui/widgets/setup.py:48 selfdrive/ui/layouts/settings/device.py:24 +#: openpilot/selfdrive/ui/widgets/setup.py:47 +#: openpilot/selfdrive/ui/layouts/settings/device.py:23 #, python-format -msgid "" -"Pair your device with comma connect (connect.comma.ai) and claim your comma " -"prime offer." -msgstr "" -"Koppeln Sie Ihr Gerät mit comma connect (connect.comma.ai) und lösen Sie Ihr " -"comma‑prime‑Angebot ein." +msgid "Pair your device with comma connect (connect.comma.ai) and claim your comma prime offer." +msgstr "Koppeln Sie Ihr Gerät mit comma connect (connect.comma.ai) und lösen Sie Ihr comma‑prime‑Angebot ein." -#: selfdrive/ui/widgets/setup.py:91 +#: openpilot/selfdrive/ui/widgets/setup.py:91 #, python-format msgid "Please connect to Wi-Fi to complete initial pairing" msgstr "Bitte mit WLAN verbinden, um das erste Koppeln abzuschließen" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Power Off" msgstr "Ausschalten" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Prevent large data uploads when on a metered Wi-Fi connection" msgstr "" -#: system/ui/widgets/network.py:135 +#: system/ui/widgets/network.py:132 #, python-format msgid "Prevent large data uploads when on a metered cellular connection" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:25 -msgid "" -"Preview the driver facing camera to ensure that driver monitoring has good " -"visibility. (vehicle must be off)" -msgstr "" -"Vorschau der Fahrer‑Kamera, um sicherzustellen, dass die Fahrerüberwachung " -"gute Sicht hat. (Fahrzeug muss ausgeschaltet sein)" +#: openpilot/selfdrive/ui/layouts/settings/device.py:24 +msgid "Preview the driver facing camera to ensure that driver monitoring has good visibility. (vehicle must be off)" +msgstr "Vorschau der Fahrer‑Kamera, um sicherzustellen, dass die Fahrerüberwachung gute Sicht hat. (Fahrzeug muss ausgeschaltet sein)" -#: selfdrive/ui/widgets/pairing_dialog.py:161 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:150 #, python-format msgid "QR Code Error" msgstr "QR‑Code‑Fehler" -#: selfdrive/ui/widgets/ssh_key.py:31 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:31 msgid "REMOVE" msgstr "ENTFERNEN" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "RESET" msgstr "ZURÜCKSETZEN" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "REVIEW" msgstr "ANSEHEN" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Reboot" msgstr "Neustart" -#: selfdrive/ui/onroad/alert_renderer.py:66 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:66 #, python-format msgid "Reboot Device" msgstr "Gerät neu starten" -#: selfdrive/ui/widgets/offroad_alerts.py:112 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:112 #, python-format msgid "Reboot and Update" msgstr "Neustarten und aktualisieren" -#: selfdrive/ui/layouts/settings/toggles.py:27 -msgid "" -"Receive alerts to steer back into the lane when your vehicle drifts over a " -"detected lane line without a turn signal activated while driving over 31 mph " -"(50 km/h)." -msgstr "" -"Erhalten Sie Warnungen, um zurück in die Spur zu lenken, wenn Ihr Fahrzeug " -"ohne Blinker über eine erkannte Spurlinie driftet und über 31 mph (50 km/h) " -"fährt." - -#: selfdrive/ui/layouts/settings/toggles.py:76 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:76 #, python-format msgid "Record and Upload Driver Camera" msgstr "Fahrerkamera aufzeichnen und hochladen" -#: selfdrive/ui/layouts/settings/toggles.py:82 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:82 #, python-format msgid "Record and Upload Microphone Audio" msgstr "Mikrofonton aufzeichnen und hochladen" -#: selfdrive/ui/layouts/settings/toggles.py:33 -msgid "" -"Record and store microphone audio while driving. The audio will be included " -"in the dashcam video in comma connect." -msgstr "" -"Mikrofonton während der Fahrt aufzeichnen und speichern. Die Audiospur wird " -"im Dashcam‑Video in comma connect enthalten sein." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:33 +msgid "Record and store microphone audio while driving. The audio will be included in the dashcam video in comma connect." +msgstr "Mikrofonton während der Fahrt aufzeichnen und speichern. Die Audiospur wird im Dashcam‑Video in comma connect enthalten sein." -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "Regulatory" msgstr "Vorschriften" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Relaxed" msgstr "Entspannt" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote access" msgstr "Fernzugriff" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote snapshots" msgstr "Remote‑Schnappschüsse" -#: selfdrive/ui/widgets/ssh_key.py:123 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:124 #, python-format msgid "Request timed out" msgstr "Zeitüberschreitung bei der Anfrage" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Reset" msgstr "Zurücksetzen" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "Reset Calibration" msgstr "Kalibrierung zurücksetzen" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "Review Training Guide" msgstr "Trainingsanleitung ansehen" -#: selfdrive/ui/layouts/settings/device.py:27 +#: openpilot/selfdrive/ui/layouts/settings/device.py:26 msgid "Review the rules, features, and limitations of openpilot" -msgstr "" -"Überprüfen Sie die Regeln, Funktionen und Einschränkungen von openpilot" +msgstr "Überprüfen Sie die Regeln, Funktionen und Einschränkungen von openpilot" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "SELECT" msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:53 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:53 #, python-format msgid "SSH Keys" msgstr "SSH‑Schlüssel" -#: system/ui/widgets/network.py:310 +#: system/ui/widgets/network.py:316 #, python-format msgid "Scanning Wi-Fi networks..." msgstr "WLAN‑Netzwerke werden gesucht..." -#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/option_dialog.py:37 #, python-format msgid "Select" msgstr "Auswählen" -#: selfdrive/ui/layouts/settings/software.py:183 +#: openpilot/selfdrive/ui/layouts/settings/software.py:203 #, python-format msgid "Select a branch" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:91 +#: openpilot/selfdrive/ui/layouts/settings/device.py:89 #, python-format msgid "Select a language" msgstr "Sprache auswählen" -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "Serial" msgstr "Seriennummer" -#: selfdrive/ui/widgets/offroad_alerts.py:106 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:106 #, python-format msgid "Snooze Update" msgstr "Update verschieben" -#: selfdrive/ui/layouts/settings/settings.py:65 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:62 msgid "Software" msgstr "Software" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Standard" msgstr "Standard" -#: selfdrive/ui/layouts/settings/toggles.py:22 -msgid "" -"Standard is recommended. In aggressive mode, openpilot will follow lead cars " -"closer and be more aggressive with the gas and brake. In relaxed mode " -"openpilot will stay further away from lead cars. On supported cars, you can " -"cycle through these personalities with your steering wheel distance button." -msgstr "" -"Standard wird empfohlen. Im aggressiven Modus folgt openpilot " -"vorausfahrenden Fahrzeugen näher und ist beim Gasgeben und Bremsen " -"aggressiver. Im entspannten Modus bleibt openpilot weiter entfernt. Bei " -"unterstützten Fahrzeugen können Sie mit der Abstandstaste am Lenkrad " -"zwischen diesen Profilen wechseln." - -#: selfdrive/ui/onroad/alert_renderer.py:59 -#: selfdrive/ui/onroad/alert_renderer.py:65 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:59 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:65 #, python-format msgid "System Unresponsive" msgstr "System reagiert nicht" -#: selfdrive/ui/onroad/alert_renderer.py:58 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:58 #, python-format msgid "TAKE CONTROL IMMEDIATELY" msgstr "SOFORT DIE KONTROLLE ÜBERNEHMEN" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 -#: selfdrive/ui/layouts/sidebar.py:127 selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "TEMP" msgstr "TEMP" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "Target Branch" msgstr "" -#: system/ui/widgets/network.py:124 +#: system/ui/widgets/network.py:121 #, python-format msgid "Tethering Password" msgstr "Tethering‑Passwort" -#: selfdrive/ui/layouts/settings/settings.py:64 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:61 msgid "Toggles" msgstr "Schalter" -#: selfdrive/ui/layouts/settings/software.py:72 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:79 +#, python-format +msgid "UI Debug Mode" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "UNINSTALL" msgstr "DEINSTALLIEREN" -#: selfdrive/ui/layouts/home.py:155 +#: openpilot/selfdrive/ui/layouts/home.py:155 #, python-format msgid "UPDATE" msgstr "UPDATE" -#: selfdrive/ui/layouts/settings/software.py:72 -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "Uninstall" msgstr "Deinstallieren" -#: selfdrive/ui/layouts/sidebar.py:117 +#: openpilot/selfdrive/ui/layouts/sidebar.py:117 msgid "Unknown" msgstr "Unbekannt" -#: selfdrive/ui/layouts/settings/software.py:48 +#: openpilot/selfdrive/ui/layouts/settings/software.py:55 #, python-format msgid "Updates are only downloaded while the car is off." msgstr "Updates werden nur heruntergeladen, wenn das Auto aus ist." -#: selfdrive/ui/widgets/prime.py:33 +#: openpilot/selfdrive/ui/widgets/prime.py:33 #, python-format msgid "Upgrade Now" msgstr "Jetzt abonnieren" -#: selfdrive/ui/layouts/settings/toggles.py:31 -msgid "" -"Upload data from the driver facing camera and help improve the driver " -"monitoring algorithm." -msgstr "" -"Daten von der Fahrer‑Kamera hochladen und den Fahrerüberwachungs‑Algorithmus " -"verbessern." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:31 +msgid "Upload data from the driver facing camera and help improve the driver monitoring algorithm." +msgstr "Daten von der Fahrer‑Kamera hochladen und den Fahrerüberwachungs‑Algorithmus verbessern." -#: selfdrive/ui/layouts/settings/toggles.py:88 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:88 #, python-format msgid "Use Metric System" msgstr "Metersystem verwenden" -#: selfdrive/ui/layouts/settings/toggles.py:17 -msgid "" -"Use the openpilot system for adaptive cruise control and lane keep driver " -"assistance. Your attention is required at all times to use this feature." -msgstr "" -"Verwenden Sie openpilot für adaptive Geschwindigkeitsregelung und " -"Spurhalteassistenz. Ihre Aufmerksamkeit ist jederzeit erforderlich, um diese " -"Funktion zu nutzen." - -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 msgid "VEHICLE" msgstr "FAHRZEUG" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "VIEW" msgstr "ANSEHEN" -#: selfdrive/ui/onroad/alert_renderer.py:52 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:52 #, python-format msgid "Waiting to start" msgstr "Warten auf Start" -#: selfdrive/ui/layouts/settings/developer.py:19 -msgid "" -"Warning: This grants SSH access to all public keys in your GitHub settings. " -"Never enter a GitHub username other than your own. A comma employee will " -"NEVER ask you to add their GitHub username." -msgstr "" -"Warnung: Dies gewährt SSH‑Zugriff auf alle öffentlichen Schlüssel in Ihren " -"GitHub‑Einstellungen. Geben Sie niemals einen anderen GitHub‑Benutzernamen " -"als Ihren eigenen ein. Ein comma‑Mitarbeiter wird Sie NIEMALS bitten, seinen " -"GitHub‑Benutzernamen hinzuzufügen." - -#: selfdrive/ui/layouts/onboarding.py:111 +#: openpilot/selfdrive/ui/layouts/onboarding.py:115 #, python-format msgid "Welcome to openpilot" msgstr "Willkommen bei openpilot" -#: selfdrive/ui/layouts/settings/toggles.py:20 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:20 msgid "When enabled, pressing the accelerator pedal will disengage openpilot." msgstr "Wenn aktiviert, deaktiviert das Drücken des Gaspedals openpilot." -#: selfdrive/ui/layouts/sidebar.py:44 +#: openpilot/selfdrive/ui/layouts/sidebar.py:44 msgid "Wi-Fi" msgstr "WLAN" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Wi-Fi Network Metered" msgstr "Getaktetes WLAN‑Netzwerk" -#: system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:320 #, python-format msgid "Wrong password" msgstr "Falsches Passwort" -#: selfdrive/ui/layouts/onboarding.py:145 +#: openpilot/selfdrive/ui/layouts/onboarding.py:149 #, python-format msgid "You must accept the Terms and Conditions in order to use openpilot." -msgstr "" -"Sie müssen die Nutzungsbedingungen akzeptieren, um openpilot zu verwenden." +msgstr "Sie müssen die Nutzungsbedingungen akzeptieren, um openpilot zu verwenden." -#: selfdrive/ui/layouts/onboarding.py:112 +#: openpilot/selfdrive/ui/layouts/onboarding.py:116 #, python-format -msgid "" -"You must accept the Terms and Conditions to use openpilot. Read the latest " -"terms at https://comma.ai/terms before continuing." -msgstr "" -"Sie müssen die Nutzungsbedingungen akzeptieren, um openpilot zu verwenden. " -"Lesen Sie die aktuellen Bedingungen unter https://comma.ai/terms, bevor Sie " -"fortfahren." +msgid "You must accept the Terms and Conditions to use openpilot. Read the latest terms at https://comma.ai/terms before continuing." +msgstr "Sie müssen die Nutzungsbedingungen akzeptieren, um openpilot zu verwenden. Lesen Sie die aktuellen Bedingungen unter https://comma.ai/terms, bevor Sie fortfahren." -#: selfdrive/ui/onroad/driver_camera_dialog.py:34 +#: openpilot/selfdrive/ui/onroad/driver_camera_dialog.py:38 #, python-format msgid "camera starting" msgstr "Kamera startet" -#: selfdrive/ui/widgets/prime.py:63 +#: openpilot/selfdrive/ui/layouts/settings/software.py:19 +#, python-format +msgid "checking..." +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:63 #, python-format msgid "comma prime" msgstr "comma prime" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "default" msgstr "Standard" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "down" msgstr "unten" -#: selfdrive/ui/layouts/settings/software.py:106 +#: openpilot/selfdrive/ui/layouts/settings/software.py:20 +#, python-format +msgid "downloading..." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:116 #, python-format msgid "failed to check for update" msgstr "Überprüfung auf Updates fehlgeschlagen" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: openpilot/selfdrive/ui/layouts/settings/software.py:21 +#, python-format +msgid "finalizing update..." +msgstr "" + +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:321 #, python-format msgid "for \"{}\"" msgstr "für „{}“" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "km/h" msgstr "km/h" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "leave blank for automatic configuration" msgstr "für automatische Konfiguration leer lassen" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "left" msgstr "links" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "metered" msgstr "getaktet" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "mph" msgstr "mph" -#: selfdrive/ui/layouts/settings/software.py:20 +#: openpilot/selfdrive/ui/layouts/settings/software.py:27 #, python-format msgid "never" msgstr "nie" -#: selfdrive/ui/layouts/settings/software.py:31 +#: openpilot/selfdrive/ui/layouts/settings/software.py:38 #, python-format msgid "now" msgstr "jetzt" -#: selfdrive/ui/layouts/settings/developer.py:71 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:71 #, python-format msgid "openpilot Longitudinal Control (Alpha)" msgstr "openpilot Längsregelung (Alpha)" -#: selfdrive/ui/onroad/alert_renderer.py:51 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:51 #, python-format msgid "openpilot Unavailable" msgstr "openpilot nicht verfügbar" -#: selfdrive/ui/layouts/settings/toggles.py:158 -#, python-format -msgid "" -"openpilot defaults to driving in chill mode. Experimental mode enables alpha-" -"level features that aren't ready for chill mode. Experimental features are " -"listed below:

End-to-End Longitudinal Control


Let the driving " -"model control the gas and brakes. openpilot will drive as it thinks a human " -"would, including stopping for red lights and stop signs. Since the driving " -"model decides the speed to drive, the set speed will only act as an upper " -"bound. This is an alpha quality feature; mistakes should be expected." -"

New Driving Visualization


The driving visualization will " -"transition to the road-facing wide-angle camera at low speeds to better show " -"some turns. The Experimental mode logo will also be shown in the top right " -"corner." -msgstr "" -"openpilot fährt standardmäßig im Chill‑Modus. Der Experimentalmodus " -"aktiviert Funktionen im Alpha‑Status, die für den Chill‑Modus noch nicht " -"bereit sind. Die experimentellen Funktionen sind unten aufgeführt:" -"

End-to‑End‑Längsregelung


Das Fahrmodell steuert Gas und " -"Bremse. openpilot fährt so, wie es einen Menschen einschätzt, einschließlich " -"Anhalten an roten Ampeln und Stoppschildern. Da das Modell die " -"Geschwindigkeit bestimmt, dient die eingestellte Geschwindigkeit nur als " -"Obergrenze. Dies ist eine Alpha‑Funktion; Fehler sind zu erwarten." -"

Neue Fahrvisualisierung


Die Visualisierung wechselt bei " -"niedriger Geschwindigkeit auf die nach vorn gerichtete Weitwinkelkamera, um " -"manche Kurven besser zu zeigen. Das Experimentalmodus‑Logo wird außerdem " -"oben rechts angezeigt." - -#: selfdrive/ui/layouts/settings/device.py:165 -#, python-format -msgid "" -"openpilot is continuously calibrating, resetting is rarely required. " -"Resetting calibration will restart openpilot if the car is powered on." -msgstr "" -" Durch Ändern dieser Einstellung wird openpilot neu gestartet, wenn das Auto " -"eingeschaltet ist." - -#: selfdrive/ui/layouts/settings/firehose.py:20 -msgid "" -"openpilot learns to drive by watching humans, like you, drive.\n" -"\n" -"Firehose Mode allows you to maximize your training data uploads to improve " -"openpilot's driving models. More data means bigger models, which means " -"better Experimental Mode." -msgstr "" -"openpilot lernt das Fahren, indem es Menschen wie Sie beobachtet.\n" -"\n" -"Der Firehose‑Modus ermöglicht es Ihnen, Ihre Trainingsdaten‑Uploads zu " -"maximieren, um die Fahrmodelle von openpilot zu verbessern. Mehr Daten " -"bedeuten größere Modelle – und damit einen besseren Experimentalmodus." - -#: selfdrive/ui/layouts/settings/toggles.py:183 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:184 #, python-format msgid "openpilot longitudinal control may come in a future update." msgstr "Die openpilot‑Längsregelung könnte in einem zukünftigen Update kommen." -#: selfdrive/ui/layouts/settings/device.py:26 -msgid "" -"openpilot requires the device to be mounted within 4° left or right and " -"within 5° up or 9° down." -msgstr "" -"openpilot erfordert, dass das Gerät innerhalb von 4° nach links oder rechts " -"und innerhalb von 5° nach oben oder 9° nach unten montiert ist." +#: openpilot/selfdrive/ui/layouts/settings/device.py:25 +msgid "openpilot requires the device to be mounted within 4° left or right and within 5° up or 9° down." +msgstr "openpilot erfordert, dass das Gerät innerhalb von 4° nach links oder rechts und innerhalb von 5° nach oben oder 9° nach unten montiert ist." -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "right" msgstr "rechts" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "unmetered" msgstr "unbegrenzt" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "up" msgstr "oben" -#: selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:127 #, python-format msgid "up to date, last checked never" msgstr "Aktuell, zuletzt geprüft: nie" -#: selfdrive/ui/layouts/settings/software.py:115 +#: openpilot/selfdrive/ui/layouts/settings/software.py:125 #, python-format msgid "up to date, last checked {}" msgstr "Aktuell, zuletzt geprüft: {}" -#: selfdrive/ui/layouts/settings/software.py:109 +#: openpilot/selfdrive/ui/layouts/settings/software.py:119 #, python-format msgid "update available" msgstr "Update verfügbar" -#: selfdrive/ui/layouts/home.py:169 +#: openpilot/selfdrive/ui/layouts/home.py:169 #, python-format msgid "{} ALERT" msgid_plural "{} ALERTS" msgstr[0] "{} WARNUNG" msgstr[1] "{} WARNUNGEN" -#: selfdrive/ui/layouts/settings/software.py:40 +#: openpilot/selfdrive/ui/layouts/settings/software.py:47 #, python-format msgid "{} day ago" msgid_plural "{} days ago" msgstr[0] "vor {} Tag" msgstr[1] "vor {} Tagen" -#: selfdrive/ui/layouts/settings/software.py:37 +#: openpilot/selfdrive/ui/layouts/settings/software.py:44 #, python-format msgid "{} hour ago" msgid_plural "{} hours ago" msgstr[0] "vor {} Stunde" msgstr[1] "vor {} Stunden" -#: selfdrive/ui/layouts/settings/software.py:34 +#: openpilot/selfdrive/ui/layouts/settings/software.py:41 #, python-format msgid "{} minute ago" msgid_plural "{} minutes ago" msgstr[0] "vor {} Minute" msgstr[1] "vor {} Minuten" -#: selfdrive/ui/layouts/settings/firehose.py:111 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:70 #, python-format msgid "{} segment of your driving is in the training dataset so far." msgid_plural "{} segments of your driving is in the training dataset so far." msgstr[0] "{} Segment Ihrer Fahrten ist bisher im Trainingsdatensatz." msgstr[1] "{} Segmente Ihrer Fahrten sind bisher im Trainingsdatensatz." -#: selfdrive/ui/widgets/prime.py:62 +#: openpilot/selfdrive/ui/widgets/prime.py:62 #, python-format msgid "✓ SUBSCRIBED" msgstr "✓ ABONNIERT" -#: selfdrive/ui/widgets/setup.py:22 +#: openpilot/selfdrive/ui/widgets/setup.py:21 #, python-format msgid "🔥 Firehose Mode 🔥" msgstr "🔥 Firehose‑Modus 🔥" + diff --git a/selfdrive/ui/translations/app_en.po b/selfdrive/ui/translations/app_en.po index 6fbb537aff..3744096226 100644 --- a/selfdrive/ui/translations/app_en.po +++ b/selfdrive/ui/translations/app_en.po @@ -17,1191 +17,1018 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1);\n" -#: selfdrive/ui/layouts/settings/device.py:160 +#: openpilot/selfdrive/ui/layouts/settings/device.py:152 #, python-format msgid " Steering torque response calibration is complete." msgstr " Steering torque response calibration is complete." -#: selfdrive/ui/layouts/settings/device.py:158 +#: openpilot/selfdrive/ui/layouts/settings/device.py:150 #, python-format msgid " Steering torque response calibration is {}% complete." msgstr " Steering torque response calibration is {}% complete." -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid " Your device is pointed {:.1f}° {} and {:.1f}° {}." msgstr " Your device is pointed {:.1f}° {} and {:.1f}° {}." -#: selfdrive/ui/layouts/sidebar.py:43 +#: openpilot/selfdrive/ui/layouts/sidebar.py:43 msgid "--" msgstr "--" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "1 year of drive storage" msgstr "1 year of drive storage" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "24/7 LTE connectivity" msgstr "24/7 LTE connectivity" -#: selfdrive/ui/layouts/sidebar.py:46 +#: openpilot/selfdrive/ui/layouts/sidebar.py:46 msgid "2G" msgstr "2G" -#: selfdrive/ui/layouts/sidebar.py:47 +#: openpilot/selfdrive/ui/layouts/sidebar.py:47 msgid "3G" msgstr "3G" -#: selfdrive/ui/layouts/sidebar.py:49 +#: openpilot/selfdrive/ui/layouts/sidebar.py:49 msgid "5G" msgstr "5G" -#: selfdrive/ui/layouts/settings/developer.py:23 -msgid "" -"WARNING: openpilot longitudinal control is in alpha for this car and will " -"disable Automatic Emergency Braking (AEB).

On this car, openpilot " -"defaults to the car's built-in ACC instead of openpilot's longitudinal " -"control. Enable this to switch to openpilot longitudinal control. Enabling " -"Experimental mode is recommended when enabling openpilot longitudinal " -"control alpha. Changing this setting will restart openpilot if the car is " -"powered on." -msgstr "" -"WARNING: openpilot longitudinal control is in alpha for this car and will " -"disable Automatic Emergency Braking (AEB).

On this car, openpilot " -"defaults to the car's built-in ACC instead of openpilot's longitudinal " -"control. Enable this to switch to openpilot longitudinal control. Enabling " -"Experimental mode is recommended when enabling openpilot longitudinal " -"control alpha. Changing this setting will restart openpilot if the car is " -"powered on." - -#: selfdrive/ui/layouts/settings/device.py:148 +#: openpilot/selfdrive/ui/layouts/settings/device.py:140 #, python-format msgid "

Steering lag calibration is complete." msgstr "

Steering lag calibration is complete." -#: selfdrive/ui/layouts/settings/device.py:146 +#: openpilot/selfdrive/ui/layouts/settings/device.py:138 #, python-format msgid "

Steering lag calibration is {}% complete." msgstr "

Steering lag calibration is {}% complete." -#: selfdrive/ui/layouts/settings/firehose.py:138 -#, python-format -msgid "ACTIVE" -msgstr "ACTIVE" - -#: selfdrive/ui/layouts/settings/developer.py:15 -msgid "" -"ADB (Android Debug Bridge) allows connecting to your device over USB or over " -"the network. See https://docs.comma.ai/how-to/connect-to-comma for more info." -msgstr "" -"ADB (Android Debug Bridge) allows connecting to your device over USB or over " -"the network. See https://docs.comma.ai/how-to/connect-to-comma for more info." - -#: selfdrive/ui/widgets/ssh_key.py:30 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:30 msgid "ADD" msgstr "ADD" -#: system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:136 #, python-format msgid "APN Setting" msgstr "APN Setting" -#: selfdrive/ui/widgets/offroad_alerts.py:109 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:109 #, python-format msgid "Acknowledge Excessive Actuation" msgstr "Acknowledge Excessive Actuation" -#: system/ui/widgets/network.py:74 system/ui/widgets/network.py:95 +#: system/ui/widgets/network.py:92 +#: system/ui/widgets/network.py:74 #, python-format msgid "Advanced" msgstr "Advanced" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Aggressive" msgstr "Aggressive" -#: selfdrive/ui/layouts/onboarding.py:116 +#: openpilot/selfdrive/ui/layouts/onboarding.py:120 #, python-format msgid "Agree" msgstr "Agree" -#: selfdrive/ui/layouts/settings/toggles.py:70 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:70 #, python-format msgid "Always-On Driver Monitoring" msgstr "Always-On Driver Monitoring" -#: selfdrive/ui/layouts/settings/toggles.py:186 -#, python-format -msgid "" -"An alpha version of openpilot longitudinal control can be tested, along with " -"Experimental mode, on non-release branches." -msgstr "" -"An alpha version of openpilot longitudinal control can be tested, along with " -"Experimental mode, on non-release branches." - -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 #, python-format msgid "Are you sure you want to power off?" msgstr "Are you sure you want to power off?" -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 #, python-format msgid "Are you sure you want to reboot?" msgstr "Are you sure you want to reboot?" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Are you sure you want to reset calibration?" msgstr "Are you sure you want to reset calibration?" -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 #, python-format msgid "Are you sure you want to uninstall?" msgstr "Are you sure you want to uninstall?" -#: system/ui/widgets/network.py:99 selfdrive/ui/layouts/onboarding.py:147 +#: system/ui/widgets/network.py:96 +#: openpilot/selfdrive/ui/layouts/onboarding.py:151 #, python-format msgid "Back" msgstr "Back" -#: selfdrive/ui/widgets/prime.py:38 +#: openpilot/selfdrive/ui/widgets/prime.py:38 #, python-format msgid "Become a comma prime member at connect.comma.ai" msgstr "Become a comma prime member at connect.comma.ai" -#: selfdrive/ui/widgets/pairing_dialog.py:130 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:119 #, python-format msgid "Bookmark connect.comma.ai to your home screen to use it like an app" msgstr "Bookmark connect.comma.ai to your home screen to use it like an app" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "CHANGE" msgstr "CHANGE" -#: selfdrive/ui/layouts/settings/software.py:50 -#: selfdrive/ui/layouts/settings/software.py:107 -#: selfdrive/ui/layouts/settings/software.py:118 -#: selfdrive/ui/layouts/settings/software.py:147 +#: openpilot/selfdrive/ui/layouts/settings/software.py:157 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 +#: openpilot/selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:128 #, python-format msgid "CHECK" msgstr "CHECK" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "CHILL MODE ON" msgstr "CHILL MODE ON" -#: system/ui/widgets/network.py:155 selfdrive/ui/layouts/sidebar.py:73 -#: selfdrive/ui/layouts/sidebar.py:134 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:138 +#: system/ui/widgets/network.py:152 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 #, python-format msgid "CONNECT" msgstr "CONNECT" -#: system/ui/widgets/network.py:369 +#: system/ui/widgets/network.py:376 #, python-format msgid "CONNECTING..." msgstr "CONNECTING..." -#: system/ui/widgets/confirm_dialog.py:23 system/ui/widgets/option_dialog.py:35 -#: system/ui/widgets/keyboard.py:81 system/ui/widgets/network.py:318 +#: system/ui/widgets/network.py:326 +#: system/ui/widgets/confirm_dialog.py:24 +#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/keyboard.py:83 #, python-format msgid "Cancel" msgstr "Cancel" -#: system/ui/widgets/network.py:134 +#: system/ui/widgets/network.py:131 #, python-format msgid "Cellular Metered" msgstr "Cellular Metered" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "Change Language" msgstr "Change Language" -#: selfdrive/ui/layouts/settings/toggles.py:125 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:125 #, python-format msgid "Changing this setting will restart openpilot if the car is powered on." msgstr "Changing this setting will restart openpilot if the car is powered on." -#: selfdrive/ui/widgets/pairing_dialog.py:129 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:118 #, python-format msgid "Click \"add new device\" and scan the QR code on the right" msgstr "Click \"add new device\" and scan the QR code on the right" -#: selfdrive/ui/widgets/offroad_alerts.py:104 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:104 #, python-format msgid "Close" msgstr "Close" -#: selfdrive/ui/layouts/settings/software.py:49 +#: openpilot/selfdrive/ui/layouts/settings/software.py:56 #, python-format msgid "Current Version" msgstr "Current Version" -#: selfdrive/ui/layouts/settings/software.py:110 +#: openpilot/selfdrive/ui/layouts/settings/software.py:120 #, python-format msgid "DOWNLOAD" msgstr "DOWNLOAD" -#: selfdrive/ui/layouts/onboarding.py:115 +#: openpilot/selfdrive/ui/layouts/onboarding.py:119 #, python-format msgid "Decline" msgstr "Decline" -#: selfdrive/ui/layouts/onboarding.py:148 +#: openpilot/selfdrive/ui/layouts/onboarding.py:152 #, python-format msgid "Decline, uninstall openpilot" msgstr "Decline, uninstall openpilot" -#: selfdrive/ui/layouts/settings/settings.py:67 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:64 msgid "Developer" msgstr "Developer" -#: selfdrive/ui/layouts/settings/settings.py:62 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:59 msgid "Device" msgstr "Device" -#: selfdrive/ui/layouts/settings/toggles.py:58 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:58 #, python-format msgid "Disengage on Accelerator Pedal" msgstr "Disengage on Accelerator Pedal" -#: selfdrive/ui/layouts/settings/device.py:184 +#: openpilot/selfdrive/ui/layouts/settings/device.py:176 #, python-format msgid "Disengage to Power Off" msgstr "Disengage to Power Off" -#: selfdrive/ui/layouts/settings/device.py:172 +#: openpilot/selfdrive/ui/layouts/settings/device.py:164 #, python-format msgid "Disengage to Reboot" msgstr "Disengage to Reboot" -#: selfdrive/ui/layouts/settings/device.py:103 +#: openpilot/selfdrive/ui/layouts/settings/device.py:95 #, python-format msgid "Disengage to Reset Calibration" msgstr "Disengage to Reset Calibration" -#: selfdrive/ui/layouts/settings/toggles.py:32 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:32 msgid "Display speed in km/h instead of mph." msgstr "Display speed in km/h instead of mph." -#: selfdrive/ui/layouts/settings/device.py:59 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 #, python-format msgid "Dongle ID" msgstr "Dongle ID" -#: selfdrive/ui/layouts/settings/software.py:50 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 #, python-format msgid "Download" msgstr "Download" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "Driver Camera" msgstr "Driver Camera" -#: selfdrive/ui/layouts/settings/toggles.py:96 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:96 #, python-format msgid "Driving Personality" msgstr "Driving Personality" -#: system/ui/widgets/network.py:123 system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:136 #, python-format msgid "EDIT" msgstr "EDIT" -#: selfdrive/ui/layouts/sidebar.py:138 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 msgid "ERROR" msgstr "ERROR" -#: selfdrive/ui/layouts/sidebar.py:45 +#: openpilot/selfdrive/ui/layouts/sidebar.py:45 msgid "ETH" msgstr "ETH" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "EXPERIMENTAL MODE ON" msgstr "EXPERIMENTAL MODE ON" -#: selfdrive/ui/layouts/settings/developer.py:166 -#: selfdrive/ui/layouts/settings/toggles.py:228 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:229 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:180 #, python-format msgid "Enable" msgstr "Enable" -#: selfdrive/ui/layouts/settings/developer.py:39 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:39 #, python-format msgid "Enable ADB" msgstr "Enable ADB" -#: selfdrive/ui/layouts/settings/toggles.py:64 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:64 #, python-format msgid "Enable Lane Departure Warnings" msgstr "Enable Lane Departure Warnings" -#: system/ui/widgets/network.py:129 +#: system/ui/widgets/network.py:126 #, python-format msgid "Enable Roaming" msgstr "Enable Roaming" -#: selfdrive/ui/layouts/settings/developer.py:48 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:48 #, python-format msgid "Enable SSH" msgstr "Enable SSH" -#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:117 #, python-format msgid "Enable Tethering" msgstr "Enable Tethering" -#: selfdrive/ui/layouts/settings/toggles.py:30 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:30 msgid "Enable driver monitoring even when openpilot is not engaged." msgstr "Enable driver monitoring even when openpilot is not engaged." -#: selfdrive/ui/layouts/settings/toggles.py:46 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:46 #, python-format msgid "Enable openpilot" msgstr "Enable openpilot" -#: selfdrive/ui/layouts/settings/toggles.py:189 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:190 #, python-format -msgid "" -"Enable the openpilot longitudinal control (alpha) toggle to allow " -"Experimental mode." -msgstr "" -"Enable the openpilot longitudinal control (alpha) toggle to allow " -"Experimental mode." +msgid "Enable the openpilot longitudinal control (alpha) toggle to allow Experimental mode." +msgstr "Enable the openpilot longitudinal control (alpha) toggle to allow Experimental mode." -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "Enter APN" msgstr "Enter APN" -#: system/ui/widgets/network.py:241 +#: system/ui/widgets/network.py:243 #, python-format msgid "Enter SSID" msgstr "Enter SSID" -#: system/ui/widgets/network.py:254 +#: system/ui/widgets/network.py:257 #, python-format msgid "Enter new tethering password" msgstr "Enter new tethering password" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:320 #, python-format msgid "Enter password" msgstr "Enter password" -#: selfdrive/ui/widgets/ssh_key.py:89 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:89 #, python-format msgid "Enter your GitHub username" msgstr "Enter your GitHub username" -#: system/ui/widgets/list_view.py:123 system/ui/widgets/list_view.py:160 +#: system/ui/widgets/list_view.py:123 +#: system/ui/widgets/list_view.py:160 #, python-format msgid "Error" msgstr "Error" -#: selfdrive/ui/layouts/settings/toggles.py:52 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:52 #, python-format msgid "Experimental Mode" msgstr "Experimental Mode" -#: selfdrive/ui/layouts/settings/toggles.py:181 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:182 #, python-format -msgid "" -"Experimental mode is currently unavailable on this car since the car's stock " -"ACC is used for longitudinal control." -msgstr "" -"Experimental mode is currently unavailable on this car since the car's stock " -"ACC is used for longitudinal control." +msgid "Experimental mode is currently unavailable on this car since the car's stock ACC is used for longitudinal control." +msgstr "Experimental mode is currently unavailable on this car since the car's stock ACC is used for longitudinal control." -#: system/ui/widgets/network.py:373 +#: system/ui/widgets/network.py:380 #, python-format msgid "FORGETTING..." msgstr "FORGETTING..." -#: selfdrive/ui/widgets/setup.py:44 +#: openpilot/selfdrive/ui/widgets/setup.py:43 #, python-format msgid "Finish Setup" msgstr "Finish Setup" -#: selfdrive/ui/layouts/settings/settings.py:66 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:63 msgid "Firehose" msgstr "Firehose" -#: selfdrive/ui/layouts/settings/firehose.py:18 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:10 msgid "Firehose Mode" msgstr "Firehose Mode" -#: selfdrive/ui/layouts/settings/firehose.py:25 -msgid "" -"For maximum effectiveness, bring your device inside and connect to a good " -"USB-C adapter and Wi-Fi weekly.\n" -"\n" -"Firehose Mode can also work while you're driving if connected to a hotspot " -"or unlimited SIM card.\n" -"\n" -"\n" -"Frequently Asked Questions\n" -"\n" -"Does it matter how or where I drive? Nope, just drive as you normally " -"would.\n" -"\n" -"Do all of my segments get pulled in Firehose Mode? No, we selectively pull a " -"subset of your segments.\n" -"\n" -"What's a good USB-C adapter? Any fast phone or laptop charger should be " -"fine.\n" -"\n" -"Does it matter which software I run? Yes, only upstream openpilot (and " -"particular forks) are able to be used for training." -msgstr "" -"For maximum effectiveness, bring your device inside and connect to a good " -"USB-C adapter and Wi-Fi weekly.\n" -"\n" -"Firehose Mode can also work while you're driving if connected to a hotspot " -"or unlimited SIM card.\n" -"\n" -"\n" -"Frequently Asked Questions\n" -"\n" -"Does it matter how or where I drive? Nope, just drive as you normally " -"would.\n" -"\n" -"Do all of my segments get pulled in Firehose Mode? No, we selectively pull a " -"subset of your segments.\n" -"\n" -"What's a good USB-C adapter? Any fast phone or laptop charger should be " -"fine.\n" -"\n" -"Does it matter which software I run? Yes, only upstream openpilot (and " -"particular forks) are able to be used for training." - -#: system/ui/widgets/network.py:318 system/ui/widgets/network.py:451 +#: system/ui/widgets/network.py:458 +#: system/ui/widgets/network.py:326 #, python-format msgid "Forget" msgstr "Forget" -#: system/ui/widgets/network.py:319 +#: system/ui/widgets/network.py:327 #, python-format msgid "Forget Wi-Fi Network \"{}\"?" msgstr "Forget Wi-Fi Network \"{}\"?" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 msgid "GOOD" msgstr "GOOD" -#: selfdrive/ui/widgets/pairing_dialog.py:128 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:117 #, python-format msgid "Go to https://connect.comma.ai on your phone" msgstr "Go to https://connect.comma.ai on your phone" -#: selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "HIGH" msgstr "HIGH" -#: system/ui/widgets/network.py:155 +#: system/ui/widgets/network.py:152 #, python-format msgid "Hidden Network" msgstr "Hidden Network" -#: selfdrive/ui/layouts/settings/firehose.py:140 -#, python-format -msgid "INACTIVE: connect to an unmetered network" -msgstr "INACTIVE: connect to an unmetered network" - -#: selfdrive/ui/layouts/settings/software.py:53 -#: selfdrive/ui/layouts/settings/software.py:136 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 +#: openpilot/selfdrive/ui/layouts/settings/software.py:146 #, python-format msgid "INSTALL" msgstr "INSTALL" -#: system/ui/widgets/network.py:150 +#: system/ui/widgets/network.py:147 #, python-format msgid "IP Address" msgstr "IP Address" -#: selfdrive/ui/layouts/settings/software.py:53 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 #, python-format msgid "Install Update" msgstr "Install Update" -#: selfdrive/ui/layouts/settings/developer.py:56 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:56 #, python-format msgid "Joystick Debug Mode" msgstr "Joystick Debug Mode" -#: selfdrive/ui/widgets/ssh_key.py:29 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:29 msgid "LOADING" msgstr "LOADING" -#: selfdrive/ui/layouts/sidebar.py:48 +#: openpilot/selfdrive/ui/layouts/sidebar.py:48 msgid "LTE" msgstr "LTE" -#: selfdrive/ui/layouts/settings/developer.py:64 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:64 #, python-format msgid "Longitudinal Maneuver Mode" msgstr "Longitudinal Maneuver Mode" -#: selfdrive/ui/onroad/hud_renderer.py:148 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:148 #, python-format msgid "MAX" msgstr "MAX" -#: selfdrive/ui/widgets/setup.py:75 +#: openpilot/selfdrive/ui/widgets/setup.py:74 #, python-format -msgid "" -"Maximize your training data uploads to improve openpilot's driving models." -msgstr "" -"Maximize your training data uploads to improve openpilot's driving models." +msgid "Maximize your training data uploads to improve openpilot's driving models." +msgstr "Maximize your training data uploads to improve openpilot's driving models." -#: selfdrive/ui/layouts/settings/device.py:59 -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "N/A" msgstr "N/A" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "NO" msgstr "NO" -#: selfdrive/ui/layouts/settings/settings.py:63 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:60 msgid "Network" msgstr "Network" -#: selfdrive/ui/widgets/ssh_key.py:114 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:115 #, python-format msgid "No SSH keys found" msgstr "No SSH keys found" -#: selfdrive/ui/widgets/ssh_key.py:126 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:127 #, python-format msgid "No SSH keys found for user '{}'" msgstr "No SSH keys found for user '{}'" -#: selfdrive/ui/widgets/offroad_alerts.py:320 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:321 #, python-format msgid "No release notes available." msgstr "No release notes available." -#: selfdrive/ui/layouts/sidebar.py:73 selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 msgid "OFFLINE" msgstr "OFFLINE" -#: system/ui/widgets/html_render.py:263 system/ui/widgets/confirm_dialog.py:93 -#: selfdrive/ui/layouts/sidebar.py:127 +#: system/ui/widgets/confirm_dialog.py:93 +#: system/ui/widgets/html_render.py:263 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 #, python-format msgid "OK" msgstr "OK" -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 msgid "ONLINE" msgstr "ONLINE" -#: selfdrive/ui/widgets/setup.py:20 +#: openpilot/selfdrive/ui/widgets/setup.py:19 #, python-format msgid "Open" msgstr "Open" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "PAIR" msgstr "PAIR" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "PANDA" msgstr "PANDA" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "PREVIEW" msgstr "PREVIEW" -#: selfdrive/ui/widgets/prime.py:44 +#: openpilot/selfdrive/ui/widgets/prime.py:44 #, python-format msgid "PRIME FEATURES:" msgstr "PRIME FEATURES:" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "Pair Device" msgstr "Pair Device" -#: selfdrive/ui/widgets/setup.py:19 +#: openpilot/selfdrive/ui/widgets/setup.py:18 #, python-format msgid "Pair device" msgstr "Pair device" -#: selfdrive/ui/widgets/pairing_dialog.py:103 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:92 #, python-format msgid "Pair your device to your comma account" msgstr "Pair your device to your comma account" -#: selfdrive/ui/widgets/setup.py:48 selfdrive/ui/layouts/settings/device.py:24 +#: openpilot/selfdrive/ui/widgets/setup.py:47 +#: openpilot/selfdrive/ui/layouts/settings/device.py:23 #, python-format -msgid "" -"Pair your device with comma connect (connect.comma.ai) and claim your comma " -"prime offer." -msgstr "" -"Pair your device with comma connect (connect.comma.ai) and claim your comma " -"prime offer." +msgid "Pair your device with comma connect (connect.comma.ai) and claim your comma prime offer." +msgstr "Pair your device with comma connect (connect.comma.ai) and claim your comma prime offer." -#: selfdrive/ui/widgets/setup.py:91 +#: openpilot/selfdrive/ui/widgets/setup.py:91 #, python-format msgid "Please connect to Wi-Fi to complete initial pairing" msgstr "Please connect to Wi-Fi to complete initial pairing" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Power Off" msgstr "Power Off" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Prevent large data uploads when on a metered Wi-Fi connection" msgstr "Prevent large data uploads when on a metered Wi-Fi connection" -#: system/ui/widgets/network.py:135 +#: system/ui/widgets/network.py:132 #, python-format msgid "Prevent large data uploads when on a metered cellular connection" msgstr "Prevent large data uploads when on a metered cellular connection" -#: selfdrive/ui/layouts/settings/device.py:25 -msgid "" -"Preview the driver facing camera to ensure that driver monitoring has good " -"visibility. (vehicle must be off)" -msgstr "" -"Preview the driver facing camera to ensure that driver monitoring has good " -"visibility. (vehicle must be off)" +#: openpilot/selfdrive/ui/layouts/settings/device.py:24 +msgid "Preview the driver facing camera to ensure that driver monitoring has good visibility. (vehicle must be off)" +msgstr "Preview the driver facing camera to ensure that driver monitoring has good visibility. (vehicle must be off)" -#: selfdrive/ui/widgets/pairing_dialog.py:161 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:150 #, python-format msgid "QR Code Error" msgstr "QR Code Error" -#: selfdrive/ui/widgets/ssh_key.py:31 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:31 msgid "REMOVE" msgstr "REMOVE" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "RESET" msgstr "RESET" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "REVIEW" msgstr "REVIEW" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Reboot" msgstr "Reboot" -#: selfdrive/ui/onroad/alert_renderer.py:66 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:66 #, python-format msgid "Reboot Device" msgstr "Reboot Device" -#: selfdrive/ui/widgets/offroad_alerts.py:112 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:112 #, python-format msgid "Reboot and Update" msgstr "Reboot and Update" -#: selfdrive/ui/layouts/settings/toggles.py:27 -msgid "" -"Receive alerts to steer back into the lane when your vehicle drifts over a " -"detected lane line without a turn signal activated while driving over 31 mph " -"(50 km/h)." -msgstr "" -"Receive alerts to steer back into the lane when your vehicle drifts over a " -"detected lane line without a turn signal activated while driving over 31 mph " -"(50 km/h)." - -#: selfdrive/ui/layouts/settings/toggles.py:76 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:76 #, python-format msgid "Record and Upload Driver Camera" msgstr "Record and Upload Driver Camera" -#: selfdrive/ui/layouts/settings/toggles.py:82 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:82 #, python-format msgid "Record and Upload Microphone Audio" msgstr "Record and Upload Microphone Audio" -#: selfdrive/ui/layouts/settings/toggles.py:33 -msgid "" -"Record and store microphone audio while driving. The audio will be included " -"in the dashcam video in comma connect." -msgstr "" -"Record and store microphone audio while driving. The audio will be included " -"in the dashcam video in comma connect." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:33 +msgid "Record and store microphone audio while driving. The audio will be included in the dashcam video in comma connect." +msgstr "Record and store microphone audio while driving. The audio will be included in the dashcam video in comma connect." -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "Regulatory" msgstr "Regulatory" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Relaxed" msgstr "Relaxed" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote access" msgstr "Remote access" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote snapshots" msgstr "Remote snapshots" -#: selfdrive/ui/widgets/ssh_key.py:123 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:124 #, python-format msgid "Request timed out" msgstr "Request timed out" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Reset" msgstr "Reset" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "Reset Calibration" msgstr "Reset Calibration" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "Review Training Guide" msgstr "Review Training Guide" -#: selfdrive/ui/layouts/settings/device.py:27 +#: openpilot/selfdrive/ui/layouts/settings/device.py:26 msgid "Review the rules, features, and limitations of openpilot" msgstr "Review the rules, features, and limitations of openpilot" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "SELECT" msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:53 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:53 #, python-format msgid "SSH Keys" msgstr "SSH Keys" -#: system/ui/widgets/network.py:310 +#: system/ui/widgets/network.py:316 #, python-format msgid "Scanning Wi-Fi networks..." msgstr "Scanning Wi-Fi networks..." -#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/option_dialog.py:37 #, python-format msgid "Select" msgstr "Select" -#: selfdrive/ui/layouts/settings/software.py:183 +#: openpilot/selfdrive/ui/layouts/settings/software.py:203 #, python-format msgid "Select a branch" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:91 +#: openpilot/selfdrive/ui/layouts/settings/device.py:89 #, python-format msgid "Select a language" msgstr "Select a language" -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "Serial" msgstr "Serial" -#: selfdrive/ui/widgets/offroad_alerts.py:106 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:106 #, python-format msgid "Snooze Update" msgstr "Snooze Update" -#: selfdrive/ui/layouts/settings/settings.py:65 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:62 msgid "Software" msgstr "Software" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Standard" msgstr "Standard" -#: selfdrive/ui/layouts/settings/toggles.py:22 -msgid "" -"Standard is recommended. In aggressive mode, openpilot will follow lead cars " -"closer and be more aggressive with the gas and brake. In relaxed mode " -"openpilot will stay further away from lead cars. On supported cars, you can " -"cycle through these personalities with your steering wheel distance button." -msgstr "" -"Standard is recommended. In aggressive mode, openpilot will follow lead cars " -"closer and be more aggressive with the gas and brake. In relaxed mode " -"openpilot will stay further away from lead cars. On supported cars, you can " -"cycle through these personalities with your steering wheel distance button." - -#: selfdrive/ui/onroad/alert_renderer.py:59 -#: selfdrive/ui/onroad/alert_renderer.py:65 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:59 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:65 #, python-format msgid "System Unresponsive" msgstr "System Unresponsive" -#: selfdrive/ui/onroad/alert_renderer.py:58 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:58 #, python-format msgid "TAKE CONTROL IMMEDIATELY" msgstr "TAKE CONTROL IMMEDIATELY" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 -#: selfdrive/ui/layouts/sidebar.py:127 selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "TEMP" msgstr "TEMP" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "Target Branch" msgstr "" -#: system/ui/widgets/network.py:124 +#: system/ui/widgets/network.py:121 #, python-format msgid "Tethering Password" msgstr "Tethering Password" -#: selfdrive/ui/layouts/settings/settings.py:64 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:61 msgid "Toggles" msgstr "Toggles" -#: selfdrive/ui/layouts/settings/software.py:72 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:79 +#, python-format +msgid "UI Debug Mode" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "UNINSTALL" msgstr "UNINSTALL" -#: selfdrive/ui/layouts/home.py:155 +#: openpilot/selfdrive/ui/layouts/home.py:155 #, python-format msgid "UPDATE" msgstr "UPDATE" -#: selfdrive/ui/layouts/settings/software.py:72 -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "Uninstall" msgstr "Uninstall" -#: selfdrive/ui/layouts/sidebar.py:117 +#: openpilot/selfdrive/ui/layouts/sidebar.py:117 msgid "Unknown" msgstr "Unknown" -#: selfdrive/ui/layouts/settings/software.py:48 +#: openpilot/selfdrive/ui/layouts/settings/software.py:55 #, python-format msgid "Updates are only downloaded while the car is off." msgstr "Updates are only downloaded while the car is off." -#: selfdrive/ui/widgets/prime.py:33 +#: openpilot/selfdrive/ui/widgets/prime.py:33 #, python-format msgid "Upgrade Now" msgstr "Upgrade Now" -#: selfdrive/ui/layouts/settings/toggles.py:31 -msgid "" -"Upload data from the driver facing camera and help improve the driver " -"monitoring algorithm." -msgstr "" -"Upload data from the driver facing camera and help improve the driver " -"monitoring algorithm." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:31 +msgid "Upload data from the driver facing camera and help improve the driver monitoring algorithm." +msgstr "Upload data from the driver facing camera and help improve the driver monitoring algorithm." -#: selfdrive/ui/layouts/settings/toggles.py:88 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:88 #, python-format msgid "Use Metric System" msgstr "Use Metric System" -#: selfdrive/ui/layouts/settings/toggles.py:17 -msgid "" -"Use the openpilot system for adaptive cruise control and lane keep driver " -"assistance. Your attention is required at all times to use this feature." -msgstr "" -"Use the openpilot system for adaptive cruise control and lane keep driver " -"assistance. Your attention is required at all times to use this feature." - -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 msgid "VEHICLE" msgstr "VEHICLE" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "VIEW" msgstr "VIEW" -#: selfdrive/ui/onroad/alert_renderer.py:52 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:52 #, python-format msgid "Waiting to start" msgstr "Waiting to start" -#: selfdrive/ui/layouts/settings/developer.py:19 -msgid "" -"Warning: This grants SSH access to all public keys in your GitHub settings. " -"Never enter a GitHub username other than your own. A comma employee will " -"NEVER ask you to add their GitHub username." -msgstr "" -"Warning: This grants SSH access to all public keys in your GitHub settings. " -"Never enter a GitHub username other than your own. A comma employee will " -"NEVER ask you to add their GitHub username." - -#: selfdrive/ui/layouts/onboarding.py:111 +#: openpilot/selfdrive/ui/layouts/onboarding.py:115 #, python-format msgid "Welcome to openpilot" msgstr "Welcome to openpilot" -#: selfdrive/ui/layouts/settings/toggles.py:20 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:20 msgid "When enabled, pressing the accelerator pedal will disengage openpilot." msgstr "When enabled, pressing the accelerator pedal will disengage openpilot." -#: selfdrive/ui/layouts/sidebar.py:44 +#: openpilot/selfdrive/ui/layouts/sidebar.py:44 msgid "Wi-Fi" msgstr "Wi-Fi" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Wi-Fi Network Metered" msgstr "Wi-Fi Network Metered" -#: system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:320 #, python-format msgid "Wrong password" msgstr "Wrong password" -#: selfdrive/ui/layouts/onboarding.py:145 +#: openpilot/selfdrive/ui/layouts/onboarding.py:149 #, python-format msgid "You must accept the Terms and Conditions in order to use openpilot." msgstr "You must accept the Terms and Conditions in order to use openpilot." -#: selfdrive/ui/layouts/onboarding.py:112 +#: openpilot/selfdrive/ui/layouts/onboarding.py:116 #, python-format -msgid "" -"You must accept the Terms and Conditions to use openpilot. Read the latest " -"terms at https://comma.ai/terms before continuing." -msgstr "" -"You must accept the Terms and Conditions to use openpilot. Read the latest " -"terms at https://comma.ai/terms before continuing." +msgid "You must accept the Terms and Conditions to use openpilot. Read the latest terms at https://comma.ai/terms before continuing." +msgstr "You must accept the Terms and Conditions to use openpilot. Read the latest terms at https://comma.ai/terms before continuing." -#: selfdrive/ui/onroad/driver_camera_dialog.py:34 +#: openpilot/selfdrive/ui/onroad/driver_camera_dialog.py:38 #, python-format msgid "camera starting" msgstr "camera starting" -#: selfdrive/ui/widgets/prime.py:63 +#: openpilot/selfdrive/ui/layouts/settings/software.py:19 +#, python-format +msgid "checking..." +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:63 #, python-format msgid "comma prime" msgstr "comma prime" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "default" msgstr "default" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "down" msgstr "down" -#: selfdrive/ui/layouts/settings/software.py:106 +#: openpilot/selfdrive/ui/layouts/settings/software.py:20 +#, python-format +msgid "downloading..." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:116 #, python-format msgid "failed to check for update" msgstr "failed to check for update" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: openpilot/selfdrive/ui/layouts/settings/software.py:21 +#, python-format +msgid "finalizing update..." +msgstr "" + +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:321 #, python-format msgid "for \"{}\"" msgstr "for \"{}\"" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "km/h" msgstr "km/h" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "leave blank for automatic configuration" msgstr "leave blank for automatic configuration" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "left" msgstr "left" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "metered" msgstr "metered" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "mph" msgstr "mph" -#: selfdrive/ui/layouts/settings/software.py:20 +#: openpilot/selfdrive/ui/layouts/settings/software.py:27 #, python-format msgid "never" msgstr "never" -#: selfdrive/ui/layouts/settings/software.py:31 +#: openpilot/selfdrive/ui/layouts/settings/software.py:38 #, python-format msgid "now" msgstr "now" -#: selfdrive/ui/layouts/settings/developer.py:71 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:71 #, python-format msgid "openpilot Longitudinal Control (Alpha)" msgstr "openpilot Longitudinal Control (Alpha)" -#: selfdrive/ui/onroad/alert_renderer.py:51 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:51 #, python-format msgid "openpilot Unavailable" msgstr "openpilot Unavailable" -#: selfdrive/ui/layouts/settings/toggles.py:158 -#, python-format -msgid "" -"openpilot defaults to driving in chill mode. Experimental mode enables alpha-" -"level features that aren't ready for chill mode. Experimental features are " -"listed below:

End-to-End Longitudinal Control


Let the driving " -"model control the gas and brakes. openpilot will drive as it thinks a human " -"would, including stopping for red lights and stop signs. Since the driving " -"model decides the speed to drive, the set speed will only act as an upper " -"bound. This is an alpha quality feature; mistakes should be expected." -"

New Driving Visualization


The driving visualization will " -"transition to the road-facing wide-angle camera at low speeds to better show " -"some turns. The Experimental mode logo will also be shown in the top right " -"corner." -msgstr "" -"openpilot defaults to driving in chill mode. Experimental mode enables alpha-" -"level features that aren't ready for chill mode. Experimental features are " -"listed below:

End-to-End Longitudinal Control


Let the driving " -"model control the gas and brakes. openpilot will drive as it thinks a human " -"would, including stopping for red lights and stop signs. Since the driving " -"model decides the speed to drive, the set speed will only act as an upper " -"bound. This is an alpha quality feature; mistakes should be expected." -"

New Driving Visualization


The driving visualization will " -"transition to the road-facing wide-angle camera at low speeds to better show " -"some turns. The Experimental mode logo will also be shown in the top right " -"corner." - -#: selfdrive/ui/layouts/settings/device.py:165 -#, python-format -msgid "" -"openpilot is continuously calibrating, resetting is rarely required. " -"Resetting calibration will restart openpilot if the car is powered on." -msgstr "" -"openpilot is continuously calibrating, resetting is rarely required. " -"Resetting calibration will restart openpilot if the car is powered on." - -#: selfdrive/ui/layouts/settings/firehose.py:20 -msgid "" -"openpilot learns to drive by watching humans, like you, drive.\n" -"\n" -"Firehose Mode allows you to maximize your training data uploads to improve " -"openpilot's driving models. More data means bigger models, which means " -"better Experimental Mode." -msgstr "" -"openpilot learns to drive by watching humans, like you, drive.\n" -"\n" -"Firehose Mode allows you to maximize your training data uploads to improve " -"openpilot's driving models. More data means bigger models, which means " -"better Experimental Mode." - -#: selfdrive/ui/layouts/settings/toggles.py:183 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:184 #, python-format msgid "openpilot longitudinal control may come in a future update." msgstr "openpilot longitudinal control may come in a future update." -#: selfdrive/ui/layouts/settings/device.py:26 -msgid "" -"openpilot requires the device to be mounted within 4° left or right and " -"within 5° up or 9° down." -msgstr "" -"openpilot requires the device to be mounted within 4° left or right and " -"within 5° up or 9° down." +#: openpilot/selfdrive/ui/layouts/settings/device.py:25 +msgid "openpilot requires the device to be mounted within 4° left or right and within 5° up or 9° down." +msgstr "openpilot requires the device to be mounted within 4° left or right and within 5° up or 9° down." -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "right" msgstr "right" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "unmetered" msgstr "unmetered" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "up" msgstr "up" -#: selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:127 #, python-format msgid "up to date, last checked never" msgstr "up to date, last checked never" -#: selfdrive/ui/layouts/settings/software.py:115 +#: openpilot/selfdrive/ui/layouts/settings/software.py:125 #, python-format msgid "up to date, last checked {}" msgstr "up to date, last checked {}" -#: selfdrive/ui/layouts/settings/software.py:109 +#: openpilot/selfdrive/ui/layouts/settings/software.py:119 #, python-format msgid "update available" msgstr "update available" -#: selfdrive/ui/layouts/home.py:169 +#: openpilot/selfdrive/ui/layouts/home.py:169 #, python-format msgid "{} ALERT" msgid_plural "{} ALERTS" msgstr[0] "{} ALERT" msgstr[1] "{} ALERTS" -#: selfdrive/ui/layouts/settings/software.py:40 +#: openpilot/selfdrive/ui/layouts/settings/software.py:47 #, python-format msgid "{} day ago" msgid_plural "{} days ago" msgstr[0] "{} day ago" msgstr[1] "{} days ago" -#: selfdrive/ui/layouts/settings/software.py:37 +#: openpilot/selfdrive/ui/layouts/settings/software.py:44 #, python-format msgid "{} hour ago" msgid_plural "{} hours ago" msgstr[0] "{} hour ago" msgstr[1] "{} hours ago" -#: selfdrive/ui/layouts/settings/software.py:34 +#: openpilot/selfdrive/ui/layouts/settings/software.py:41 #, python-format msgid "{} minute ago" msgid_plural "{} minutes ago" msgstr[0] "{} minute ago" msgstr[1] "{} minutes ago" -#: selfdrive/ui/layouts/settings/firehose.py:111 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:70 #, python-format msgid "{} segment of your driving is in the training dataset so far." msgid_plural "{} segments of your driving is in the training dataset so far." msgstr[0] "{} segment of your driving is in the training dataset so far." msgstr[1] "{} segments of your driving is in the training dataset so far." -#: selfdrive/ui/widgets/prime.py:62 +#: openpilot/selfdrive/ui/widgets/prime.py:62 #, python-format msgid "✓ SUBSCRIBED" msgstr "✓ SUBSCRIBED" -#: selfdrive/ui/widgets/setup.py:22 +#: openpilot/selfdrive/ui/widgets/setup.py:21 #, python-format msgid "🔥 Firehose Mode 🔥" msgstr "🔥 Firehose Mode 🔥" + diff --git a/selfdrive/ui/translations/app_es.po b/selfdrive/ui/translations/app_es.po index 59b9e6dfdb..35188fe2fc 100644 --- a/selfdrive/ui/translations/app_es.po +++ b/selfdrive/ui/translations/app_es.po @@ -17,1209 +17,1018 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1);\n" -#: selfdrive/ui/layouts/settings/device.py:160 +#: openpilot/selfdrive/ui/layouts/settings/device.py:152 #, python-format msgid " Steering torque response calibration is complete." msgstr " La calibración de respuesta de par de dirección está completa." -#: selfdrive/ui/layouts/settings/device.py:158 +#: openpilot/selfdrive/ui/layouts/settings/device.py:150 #, python-format msgid " Steering torque response calibration is {}% complete." msgstr " La calibración de respuesta de par de dirección está {}% completa." -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid " Your device is pointed {:.1f}° {} and {:.1f}° {}." msgstr " Tu dispositivo está orientado {:.1f}° {} y {:.1f}° {}." -#: selfdrive/ui/layouts/sidebar.py:43 +#: openpilot/selfdrive/ui/layouts/sidebar.py:43 msgid "--" msgstr "--" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "1 year of drive storage" msgstr "1 año de almacenamiento de conducción" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "24/7 LTE connectivity" msgstr "Conectividad LTE 24/7" -#: selfdrive/ui/layouts/sidebar.py:46 +#: openpilot/selfdrive/ui/layouts/sidebar.py:46 msgid "2G" msgstr "2G" -#: selfdrive/ui/layouts/sidebar.py:47 +#: openpilot/selfdrive/ui/layouts/sidebar.py:47 msgid "3G" msgstr "3G" -#: selfdrive/ui/layouts/sidebar.py:49 +#: openpilot/selfdrive/ui/layouts/sidebar.py:49 msgid "5G" msgstr "5G" -#: selfdrive/ui/layouts/settings/developer.py:23 -msgid "" -"WARNING: openpilot longitudinal control is in alpha for this car and will " -"disable Automatic Emergency Braking (AEB).

On this car, openpilot " -"defaults to the car's built-in ACC instead of openpilot's longitudinal " -"control. Enable this to switch to openpilot longitudinal control. Enabling " -"Experimental mode is recommended when enabling openpilot longitudinal " -"control alpha. Changing this setting will restart openpilot if the car is " -"powered on." -msgstr "" -"ADVERTENCIA: el control longitudinal de openpilot está en alpha para este " -"coche y deshabilitará el Frenado Automático de Emergencia (AEB).

En este coche, openpilot usa por defecto el ACC integrado del " -"coche en lugar del control longitudinal de openpilot. Activa esto para " -"cambiar al control longitudinal de openpilot. Se recomienda activar el modo " -"Experimental al habilitar el control longitudinal de openpilot (alpha)." - -#: selfdrive/ui/layouts/settings/device.py:148 +#: openpilot/selfdrive/ui/layouts/settings/device.py:140 #, python-format msgid "

Steering lag calibration is complete." msgstr "" -#: selfdrive/ui/layouts/settings/device.py:146 +#: openpilot/selfdrive/ui/layouts/settings/device.py:138 #, python-format msgid "

Steering lag calibration is {}% complete." msgstr "" -#: selfdrive/ui/layouts/settings/firehose.py:138 -#, python-format -msgid "ACTIVE" -msgstr "ACTIVO" - -#: selfdrive/ui/layouts/settings/developer.py:15 -msgid "" -"ADB (Android Debug Bridge) allows connecting to your device over USB or over " -"the network. See https://docs.comma.ai/how-to/connect-to-comma for more info." -msgstr "" -"ADB (Android Debug Bridge) permite conectar tu dispositivo por USB o por la " -"red. Consulta https://docs.comma.ai/how-to/connect-to-comma para más " -"información." - -#: selfdrive/ui/widgets/ssh_key.py:30 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:30 msgid "ADD" msgstr "AÑADIR" -#: system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:136 #, python-format msgid "APN Setting" msgstr "" -#: selfdrive/ui/widgets/offroad_alerts.py:109 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:109 #, python-format msgid "Acknowledge Excessive Actuation" msgstr "Reconocer actuación excesiva" -#: system/ui/widgets/network.py:74 system/ui/widgets/network.py:95 +#: system/ui/widgets/network.py:92 +#: system/ui/widgets/network.py:74 #, python-format msgid "Advanced" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Aggressive" msgstr "Agresivo" -#: selfdrive/ui/layouts/onboarding.py:116 +#: openpilot/selfdrive/ui/layouts/onboarding.py:120 #, python-format msgid "Agree" msgstr "Aceptar" -#: selfdrive/ui/layouts/settings/toggles.py:70 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:70 #, python-format msgid "Always-On Driver Monitoring" msgstr "Supervisión del conductor siempre activa" -#: selfdrive/ui/layouts/settings/toggles.py:186 -#, python-format -msgid "" -"An alpha version of openpilot longitudinal control can be tested, along with " -"Experimental mode, on non-release branches." -msgstr "" -"Se puede probar una versión alpha del control longitudinal de openpilot, " -"junto con el modo Experimental, en ramas que no son de lanzamiento." - -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 #, python-format msgid "Are you sure you want to power off?" msgstr "¿Seguro que quieres apagar?" -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 #, python-format msgid "Are you sure you want to reboot?" msgstr "¿Seguro que quieres reiniciar?" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Are you sure you want to reset calibration?" msgstr "¿Seguro que quieres restablecer la calibración?" -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 #, python-format msgid "Are you sure you want to uninstall?" msgstr "¿Seguro que quieres desinstalar?" -#: system/ui/widgets/network.py:99 selfdrive/ui/layouts/onboarding.py:147 +#: system/ui/widgets/network.py:96 +#: openpilot/selfdrive/ui/layouts/onboarding.py:151 #, python-format msgid "Back" msgstr "Atrás" -#: selfdrive/ui/widgets/prime.py:38 +#: openpilot/selfdrive/ui/widgets/prime.py:38 #, python-format msgid "Become a comma prime member at connect.comma.ai" msgstr "Hazte miembro de comma prime en connect.comma.ai" -#: selfdrive/ui/widgets/pairing_dialog.py:130 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:119 #, python-format msgid "Bookmark connect.comma.ai to your home screen to use it like an app" -msgstr "" -"Añade connect.comma.ai a tu pantalla de inicio para usarlo como una app" +msgstr "Añade connect.comma.ai a tu pantalla de inicio para usarlo como una app" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "CHANGE" msgstr "CAMBIAR" -#: selfdrive/ui/layouts/settings/software.py:50 -#: selfdrive/ui/layouts/settings/software.py:107 -#: selfdrive/ui/layouts/settings/software.py:118 -#: selfdrive/ui/layouts/settings/software.py:147 +#: openpilot/selfdrive/ui/layouts/settings/software.py:157 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 +#: openpilot/selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:128 #, python-format msgid "CHECK" msgstr "COMPROBAR" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "CHILL MODE ON" msgstr "MODO CHILL ACTIVADO" -#: system/ui/widgets/network.py:155 selfdrive/ui/layouts/sidebar.py:73 -#: selfdrive/ui/layouts/sidebar.py:134 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:138 +#: system/ui/widgets/network.py:152 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 #, python-format msgid "CONNECT" msgstr "CONECTAR" -#: system/ui/widgets/network.py:369 +#: system/ui/widgets/network.py:376 #, python-format msgid "CONNECTING..." msgstr "CONECTAR" -#: system/ui/widgets/confirm_dialog.py:23 system/ui/widgets/option_dialog.py:35 -#: system/ui/widgets/keyboard.py:81 system/ui/widgets/network.py:318 +#: system/ui/widgets/network.py:326 +#: system/ui/widgets/confirm_dialog.py:24 +#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/keyboard.py:83 #, python-format msgid "Cancel" msgstr "" -#: system/ui/widgets/network.py:134 +#: system/ui/widgets/network.py:131 #, python-format msgid "Cellular Metered" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "Change Language" msgstr "Cambiar idioma" -#: selfdrive/ui/layouts/settings/toggles.py:125 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:125 #, python-format msgid "Changing this setting will restart openpilot if the car is powered on." -msgstr "" -" Cambiar esta configuración reiniciará openpilot si el coche está encendido." +msgstr " Cambiar esta configuración reiniciará openpilot si el coche está encendido." -#: selfdrive/ui/widgets/pairing_dialog.py:129 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:118 #, python-format msgid "Click \"add new device\" and scan the QR code on the right" -msgstr "" -"Haz clic en \"añadir nuevo dispositivo\" y escanea el código QR de la derecha" +msgstr "Haz clic en \"añadir nuevo dispositivo\" y escanea el código QR de la derecha" -#: selfdrive/ui/widgets/offroad_alerts.py:104 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:104 #, python-format msgid "Close" msgstr "Cerrar" -#: selfdrive/ui/layouts/settings/software.py:49 +#: openpilot/selfdrive/ui/layouts/settings/software.py:56 #, python-format msgid "Current Version" msgstr "Versión actual" -#: selfdrive/ui/layouts/settings/software.py:110 +#: openpilot/selfdrive/ui/layouts/settings/software.py:120 #, python-format msgid "DOWNLOAD" msgstr "DESCARGAR" -#: selfdrive/ui/layouts/onboarding.py:115 +#: openpilot/selfdrive/ui/layouts/onboarding.py:119 #, python-format msgid "Decline" msgstr "Rechazar" -#: selfdrive/ui/layouts/onboarding.py:148 +#: openpilot/selfdrive/ui/layouts/onboarding.py:152 #, python-format msgid "Decline, uninstall openpilot" msgstr "Rechazar, desinstalar openpilot" -#: selfdrive/ui/layouts/settings/settings.py:67 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:64 msgid "Developer" msgstr "Desarrollador" -#: selfdrive/ui/layouts/settings/settings.py:62 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:59 msgid "Device" msgstr "Dispositivo" -#: selfdrive/ui/layouts/settings/toggles.py:58 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:58 #, python-format msgid "Disengage on Accelerator Pedal" msgstr "Desactivar con el pedal del acelerador" -#: selfdrive/ui/layouts/settings/device.py:184 +#: openpilot/selfdrive/ui/layouts/settings/device.py:176 #, python-format msgid "Disengage to Power Off" msgstr "Desactivar para apagar" -#: selfdrive/ui/layouts/settings/device.py:172 +#: openpilot/selfdrive/ui/layouts/settings/device.py:164 #, python-format msgid "Disengage to Reboot" msgstr "Desactivar para reiniciar" -#: selfdrive/ui/layouts/settings/device.py:103 +#: openpilot/selfdrive/ui/layouts/settings/device.py:95 #, python-format msgid "Disengage to Reset Calibration" msgstr "Desactivar para restablecer la calibración" -#: selfdrive/ui/layouts/settings/toggles.py:32 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:32 msgid "Display speed in km/h instead of mph." msgstr "Mostrar la velocidad en km/h en lugar de mph." -#: selfdrive/ui/layouts/settings/device.py:59 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 #, python-format msgid "Dongle ID" msgstr "ID del dongle" -#: selfdrive/ui/layouts/settings/software.py:50 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 #, python-format msgid "Download" msgstr "Descargar" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "Driver Camera" msgstr "Cámara del conductor" -#: selfdrive/ui/layouts/settings/toggles.py:96 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:96 #, python-format msgid "Driving Personality" msgstr "Estilo de conducción" -#: system/ui/widgets/network.py:123 system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:136 #, python-format msgid "EDIT" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:138 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 msgid "ERROR" msgstr "ERROR" -#: selfdrive/ui/layouts/sidebar.py:45 +#: openpilot/selfdrive/ui/layouts/sidebar.py:45 msgid "ETH" msgstr "ETH" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "EXPERIMENTAL MODE ON" msgstr "MODO EXPERIMENTAL ACTIVADO" -#: selfdrive/ui/layouts/settings/developer.py:166 -#: selfdrive/ui/layouts/settings/toggles.py:228 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:229 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:180 #, python-format msgid "Enable" msgstr "Activar" -#: selfdrive/ui/layouts/settings/developer.py:39 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:39 #, python-format msgid "Enable ADB" msgstr "Activar ADB" -#: selfdrive/ui/layouts/settings/toggles.py:64 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:64 #, python-format msgid "Enable Lane Departure Warnings" msgstr "Activar advertencias de salida de carril" -#: system/ui/widgets/network.py:129 +#: system/ui/widgets/network.py:126 #, python-format msgid "Enable Roaming" msgstr "Activar openpilot" -#: selfdrive/ui/layouts/settings/developer.py:48 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:48 #, python-format msgid "Enable SSH" msgstr "Activar SSH" -#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:117 #, python-format msgid "Enable Tethering" msgstr "Activar advertencias de salida de carril" -#: selfdrive/ui/layouts/settings/toggles.py:30 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:30 msgid "Enable driver monitoring even when openpilot is not engaged." -msgstr "" -"Activar la supervisión del conductor incluso cuando openpilot no esté " -"activado." +msgstr "Activar la supervisión del conductor incluso cuando openpilot no esté activado." -#: selfdrive/ui/layouts/settings/toggles.py:46 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:46 #, python-format msgid "Enable openpilot" msgstr "Activar openpilot" -#: selfdrive/ui/layouts/settings/toggles.py:189 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:190 #, python-format -msgid "" -"Enable the openpilot longitudinal control (alpha) toggle to allow " -"Experimental mode." -msgstr "" -"Activa el interruptor de control longitudinal de openpilot (alpha) para " -"permitir el modo Experimental." +msgid "Enable the openpilot longitudinal control (alpha) toggle to allow Experimental mode." +msgstr "Activa el interruptor de control longitudinal de openpilot (alpha) para permitir el modo Experimental." -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "Enter APN" msgstr "" -#: system/ui/widgets/network.py:241 +#: system/ui/widgets/network.py:243 #, python-format msgid "Enter SSID" msgstr "" -#: system/ui/widgets/network.py:254 +#: system/ui/widgets/network.py:257 #, python-format msgid "Enter new tethering password" msgstr "" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:320 #, python-format msgid "Enter password" msgstr "" -#: selfdrive/ui/widgets/ssh_key.py:89 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:89 #, python-format msgid "Enter your GitHub username" msgstr "Introduce tu nombre de usuario de GitHub" -#: system/ui/widgets/list_view.py:123 system/ui/widgets/list_view.py:160 +#: system/ui/widgets/list_view.py:123 +#: system/ui/widgets/list_view.py:160 #, python-format msgid "Error" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:52 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:52 #, python-format msgid "Experimental Mode" msgstr "Modo experimental" -#: selfdrive/ui/layouts/settings/toggles.py:181 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:182 #, python-format -msgid "" -"Experimental mode is currently unavailable on this car since the car's stock " -"ACC is used for longitudinal control." -msgstr "" -"El modo experimental no está disponible actualmente en este coche, ya que se " -"usa el ACC de fábrica para el control longitudinal." +msgid "Experimental mode is currently unavailable on this car since the car's stock ACC is used for longitudinal control." +msgstr "El modo experimental no está disponible actualmente en este coche, ya que se usa el ACC de fábrica para el control longitudinal." -#: system/ui/widgets/network.py:373 +#: system/ui/widgets/network.py:380 #, python-format msgid "FORGETTING..." msgstr "" -#: selfdrive/ui/widgets/setup.py:44 +#: openpilot/selfdrive/ui/widgets/setup.py:43 #, python-format msgid "Finish Setup" msgstr "Finalizar configuración" -#: selfdrive/ui/layouts/settings/settings.py:66 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:63 msgid "Firehose" msgstr "Firehose" -#: selfdrive/ui/layouts/settings/firehose.py:18 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:10 msgid "Firehose Mode" msgstr "Modo Firehose" -#: selfdrive/ui/layouts/settings/firehose.py:25 -msgid "" -"For maximum effectiveness, bring your device inside and connect to a good " -"USB-C adapter and Wi-Fi weekly.\n" -"\n" -"Firehose Mode can also work while you're driving if connected to a hotspot " -"or unlimited SIM card.\n" -"\n" -"\n" -"Frequently Asked Questions\n" -"\n" -"Does it matter how or where I drive? Nope, just drive as you normally " -"would.\n" -"\n" -"Do all of my segments get pulled in Firehose Mode? No, we selectively pull a " -"subset of your segments.\n" -"\n" -"What's a good USB-C adapter? Any fast phone or laptop charger should be " -"fine.\n" -"\n" -"Does it matter which software I run? Yes, only upstream openpilot (and " -"particular forks) are able to be used for training." -msgstr "" -"Para la máxima efectividad, lleva tu dispositivo al interior y conéctalo " -"semanalmente a un buen adaptador USB‑C y Wi‑Fi.\n" -"\n" -"El Modo Firehose también puede funcionar mientras conduces si está conectado " -"a un hotspot o a una SIM ilimitada.\n" -"\n" -"\n" -"Preguntas frecuentes\n" -"\n" -"¿Importa cómo o dónde conduzco? No, conduce como normalmente lo harías.\n" -"\n" -"¿Se suben todos mis segmentos en el Modo Firehose? No, seleccionamos un " -"subconjunto de tus segmentos.\n" -"\n" -"¿Qué es un buen adaptador USB‑C? Cualquier cargador rápido de teléfono o " -"laptop sirve.\n" -"\n" -"¿Importa qué software ejecuto? Sí, solo openpilot upstream (y forks " -"particulares) pueden usarse para entrenamiento." - -#: system/ui/widgets/network.py:318 system/ui/widgets/network.py:451 +#: system/ui/widgets/network.py:458 +#: system/ui/widgets/network.py:326 #, python-format msgid "Forget" msgstr "" -#: system/ui/widgets/network.py:319 +#: system/ui/widgets/network.py:327 #, python-format msgid "Forget Wi-Fi Network \"{}\"?" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 msgid "GOOD" msgstr "BUENO" -#: selfdrive/ui/widgets/pairing_dialog.py:128 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:117 #, python-format msgid "Go to https://connect.comma.ai on your phone" msgstr "Ve a https://connect.comma.ai en tu teléfono" -#: selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "HIGH" msgstr "ALTO" -#: system/ui/widgets/network.py:155 +#: system/ui/widgets/network.py:152 #, python-format msgid "Hidden Network" msgstr "Red" -#: selfdrive/ui/layouts/settings/firehose.py:140 -#, python-format -msgid "INACTIVE: connect to an unmetered network" -msgstr "INACTIVO: conéctate a una red sin límites" - -#: selfdrive/ui/layouts/settings/software.py:53 -#: selfdrive/ui/layouts/settings/software.py:136 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 +#: openpilot/selfdrive/ui/layouts/settings/software.py:146 #, python-format msgid "INSTALL" msgstr "INSTALAR" -#: system/ui/widgets/network.py:150 +#: system/ui/widgets/network.py:147 #, python-format msgid "IP Address" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:53 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 #, python-format msgid "Install Update" msgstr "Instalar actualización" -#: selfdrive/ui/layouts/settings/developer.py:56 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:56 #, python-format msgid "Joystick Debug Mode" msgstr "Modo de depuración de joystick" -#: selfdrive/ui/widgets/ssh_key.py:29 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:29 msgid "LOADING" msgstr "CARGANDO" -#: selfdrive/ui/layouts/sidebar.py:48 +#: openpilot/selfdrive/ui/layouts/sidebar.py:48 msgid "LTE" msgstr "LTE" -#: selfdrive/ui/layouts/settings/developer.py:64 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:64 #, python-format msgid "Longitudinal Maneuver Mode" msgstr "Modo de maniobra longitudinal" -#: selfdrive/ui/onroad/hud_renderer.py:148 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:148 #, python-format msgid "MAX" msgstr "MÁX" -#: selfdrive/ui/widgets/setup.py:75 +#: openpilot/selfdrive/ui/widgets/setup.py:74 #, python-format -msgid "" -"Maximize your training data uploads to improve openpilot's driving models." -msgstr "" -"Maximiza tus cargas de datos de entrenamiento para mejorar los modelos de " -"conducción de openpilot." +msgid "Maximize your training data uploads to improve openpilot's driving models." +msgstr "Maximiza tus cargas de datos de entrenamiento para mejorar los modelos de conducción de openpilot." -#: selfdrive/ui/layouts/settings/device.py:59 -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "N/A" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "NO" msgstr "NO" -#: selfdrive/ui/layouts/settings/settings.py:63 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:60 msgid "Network" msgstr "Red" -#: selfdrive/ui/widgets/ssh_key.py:114 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:115 #, python-format msgid "No SSH keys found" msgstr "No se encontraron claves SSH" -#: selfdrive/ui/widgets/ssh_key.py:126 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:127 #, python-format msgid "No SSH keys found for user '{}'" msgstr "No se encontraron claves SSH para el usuario '{username}'" -#: selfdrive/ui/widgets/offroad_alerts.py:320 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:321 #, python-format msgid "No release notes available." msgstr "No hay notas de versión disponibles." -#: selfdrive/ui/layouts/sidebar.py:73 selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 msgid "OFFLINE" msgstr "SIN CONEXIÓN" -#: system/ui/widgets/html_render.py:263 system/ui/widgets/confirm_dialog.py:93 -#: selfdrive/ui/layouts/sidebar.py:127 +#: system/ui/widgets/confirm_dialog.py:93 +#: system/ui/widgets/html_render.py:263 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 #, python-format msgid "OK" msgstr "OK" -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 msgid "ONLINE" msgstr "EN LÍNEA" -#: selfdrive/ui/widgets/setup.py:20 +#: openpilot/selfdrive/ui/widgets/setup.py:19 #, python-format msgid "Open" msgstr "Abrir" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "PAIR" msgstr "EMPAREJAR" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "PANDA" msgstr "PANDA" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "PREVIEW" msgstr "VISTA PREVIA" -#: selfdrive/ui/widgets/prime.py:44 +#: openpilot/selfdrive/ui/widgets/prime.py:44 #, python-format msgid "PRIME FEATURES:" msgstr "FUNCIONES PRIME:" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "Pair Device" msgstr "Emparejar dispositivo" -#: selfdrive/ui/widgets/setup.py:19 +#: openpilot/selfdrive/ui/widgets/setup.py:18 #, python-format msgid "Pair device" msgstr "Emparejar dispositivo" -#: selfdrive/ui/widgets/pairing_dialog.py:103 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:92 #, python-format msgid "Pair your device to your comma account" msgstr "Empareja tu dispositivo con tu cuenta de comma" -#: selfdrive/ui/widgets/setup.py:48 selfdrive/ui/layouts/settings/device.py:24 +#: openpilot/selfdrive/ui/widgets/setup.py:47 +#: openpilot/selfdrive/ui/layouts/settings/device.py:23 #, python-format -msgid "" -"Pair your device with comma connect (connect.comma.ai) and claim your comma " -"prime offer." -msgstr "" -"Empareja tu dispositivo con comma connect (connect.comma.ai) y reclama tu " -"oferta de comma prime." +msgid "Pair your device with comma connect (connect.comma.ai) and claim your comma prime offer." +msgstr "Empareja tu dispositivo con comma connect (connect.comma.ai) y reclama tu oferta de comma prime." -#: selfdrive/ui/widgets/setup.py:91 +#: openpilot/selfdrive/ui/widgets/setup.py:91 #, python-format msgid "Please connect to Wi-Fi to complete initial pairing" msgstr "Conéctate a Wi‑Fi para completar el emparejamiento inicial" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Power Off" msgstr "Apagar" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Prevent large data uploads when on a metered Wi-Fi connection" msgstr "" -#: system/ui/widgets/network.py:135 +#: system/ui/widgets/network.py:132 #, python-format msgid "Prevent large data uploads when on a metered cellular connection" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:25 -msgid "" -"Preview the driver facing camera to ensure that driver monitoring has good " -"visibility. (vehicle must be off)" -msgstr "" -"Previsualiza la cámara hacia el conductor para asegurarte de que la " -"supervisión del conductor tenga buena visibilidad. (el vehículo debe estar " -"apagado)" +#: openpilot/selfdrive/ui/layouts/settings/device.py:24 +msgid "Preview the driver facing camera to ensure that driver monitoring has good visibility. (vehicle must be off)" +msgstr "Previsualiza la cámara hacia el conductor para asegurarte de que la supervisión del conductor tenga buena visibilidad. (el vehículo debe estar apagado)" -#: selfdrive/ui/widgets/pairing_dialog.py:161 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:150 #, python-format msgid "QR Code Error" msgstr "Error de código QR" -#: selfdrive/ui/widgets/ssh_key.py:31 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:31 msgid "REMOVE" msgstr "ELIMINAR" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "RESET" msgstr "RESTABLECER" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "REVIEW" msgstr "REVISAR" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Reboot" msgstr "Reiniciar" -#: selfdrive/ui/onroad/alert_renderer.py:66 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:66 #, python-format msgid "Reboot Device" msgstr "Reiniciar dispositivo" -#: selfdrive/ui/widgets/offroad_alerts.py:112 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:112 #, python-format msgid "Reboot and Update" msgstr "Reiniciar y actualizar" -#: selfdrive/ui/layouts/settings/toggles.py:27 -msgid "" -"Receive alerts to steer back into the lane when your vehicle drifts over a " -"detected lane line without a turn signal activated while driving over 31 mph " -"(50 km/h)." -msgstr "" -"Recibe alertas para volver al carril cuando tu vehículo se desvíe sobre una " -"línea de carril detectada sin la direccional activada mientras conduces a " -"más de 31 mph (50 km/h)." - -#: selfdrive/ui/layouts/settings/toggles.py:76 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:76 #, python-format msgid "Record and Upload Driver Camera" msgstr "Grabar y subir cámara del conductor" -#: selfdrive/ui/layouts/settings/toggles.py:82 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:82 #, python-format msgid "Record and Upload Microphone Audio" msgstr "Grabar y subir audio del micrófono" -#: selfdrive/ui/layouts/settings/toggles.py:33 -msgid "" -"Record and store microphone audio while driving. The audio will be included " -"in the dashcam video in comma connect." -msgstr "" -"Grabar y almacenar audio del micrófono mientras conduces. El audio se " -"incluirá en el video de la dashcam en comma connect." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:33 +msgid "Record and store microphone audio while driving. The audio will be included in the dashcam video in comma connect." +msgstr "Grabar y almacenar audio del micrófono mientras conduces. El audio se incluirá en el video de la dashcam en comma connect." -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "Regulatory" msgstr "Reglamentario" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Relaxed" msgstr "Relajado" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote access" msgstr "Acceso remoto" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote snapshots" msgstr "Capturas remotas" -#: selfdrive/ui/widgets/ssh_key.py:123 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:124 #, python-format msgid "Request timed out" msgstr "Se agotó el tiempo de espera de la solicitud" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Reset" msgstr "Restablecer" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "Reset Calibration" msgstr "Restablecer calibración" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "Review Training Guide" msgstr "Revisar guía de entrenamiento" -#: selfdrive/ui/layouts/settings/device.py:27 +#: openpilot/selfdrive/ui/layouts/settings/device.py:26 msgid "Review the rules, features, and limitations of openpilot" msgstr "Revisa las reglas, funciones y limitaciones de openpilot" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "SELECT" msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:53 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:53 #, python-format msgid "SSH Keys" msgstr "" -#: system/ui/widgets/network.py:310 +#: system/ui/widgets/network.py:316 #, python-format msgid "Scanning Wi-Fi networks..." msgstr "" -#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/option_dialog.py:37 #, python-format msgid "Select" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:183 +#: openpilot/selfdrive/ui/layouts/settings/software.py:203 #, python-format msgid "Select a branch" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:91 +#: openpilot/selfdrive/ui/layouts/settings/device.py:89 #, python-format msgid "Select a language" msgstr "Selecciona un idioma" -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "Serial" msgstr "Número de serie" -#: selfdrive/ui/widgets/offroad_alerts.py:106 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:106 #, python-format msgid "Snooze Update" msgstr "Posponer actualización" -#: selfdrive/ui/layouts/settings/settings.py:65 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:62 msgid "Software" msgstr "Software" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Standard" msgstr "Estándar" -#: selfdrive/ui/layouts/settings/toggles.py:22 -msgid "" -"Standard is recommended. In aggressive mode, openpilot will follow lead cars " -"closer and be more aggressive with the gas and brake. In relaxed mode " -"openpilot will stay further away from lead cars. On supported cars, you can " -"cycle through these personalities with your steering wheel distance button." -msgstr "" -"Se recomienda Estándar. En modo agresivo, openpilot seguirá más de cerca a " -"los coches delanteros y será más agresivo con el acelerador y el freno. En " -"modo relajado, openpilot se mantendrá más lejos de los coches delanteros. En " -"coches compatibles, puedes cambiar entre estas personalidades con el botón " -"de distancia del volante." - -#: selfdrive/ui/onroad/alert_renderer.py:59 -#: selfdrive/ui/onroad/alert_renderer.py:65 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:59 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:65 #, python-format msgid "System Unresponsive" msgstr "Sistema sin respuesta" -#: selfdrive/ui/onroad/alert_renderer.py:58 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:58 #, python-format msgid "TAKE CONTROL IMMEDIATELY" msgstr "TOME EL CONTROL INMEDIATAMENTE" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 -#: selfdrive/ui/layouts/sidebar.py:127 selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "TEMP" msgstr "TEMP" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "Target Branch" msgstr "" -#: system/ui/widgets/network.py:124 +#: system/ui/widgets/network.py:121 #, python-format msgid "Tethering Password" msgstr "" -#: selfdrive/ui/layouts/settings/settings.py:64 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:61 msgid "Toggles" msgstr "Interruptores" -#: selfdrive/ui/layouts/settings/software.py:72 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:79 +#, python-format +msgid "UI Debug Mode" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "UNINSTALL" msgstr "DESINSTALAR" -#: selfdrive/ui/layouts/home.py:155 +#: openpilot/selfdrive/ui/layouts/home.py:155 #, python-format msgid "UPDATE" msgstr "ACTUALIZAR" -#: selfdrive/ui/layouts/settings/software.py:72 -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "Uninstall" msgstr "Desinstalar" -#: selfdrive/ui/layouts/sidebar.py:117 +#: openpilot/selfdrive/ui/layouts/sidebar.py:117 msgid "Unknown" msgstr "Desconocido" -#: selfdrive/ui/layouts/settings/software.py:48 +#: openpilot/selfdrive/ui/layouts/settings/software.py:55 #, python-format msgid "Updates are only downloaded while the car is off." msgstr "Las actualizaciones solo se descargan cuando el coche está apagado." -#: selfdrive/ui/widgets/prime.py:33 +#: openpilot/selfdrive/ui/widgets/prime.py:33 #, python-format msgid "Upgrade Now" msgstr "Mejorar ahora" -#: selfdrive/ui/layouts/settings/toggles.py:31 -msgid "" -"Upload data from the driver facing camera and help improve the driver " -"monitoring algorithm." -msgstr "" -"Sube datos de la cámara orientada al conductor y ayuda a mejorar el " -"algoritmo de supervisión del conductor." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:31 +msgid "Upload data from the driver facing camera and help improve the driver monitoring algorithm." +msgstr "Sube datos de la cámara orientada al conductor y ayuda a mejorar el algoritmo de supervisión del conductor." -#: selfdrive/ui/layouts/settings/toggles.py:88 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:88 #, python-format msgid "Use Metric System" msgstr "Usar sistema métrico" -#: selfdrive/ui/layouts/settings/toggles.py:17 -msgid "" -"Use the openpilot system for adaptive cruise control and lane keep driver " -"assistance. Your attention is required at all times to use this feature." -msgstr "" -"Usa el sistema openpilot para control de crucero adaptativo y asistencia de " -"mantenimiento de carril. Tu atención se requiere en todo momento para usar " -"esta función." - -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 msgid "VEHICLE" msgstr "VEHÍCULO" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "VIEW" msgstr "VER" -#: selfdrive/ui/onroad/alert_renderer.py:52 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:52 #, python-format msgid "Waiting to start" msgstr "Esperando para iniciar" -#: selfdrive/ui/layouts/settings/developer.py:19 -msgid "" -"Warning: This grants SSH access to all public keys in your GitHub settings. " -"Never enter a GitHub username other than your own. A comma employee will " -"NEVER ask you to add their GitHub username." -msgstr "" -"Advertencia: Esto otorga acceso SSH a todas las claves públicas en tu " -"configuración de GitHub. Nunca introduzcas un nombre de usuario de GitHub " -"que no sea el tuyo. Un empleado de comma NUNCA te pedirá que agregues su " -"nombre de usuario de GitHub." - -#: selfdrive/ui/layouts/onboarding.py:111 +#: openpilot/selfdrive/ui/layouts/onboarding.py:115 #, python-format msgid "Welcome to openpilot" msgstr "Bienvenido a openpilot" -#: selfdrive/ui/layouts/settings/toggles.py:20 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:20 msgid "When enabled, pressing the accelerator pedal will disengage openpilot." -msgstr "" -"Cuando está activado, al presionar el pedal del acelerador se desactivará " -"openpilot." +msgstr "Cuando está activado, al presionar el pedal del acelerador se desactivará openpilot." -#: selfdrive/ui/layouts/sidebar.py:44 +#: openpilot/selfdrive/ui/layouts/sidebar.py:44 msgid "Wi-Fi" msgstr "Wi‑Fi" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Wi-Fi Network Metered" msgstr "" -#: system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:320 #, python-format msgid "Wrong password" msgstr "" -#: selfdrive/ui/layouts/onboarding.py:145 +#: openpilot/selfdrive/ui/layouts/onboarding.py:149 #, python-format msgid "You must accept the Terms and Conditions in order to use openpilot." msgstr "Debes aceptar los Términos y Condiciones para poder usar openpilot." -#: selfdrive/ui/layouts/onboarding.py:112 +#: openpilot/selfdrive/ui/layouts/onboarding.py:116 #, python-format -msgid "" -"You must accept the Terms and Conditions to use openpilot. Read the latest " -"terms at https://comma.ai/terms before continuing." -msgstr "" -"Debes aceptar los Términos y Condiciones para usar openpilot. Lee los " -"términos más recientes en https://comma.ai/terms antes de continuar." +msgid "You must accept the Terms and Conditions to use openpilot. Read the latest terms at https://comma.ai/terms before continuing." +msgstr "Debes aceptar los Términos y Condiciones para usar openpilot. Lee los términos más recientes en https://comma.ai/terms antes de continuar." -#: selfdrive/ui/onroad/driver_camera_dialog.py:34 +#: openpilot/selfdrive/ui/onroad/driver_camera_dialog.py:38 #, python-format msgid "camera starting" msgstr "iniciando cámara" -#: selfdrive/ui/widgets/prime.py:63 +#: openpilot/selfdrive/ui/layouts/settings/software.py:19 +#, python-format +msgid "checking..." +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:63 #, python-format msgid "comma prime" msgstr "comma prime" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "default" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "down" msgstr "abajo" -#: selfdrive/ui/layouts/settings/software.py:106 +#: openpilot/selfdrive/ui/layouts/settings/software.py:20 +#, python-format +msgid "downloading..." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:116 #, python-format msgid "failed to check for update" msgstr "Error al buscar actualizaciones" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: openpilot/selfdrive/ui/layouts/settings/software.py:21 +#, python-format +msgid "finalizing update..." +msgstr "" + +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:321 #, python-format msgid "for \"{}\"" msgstr "" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "km/h" msgstr "km/h" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "leave blank for automatic configuration" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "left" msgstr "izquierda" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "metered" msgstr "" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "mph" msgstr "mph" -#: selfdrive/ui/layouts/settings/software.py:20 +#: openpilot/selfdrive/ui/layouts/settings/software.py:27 #, python-format msgid "never" msgstr "nunca" -#: selfdrive/ui/layouts/settings/software.py:31 +#: openpilot/selfdrive/ui/layouts/settings/software.py:38 #, python-format msgid "now" msgstr "ahora" -#: selfdrive/ui/layouts/settings/developer.py:71 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:71 #, python-format msgid "openpilot Longitudinal Control (Alpha)" msgstr "Control longitudinal de openpilot (Alpha)" -#: selfdrive/ui/onroad/alert_renderer.py:51 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:51 #, python-format msgid "openpilot Unavailable" msgstr "openpilot no disponible" -#: selfdrive/ui/layouts/settings/toggles.py:158 -#, python-format -msgid "" -"openpilot defaults to driving in chill mode. Experimental mode enables alpha-" -"level features that aren't ready for chill mode. Experimental features are " -"listed below:

End-to-End Longitudinal Control


Let the driving " -"model control the gas and brakes. openpilot will drive as it thinks a human " -"would, including stopping for red lights and stop signs. Since the driving " -"model decides the speed to drive, the set speed will only act as an upper " -"bound. This is an alpha quality feature; mistakes should be expected." -"

New Driving Visualization


The driving visualization will " -"transition to the road-facing wide-angle camera at low speeds to better show " -"some turns. The Experimental mode logo will also be shown in the top right " -"corner." -msgstr "" -"openpilot conduce por defecto en modo chill. El modo Experimental habilita " -"funciones de nivel alpha que no están listas para el modo chill. Las " -"funciones experimentales se enumeran a continuación:

Control " -"longitudinal de extremo a extremo


Deja que el modelo de conducción " -"controle el acelerador y los frenos. openpilot conducirá como piensa que lo " -"haría un humano, incluyendo detenerse en luces rojas y señales de alto. Dado " -"que el modelo decide la velocidad a la que conducir, la velocidad " -"establecida solo actuará como límite superior. Esta es una función de " -"calidad alpha; se deben esperar errores.

Nueva visualización de " -"conducción


La visualización de conducción hará la transición a la " -"cámara gran angular orientada a la carretera a bajas velocidades para " -"mostrar mejor algunos giros. El logotipo del modo Experimental también se " -"mostrará en la esquina superior derecha." - -#: selfdrive/ui/layouts/settings/device.py:165 -#, python-format -msgid "" -"openpilot is continuously calibrating, resetting is rarely required. " -"Resetting calibration will restart openpilot if the car is powered on." -msgstr "" -" Cambiar esta configuración reiniciará openpilot si el coche está encendido." - -#: selfdrive/ui/layouts/settings/firehose.py:20 -msgid "" -"openpilot learns to drive by watching humans, like you, drive.\n" -"\n" -"Firehose Mode allows you to maximize your training data uploads to improve " -"openpilot's driving models. More data means bigger models, which means " -"better Experimental Mode." -msgstr "" -"openpilot aprende a conducir observando a humanos, como tú, conducir.\n" -"\n" -"El Modo Firehose te permite maximizar tus cargas de datos de entrenamiento " -"para mejorar los modelos de conducción de openpilot. Más datos significan " -"modelos más grandes, lo que significa un mejor Modo Experimental." - -#: selfdrive/ui/layouts/settings/toggles.py:183 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:184 #, python-format msgid "openpilot longitudinal control may come in a future update." -msgstr "" -"El control longitudinal de openpilot podría llegar en una actualización " -"futura." +msgstr "El control longitudinal de openpilot podría llegar en una actualización futura." -#: selfdrive/ui/layouts/settings/device.py:26 -msgid "" -"openpilot requires the device to be mounted within 4° left or right and " -"within 5° up or 9° down." -msgstr "" -"openpilot requiere que el dispositivo esté montado dentro de 4° a izquierda " -"o derecha y dentro de 5° hacia arriba o 9° hacia abajo." +#: openpilot/selfdrive/ui/layouts/settings/device.py:25 +msgid "openpilot requires the device to be mounted within 4° left or right and within 5° up or 9° down." +msgstr "openpilot requiere que el dispositivo esté montado dentro de 4° a izquierda o derecha y dentro de 5° hacia arriba o 9° hacia abajo." -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "right" msgstr "derecha" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "unmetered" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "up" msgstr "arriba" -#: selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:127 #, python-format msgid "up to date, last checked never" msgstr "actualizado, última comprobación: nunca" -#: selfdrive/ui/layouts/settings/software.py:115 +#: openpilot/selfdrive/ui/layouts/settings/software.py:125 #, python-format msgid "up to date, last checked {}" msgstr "actualizado, última comprobación: {}" -#: selfdrive/ui/layouts/settings/software.py:109 +#: openpilot/selfdrive/ui/layouts/settings/software.py:119 #, python-format msgid "update available" msgstr "actualización disponible" -#: selfdrive/ui/layouts/home.py:169 +#: openpilot/selfdrive/ui/layouts/home.py:169 #, python-format msgid "{} ALERT" msgid_plural "{} ALERTS" msgstr[0] "{} ALERTA" msgstr[1] "{} ALERTAS" -#: selfdrive/ui/layouts/settings/software.py:40 +#: openpilot/selfdrive/ui/layouts/settings/software.py:47 #, python-format msgid "{} day ago" msgid_plural "{} days ago" msgstr[0] "hace {} día" msgstr[1] "hace {} días" -#: selfdrive/ui/layouts/settings/software.py:37 +#: openpilot/selfdrive/ui/layouts/settings/software.py:44 #, python-format msgid "{} hour ago" msgid_plural "{} hours ago" msgstr[0] "hace {} hora" msgstr[1] "hace {} horas" -#: selfdrive/ui/layouts/settings/software.py:34 +#: openpilot/selfdrive/ui/layouts/settings/software.py:41 #, python-format msgid "{} minute ago" msgid_plural "{} minutes ago" msgstr[0] "hace {} minuto" msgstr[1] "hace {} minutos" -#: selfdrive/ui/layouts/settings/firehose.py:111 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:70 #, python-format msgid "{} segment of your driving is in the training dataset so far." msgid_plural "{} segments of your driving is in the training dataset so far." -msgstr[0] "" -"{} segmento de tu conducción está en el conjunto de entrenamiento hasta " -"ahora." -msgstr[1] "" -"{} segmentos de tu conducción están en el conjunto de entrenamiento hasta " -"ahora." +msgstr[0] "{} segmento de tu conducción está en el conjunto de entrenamiento hasta ahora." +msgstr[1] "{} segmentos de tu conducción están en el conjunto de entrenamiento hasta ahora." -#: selfdrive/ui/widgets/prime.py:62 +#: openpilot/selfdrive/ui/widgets/prime.py:62 #, python-format msgid "✓ SUBSCRIBED" msgstr "✓ SUSCRITO" -#: selfdrive/ui/widgets/setup.py:22 +#: openpilot/selfdrive/ui/widgets/setup.py:21 #, python-format msgid "🔥 Firehose Mode 🔥" msgstr "🔥 Modo Firehose 🔥" + diff --git a/selfdrive/ui/translations/app_ja.po b/selfdrive/ui/translations/app_ja.po index ca8aac1515..41eb91dd58 100644 --- a/selfdrive/ui/translations/app_ja.po +++ b/selfdrive/ui/translations/app_ja.po @@ -17,1181 +17,1013 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=1; plural=0;\n" -#: selfdrive/ui/layouts/settings/device.py:160 +#: openpilot/selfdrive/ui/layouts/settings/device.py:152 #, python-format msgid " Steering torque response calibration is complete." msgstr " ステアリングトルク応答のキャリブレーションが完了しました。" -#: selfdrive/ui/layouts/settings/device.py:158 +#: openpilot/selfdrive/ui/layouts/settings/device.py:150 #, python-format msgid " Steering torque response calibration is {}% complete." msgstr " ステアリングトルク応答のキャリブレーションは{}%完了しました。" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid " Your device is pointed {:.1f}° {} and {:.1f}° {}." msgstr " デバイスは{:.1f}°{}、{:.1f}°{}の向きです。" -#: selfdrive/ui/layouts/sidebar.py:43 +#: openpilot/selfdrive/ui/layouts/sidebar.py:43 msgid "--" msgstr "--" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "1 year of drive storage" msgstr "走行データを1年間保存" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "24/7 LTE connectivity" msgstr "24時間365日のLTE接続" -#: selfdrive/ui/layouts/sidebar.py:46 +#: openpilot/selfdrive/ui/layouts/sidebar.py:46 msgid "2G" msgstr "2G" -#: selfdrive/ui/layouts/sidebar.py:47 +#: openpilot/selfdrive/ui/layouts/sidebar.py:47 msgid "3G" msgstr "3G" -#: selfdrive/ui/layouts/sidebar.py:49 +#: openpilot/selfdrive/ui/layouts/sidebar.py:49 msgid "5G" msgstr "5G" -#: selfdrive/ui/layouts/settings/developer.py:23 -msgid "" -"WARNING: openpilot longitudinal control is in alpha for this car and will " -"disable Automatic Emergency Braking (AEB).

On this car, openpilot " -"defaults to the car's built-in ACC instead of openpilot's longitudinal " -"control. Enable this to switch to openpilot longitudinal control. Enabling " -"Experimental mode is recommended when enabling openpilot longitudinal " -"control alpha. Changing this setting will restart openpilot if the car is " -"powered on." -msgstr "" -"警告: この車におけるopenpilotの縦制御はアルファ版であり、自動緊急ブレーキ" -"(AEB)を無効にします。

この車では、openpilotは縦制御として" -"openpilotではなく車両の内蔵ACCを既定で使用します。openpilotの縦制御に切り替え" -"るにはこの設定を有効にしてください。openpilot縦制御アルファを有効にする場合は" -"実験モードの有効化を推奨します。この設定を変更すると、車が起動中の場合は" -"openpilotが再起動します。" - -#: selfdrive/ui/layouts/settings/device.py:148 +#: openpilot/selfdrive/ui/layouts/settings/device.py:140 #, python-format msgid "

Steering lag calibration is complete." msgstr "

ステアリング遅延のキャリブレーションが完了しました。" -#: selfdrive/ui/layouts/settings/device.py:146 +#: openpilot/selfdrive/ui/layouts/settings/device.py:138 #, python-format msgid "

Steering lag calibration is {}% complete." msgstr "

ステアリング遅延のキャリブレーションは{}%完了しました。" -#: selfdrive/ui/layouts/settings/firehose.py:138 -#, python-format -msgid "ACTIVE" -msgstr "アクティブ" - -#: selfdrive/ui/layouts/settings/developer.py:15 -msgid "" -"ADB (Android Debug Bridge) allows connecting to your device over USB or over " -"the network. See https://docs.comma.ai/how-to/connect-to-comma for more info." -msgstr "" -"ADB(Android Debug Bridge)を使用すると、USBまたはネットワーク経由でデバイス" -"に接続できます。詳しくは https://docs.comma.ai/how-to/connect-to-comma を参照" -"してください。" - -#: selfdrive/ui/widgets/ssh_key.py:30 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:30 msgid "ADD" msgstr "追加" -#: system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:136 #, python-format msgid "APN Setting" msgstr "APN設定" -#: selfdrive/ui/widgets/offroad_alerts.py:109 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:109 #, python-format msgid "Acknowledge Excessive Actuation" msgstr "過度な作動を承認" -#: system/ui/widgets/network.py:74 system/ui/widgets/network.py:95 +#: system/ui/widgets/network.py:92 +#: system/ui/widgets/network.py:74 #, python-format msgid "Advanced" msgstr "詳細設定" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Aggressive" msgstr "アグレッシブ" -#: selfdrive/ui/layouts/onboarding.py:116 +#: openpilot/selfdrive/ui/layouts/onboarding.py:120 #, python-format msgid "Agree" msgstr "同意する" -#: selfdrive/ui/layouts/settings/toggles.py:70 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:70 #, python-format msgid "Always-On Driver Monitoring" msgstr "常時ドライバーモニタリング" -#: selfdrive/ui/layouts/settings/toggles.py:186 -#, python-format -msgid "" -"An alpha version of openpilot longitudinal control can be tested, along with " -"Experimental mode, on non-release branches." -msgstr "" -"openpilotの縦制御アルファ版は、実験モードと併せて非リリースブランチでテストで" -"きます。" - -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 #, python-format msgid "Are you sure you want to power off?" msgstr "本当に電源をオフにしますか?" -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 #, python-format msgid "Are you sure you want to reboot?" msgstr "本当に再起動しますか?" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Are you sure you want to reset calibration?" msgstr "本当にキャリブレーションをリセットしますか?" -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 #, python-format msgid "Are you sure you want to uninstall?" msgstr "本当にアンインストールしますか?" -#: system/ui/widgets/network.py:99 selfdrive/ui/layouts/onboarding.py:147 +#: system/ui/widgets/network.py:96 +#: openpilot/selfdrive/ui/layouts/onboarding.py:151 #, python-format msgid "Back" msgstr "戻る" -#: selfdrive/ui/widgets/prime.py:38 +#: openpilot/selfdrive/ui/widgets/prime.py:38 #, python-format msgid "Become a comma prime member at connect.comma.ai" msgstr "connect.comma.aiで comma prime に加入" -#: selfdrive/ui/widgets/pairing_dialog.py:130 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:119 #, python-format msgid "Bookmark connect.comma.ai to your home screen to use it like an app" msgstr "connect.comma.aiをホーム画面に追加してアプリのように使いましょう" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "CHANGE" msgstr "変更" -#: selfdrive/ui/layouts/settings/software.py:50 -#: selfdrive/ui/layouts/settings/software.py:107 -#: selfdrive/ui/layouts/settings/software.py:118 -#: selfdrive/ui/layouts/settings/software.py:147 +#: openpilot/selfdrive/ui/layouts/settings/software.py:157 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 +#: openpilot/selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:128 #, python-format msgid "CHECK" msgstr "確認" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "CHILL MODE ON" msgstr "チルモードON" -#: system/ui/widgets/network.py:155 selfdrive/ui/layouts/sidebar.py:73 -#: selfdrive/ui/layouts/sidebar.py:134 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:138 +#: system/ui/widgets/network.py:152 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 #, python-format msgid "CONNECT" msgstr "接続" -#: system/ui/widgets/network.py:369 +#: system/ui/widgets/network.py:376 #, python-format msgid "CONNECTING..." msgstr "接続中..." -#: system/ui/widgets/confirm_dialog.py:23 system/ui/widgets/option_dialog.py:35 -#: system/ui/widgets/keyboard.py:81 system/ui/widgets/network.py:318 +#: system/ui/widgets/network.py:326 +#: system/ui/widgets/confirm_dialog.py:24 +#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/keyboard.py:83 #, python-format msgid "Cancel" msgstr "キャンセル" -#: system/ui/widgets/network.py:134 +#: system/ui/widgets/network.py:131 #, python-format msgid "Cellular Metered" msgstr "従量課金の携帯回線" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "Change Language" msgstr "言語を変更" -#: selfdrive/ui/layouts/settings/toggles.py:125 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:125 #, python-format msgid "Changing this setting will restart openpilot if the car is powered on." msgstr "車が起動中の場合、この設定を変更するとopenpilotが再起動します。" -#: selfdrive/ui/widgets/pairing_dialog.py:129 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:118 #, python-format msgid "Click \"add new device\" and scan the QR code on the right" msgstr "\"add new device\"を押して右側のQRコードをスキャン" -#: selfdrive/ui/widgets/offroad_alerts.py:104 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:104 #, python-format msgid "Close" msgstr "閉じる" -#: selfdrive/ui/layouts/settings/software.py:49 +#: openpilot/selfdrive/ui/layouts/settings/software.py:56 #, python-format msgid "Current Version" msgstr "現在のバージョン" -#: selfdrive/ui/layouts/settings/software.py:110 +#: openpilot/selfdrive/ui/layouts/settings/software.py:120 #, python-format msgid "DOWNLOAD" msgstr "ダウンロード" -#: selfdrive/ui/layouts/onboarding.py:115 +#: openpilot/selfdrive/ui/layouts/onboarding.py:119 #, python-format msgid "Decline" msgstr "拒否する" -#: selfdrive/ui/layouts/onboarding.py:148 +#: openpilot/selfdrive/ui/layouts/onboarding.py:152 #, python-format msgid "Decline, uninstall openpilot" msgstr "拒否してopenpilotをアンインストール" -#: selfdrive/ui/layouts/settings/settings.py:67 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:64 msgid "Developer" msgstr "開発者" -#: selfdrive/ui/layouts/settings/settings.py:62 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:59 msgid "Device" msgstr "デバイス" -#: selfdrive/ui/layouts/settings/toggles.py:58 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:58 #, python-format msgid "Disengage on Accelerator Pedal" msgstr "アクセルで解除" -#: selfdrive/ui/layouts/settings/device.py:184 +#: openpilot/selfdrive/ui/layouts/settings/device.py:176 #, python-format msgid "Disengage to Power Off" msgstr "解除して電源オフ" -#: selfdrive/ui/layouts/settings/device.py:172 +#: openpilot/selfdrive/ui/layouts/settings/device.py:164 #, python-format msgid "Disengage to Reboot" msgstr "解除して再起動" -#: selfdrive/ui/layouts/settings/device.py:103 +#: openpilot/selfdrive/ui/layouts/settings/device.py:95 #, python-format msgid "Disengage to Reset Calibration" msgstr "解除してキャリブレーションをリセット" -#: selfdrive/ui/layouts/settings/toggles.py:32 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:32 msgid "Display speed in km/h instead of mph." msgstr "速度をmphではなくkm/hで表示します。" -#: selfdrive/ui/layouts/settings/device.py:59 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 #, python-format msgid "Dongle ID" msgstr "ドングルID" -#: selfdrive/ui/layouts/settings/software.py:50 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 #, python-format msgid "Download" msgstr "ダウンロード" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "Driver Camera" msgstr "ドライバーカメラ" -#: selfdrive/ui/layouts/settings/toggles.py:96 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:96 #, python-format msgid "Driving Personality" msgstr "走行性格" -#: system/ui/widgets/network.py:123 system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:136 #, python-format msgid "EDIT" msgstr "編集" -#: selfdrive/ui/layouts/sidebar.py:138 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 msgid "ERROR" msgstr "エラー" -#: selfdrive/ui/layouts/sidebar.py:45 +#: openpilot/selfdrive/ui/layouts/sidebar.py:45 msgid "ETH" msgstr "ETH" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "EXPERIMENTAL MODE ON" msgstr "実験モードON" -#: selfdrive/ui/layouts/settings/developer.py:166 -#: selfdrive/ui/layouts/settings/toggles.py:228 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:229 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:180 #, python-format msgid "Enable" msgstr "有効化" -#: selfdrive/ui/layouts/settings/developer.py:39 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:39 #, python-format msgid "Enable ADB" msgstr "ADBを有効化" -#: selfdrive/ui/layouts/settings/toggles.py:64 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:64 #, python-format msgid "Enable Lane Departure Warnings" msgstr "車線逸脱警報を有効化" -#: system/ui/widgets/network.py:129 +#: system/ui/widgets/network.py:126 #, python-format msgid "Enable Roaming" msgstr "ローミングを有効化" -#: selfdrive/ui/layouts/settings/developer.py:48 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:48 #, python-format msgid "Enable SSH" msgstr "SSHを有効化" -#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:117 #, python-format msgid "Enable Tethering" msgstr "テザリングを有効化" -#: selfdrive/ui/layouts/settings/toggles.py:30 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:30 msgid "Enable driver monitoring even when openpilot is not engaged." msgstr "openpilotが未作動でもドライバーモニタリングを有効にします。" -#: selfdrive/ui/layouts/settings/toggles.py:46 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:46 #, python-format msgid "Enable openpilot" msgstr "openpilotを有効化" -#: selfdrive/ui/layouts/settings/toggles.py:189 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:190 #, python-format -msgid "" -"Enable the openpilot longitudinal control (alpha) toggle to allow " -"Experimental mode." -msgstr "" -"openpilot縦制御(アルファ)のトグルを有効にすると実験モードが使用できます。" +msgid "Enable the openpilot longitudinal control (alpha) toggle to allow Experimental mode." +msgstr "openpilot縦制御(アルファ)のトグルを有効にすると実験モードが使用できます。" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "Enter APN" msgstr "APNを入力" -#: system/ui/widgets/network.py:241 +#: system/ui/widgets/network.py:243 #, python-format msgid "Enter SSID" msgstr "SSIDを入力" -#: system/ui/widgets/network.py:254 +#: system/ui/widgets/network.py:257 #, python-format msgid "Enter new tethering password" msgstr "新しいテザリングのパスワードを入力" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:320 #, python-format msgid "Enter password" msgstr "パスワードを入力" -#: selfdrive/ui/widgets/ssh_key.py:89 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:89 #, python-format msgid "Enter your GitHub username" msgstr "GitHubユーザー名を入力" -#: system/ui/widgets/list_view.py:123 system/ui/widgets/list_view.py:160 +#: system/ui/widgets/list_view.py:123 +#: system/ui/widgets/list_view.py:160 #, python-format msgid "Error" msgstr "エラー" -#: selfdrive/ui/layouts/settings/toggles.py:52 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:52 #, python-format msgid "Experimental Mode" msgstr "実験モード" -#: selfdrive/ui/layouts/settings/toggles.py:181 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:182 #, python-format -msgid "" -"Experimental mode is currently unavailable on this car since the car's stock " -"ACC is used for longitudinal control." -msgstr "" -"この車では縦制御に純正ACCを使用するため、現在実験モードは利用できません。" +msgid "Experimental mode is currently unavailable on this car since the car's stock ACC is used for longitudinal control." +msgstr "この車では縦制御に純正ACCを使用するため、現在実験モードは利用できません。" -#: system/ui/widgets/network.py:373 +#: system/ui/widgets/network.py:380 #, python-format msgid "FORGETTING..." msgstr "削除中..." -#: selfdrive/ui/widgets/setup.py:44 +#: openpilot/selfdrive/ui/widgets/setup.py:43 #, python-format msgid "Finish Setup" msgstr "セットアップを完了" -#: selfdrive/ui/layouts/settings/settings.py:66 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:63 msgid "Firehose" msgstr "Firehose" -#: selfdrive/ui/layouts/settings/firehose.py:18 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:10 msgid "Firehose Mode" msgstr "Firehoseモード" -#: selfdrive/ui/layouts/settings/firehose.py:25 -msgid "" -"For maximum effectiveness, bring your device inside and connect to a good " -"USB-C adapter and Wi-Fi weekly.\n" -"\n" -"Firehose Mode can also work while you're driving if connected to a hotspot " -"or unlimited SIM card.\n" -"\n" -"\n" -"Frequently Asked Questions\n" -"\n" -"Does it matter how or where I drive? Nope, just drive as you normally " -"would.\n" -"\n" -"Do all of my segments get pulled in Firehose Mode? No, we selectively pull a " -"subset of your segments.\n" -"\n" -"What's a good USB-C adapter? Any fast phone or laptop charger should be " -"fine.\n" -"\n" -"Does it matter which software I run? Yes, only upstream openpilot (and " -"particular forks) are able to be used for training." -msgstr "" -"最大限の効果を得るため、デバイスを屋内に持ち込み、週に一度は品質の良いUSB-Cア" -"ダプターとWi‑Fiに接続してください。\n" -"\n" -"Firehoseモードは、ホットスポットや無制限SIMに接続していれば走行中でも動作しま" -"す。\n" -"\n" -"\n" -"よくある質問\n" -"\n" -"運転の仕方や場所は関係ありますか? いいえ。普段どおりに運転してください。\n" -"\n" -"Firehoseモードではすべてのセグメントが取得されますか? いいえ。セグメントの一" -"部を選択的に取得します。\n" -"\n" -"良いUSB‑Cアダプターとは? 高速なスマホまたはノートPC用充電器で問題ありませ" -"ん。\n" -"\n" -"どのソフトウェアを使うかは重要ですか? はい。学習に使えるのは上流のopenpilot" -"(および特定のフォーク)のみです。" - -#: system/ui/widgets/network.py:318 system/ui/widgets/network.py:451 +#: system/ui/widgets/network.py:458 +#: system/ui/widgets/network.py:326 #, python-format msgid "Forget" msgstr "削除" -#: system/ui/widgets/network.py:319 +#: system/ui/widgets/network.py:327 #, python-format msgid "Forget Wi-Fi Network \"{}\"?" msgstr "Wi‑Fiネットワーク「{}」を削除しますか?" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 msgid "GOOD" msgstr "良好" -#: selfdrive/ui/widgets/pairing_dialog.py:128 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:117 #, python-format msgid "Go to https://connect.comma.ai on your phone" msgstr "スマートフォンで https://connect.comma.ai にアクセス" -#: selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "HIGH" msgstr "高温" -#: system/ui/widgets/network.py:155 +#: system/ui/widgets/network.py:152 #, python-format msgid "Hidden Network" msgstr "非公開ネットワーク" -#: selfdrive/ui/layouts/settings/firehose.py:140 -#, python-format -msgid "INACTIVE: connect to an unmetered network" -msgstr "非アクティブ:非従量のネットワークに接続してください" - -#: selfdrive/ui/layouts/settings/software.py:53 -#: selfdrive/ui/layouts/settings/software.py:136 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 +#: openpilot/selfdrive/ui/layouts/settings/software.py:146 #, python-format msgid "INSTALL" msgstr "インストール" -#: system/ui/widgets/network.py:150 +#: system/ui/widgets/network.py:147 #, python-format msgid "IP Address" msgstr "IPアドレス" -#: selfdrive/ui/layouts/settings/software.py:53 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 #, python-format msgid "Install Update" msgstr "アップデートをインストール" -#: selfdrive/ui/layouts/settings/developer.py:56 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:56 #, python-format msgid "Joystick Debug Mode" msgstr "ジョイスティックデバッグモード" -#: selfdrive/ui/widgets/ssh_key.py:29 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:29 msgid "LOADING" msgstr "読み込み中" -#: selfdrive/ui/layouts/sidebar.py:48 +#: openpilot/selfdrive/ui/layouts/sidebar.py:48 msgid "LTE" msgstr "LTE" -#: selfdrive/ui/layouts/settings/developer.py:64 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:64 #, python-format msgid "Longitudinal Maneuver Mode" msgstr "縦制御マヌーバーモード" -#: selfdrive/ui/onroad/hud_renderer.py:148 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:148 #, python-format msgid "MAX" msgstr "最大" -#: selfdrive/ui/widgets/setup.py:75 +#: openpilot/selfdrive/ui/widgets/setup.py:74 #, python-format -msgid "" -"Maximize your training data uploads to improve openpilot's driving models." -msgstr "" -"学習データのアップロードを最大化してopenpilotの運転モデルを改善しましょう。" +msgid "Maximize your training data uploads to improve openpilot's driving models." +msgstr "学習データのアップロードを最大化してopenpilotの運転モデルを改善しましょう。" -#: selfdrive/ui/layouts/settings/device.py:59 -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "N/A" msgstr "該当なし" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "NO" msgstr "いいえ" -#: selfdrive/ui/layouts/settings/settings.py:63 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:60 msgid "Network" msgstr "ネットワーク" -#: selfdrive/ui/widgets/ssh_key.py:114 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:115 #, python-format msgid "No SSH keys found" msgstr "SSH鍵が見つかりません" -#: selfdrive/ui/widgets/ssh_key.py:126 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:127 #, python-format msgid "No SSH keys found for user '{}'" msgstr "ユーザー'{}'のSSH鍵が見つかりません" -#: selfdrive/ui/widgets/offroad_alerts.py:320 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:321 #, python-format msgid "No release notes available." msgstr "リリースノートはありません。" -#: selfdrive/ui/layouts/sidebar.py:73 selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 msgid "OFFLINE" msgstr "オフライン" -#: system/ui/widgets/html_render.py:263 system/ui/widgets/confirm_dialog.py:93 -#: selfdrive/ui/layouts/sidebar.py:127 +#: system/ui/widgets/confirm_dialog.py:93 +#: system/ui/widgets/html_render.py:263 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 #, python-format msgid "OK" msgstr "OK" -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 msgid "ONLINE" msgstr "オンライン" -#: selfdrive/ui/widgets/setup.py:20 +#: openpilot/selfdrive/ui/widgets/setup.py:19 #, python-format msgid "Open" msgstr "開く" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "PAIR" msgstr "ペアリング" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "PANDA" msgstr "PANDA" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "PREVIEW" msgstr "プレビュー" -#: selfdrive/ui/widgets/prime.py:44 +#: openpilot/selfdrive/ui/widgets/prime.py:44 #, python-format msgid "PRIME FEATURES:" msgstr "prime の特典:" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "Pair Device" msgstr "デバイスをペアリング" -#: selfdrive/ui/widgets/setup.py:19 +#: openpilot/selfdrive/ui/widgets/setup.py:18 #, python-format msgid "Pair device" msgstr "デバイスをペアリング" -#: selfdrive/ui/widgets/pairing_dialog.py:103 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:92 #, python-format msgid "Pair your device to your comma account" msgstr "デバイスをあなたの comma アカウントにペアリング" -#: selfdrive/ui/widgets/setup.py:48 selfdrive/ui/layouts/settings/device.py:24 +#: openpilot/selfdrive/ui/widgets/setup.py:47 +#: openpilot/selfdrive/ui/layouts/settings/device.py:23 #, python-format -msgid "" -"Pair your device with comma connect (connect.comma.ai) and claim your comma " -"prime offer." -msgstr "" -"デバイスを comma connect(connect.comma.ai)とペアリングして、comma prime 特" -"典を受け取りましょう。" +msgid "Pair your device with comma connect (connect.comma.ai) and claim your comma prime offer." +msgstr "デバイスを comma connect(connect.comma.ai)とペアリングして、comma prime 特典を受け取りましょう。" -#: selfdrive/ui/widgets/setup.py:91 +#: openpilot/selfdrive/ui/widgets/setup.py:91 #, python-format msgid "Please connect to Wi-Fi to complete initial pairing" msgstr "初回ペアリングを完了するにはWi‑Fiに接続してください" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Power Off" msgstr "電源オフ" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Prevent large data uploads when on a metered Wi-Fi connection" msgstr "従量課金のWi‑Fi接続時は大きなデータのアップロードを抑制" -#: system/ui/widgets/network.py:135 +#: system/ui/widgets/network.py:132 #, python-format msgid "Prevent large data uploads when on a metered cellular connection" msgstr "従量課金の携帯回線接続時は大きなデータのアップロードを抑制" -#: selfdrive/ui/layouts/settings/device.py:25 -msgid "" -"Preview the driver facing camera to ensure that driver monitoring has good " -"visibility. (vehicle must be off)" -msgstr "" -"ドライバー向きカメラのプレビューでモニタリングの視界を確認します。(車両は停" -"止状態である必要があります)" +#: openpilot/selfdrive/ui/layouts/settings/device.py:24 +msgid "Preview the driver facing camera to ensure that driver monitoring has good visibility. (vehicle must be off)" +msgstr "ドライバー向きカメラのプレビューでモニタリングの視界を確認します。(車両は停止状態である必要があります)" -#: selfdrive/ui/widgets/pairing_dialog.py:161 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:150 #, python-format msgid "QR Code Error" msgstr "QRコードエラー" -#: selfdrive/ui/widgets/ssh_key.py:31 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:31 msgid "REMOVE" msgstr "削除" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "RESET" msgstr "リセット" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "REVIEW" msgstr "確認" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Reboot" msgstr "再起動" -#: selfdrive/ui/onroad/alert_renderer.py:66 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:66 #, python-format msgid "Reboot Device" msgstr "デバイスを再起動" -#: selfdrive/ui/widgets/offroad_alerts.py:112 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:112 #, python-format msgid "Reboot and Update" msgstr "再起動して更新" -#: selfdrive/ui/layouts/settings/toggles.py:27 -msgid "" -"Receive alerts to steer back into the lane when your vehicle drifts over a " -"detected lane line without a turn signal activated while driving over 31 mph " -"(50 km/h)." -msgstr "" -"時速31mph(50km/h)を超えて走行中にウインカーを出さず検出された車線を外れた場" -"合、車線内に戻るよう警告を受け取ります。" - -#: selfdrive/ui/layouts/settings/toggles.py:76 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:76 #, python-format msgid "Record and Upload Driver Camera" msgstr "ドライバーカメラを記録してアップロード" -#: selfdrive/ui/layouts/settings/toggles.py:82 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:82 #, python-format msgid "Record and Upload Microphone Audio" msgstr "マイク音声を記録してアップロード" -#: selfdrive/ui/layouts/settings/toggles.py:33 -msgid "" -"Record and store microphone audio while driving. The audio will be included " -"in the dashcam video in comma connect." -msgstr "" -"走行中にマイク音声を記録・保存します。音声は comma connect のドライブレコー" -"ダー動画に含まれます。" +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:33 +msgid "Record and store microphone audio while driving. The audio will be included in the dashcam video in comma connect." +msgstr "走行中にマイク音声を記録・保存します。音声は comma connect のドライブレコーダー動画に含まれます。" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "Regulatory" msgstr "規制情報" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Relaxed" msgstr "リラックス" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote access" msgstr "リモートアクセス" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote snapshots" msgstr "リモートスナップショット" -#: selfdrive/ui/widgets/ssh_key.py:123 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:124 #, python-format msgid "Request timed out" msgstr "リクエストがタイムアウトしました" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Reset" msgstr "リセット" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "Reset Calibration" msgstr "キャリブレーションをリセット" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "Review Training Guide" msgstr "トレーニングガイドを確認" -#: selfdrive/ui/layouts/settings/device.py:27 +#: openpilot/selfdrive/ui/layouts/settings/device.py:26 msgid "Review the rules, features, and limitations of openpilot" msgstr "openpilotのルール、機能、制限を確認" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "SELECT" msgstr "選択" -#: selfdrive/ui/layouts/settings/developer.py:53 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:53 #, python-format msgid "SSH Keys" msgstr "SSH鍵" -#: system/ui/widgets/network.py:310 +#: system/ui/widgets/network.py:316 #, python-format msgid "Scanning Wi-Fi networks..." msgstr "Wi‑Fiネットワークを検索中..." -#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/option_dialog.py:37 #, python-format msgid "Select" msgstr "選択" -#: selfdrive/ui/layouts/settings/software.py:183 +#: openpilot/selfdrive/ui/layouts/settings/software.py:203 #, python-format msgid "Select a branch" msgstr "ブランチを選択" -#: selfdrive/ui/layouts/settings/device.py:91 +#: openpilot/selfdrive/ui/layouts/settings/device.py:89 #, python-format msgid "Select a language" msgstr "言語を選択" -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "Serial" msgstr "シリアル" -#: selfdrive/ui/widgets/offroad_alerts.py:106 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:106 #, python-format msgid "Snooze Update" msgstr "更新を後で通知" -#: selfdrive/ui/layouts/settings/settings.py:65 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:62 msgid "Software" msgstr "ソフトウェア" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Standard" msgstr "スタンダード" -#: selfdrive/ui/layouts/settings/toggles.py:22 -msgid "" -"Standard is recommended. In aggressive mode, openpilot will follow lead cars " -"closer and be more aggressive with the gas and brake. In relaxed mode " -"openpilot will stay further away from lead cars. On supported cars, you can " -"cycle through these personalities with your steering wheel distance button." -msgstr "" -"標準を推奨します。アグレッシブでは前走車に近づき、加減速も積極的になります。" -"リラックスでは前走車との距離を保ちます。対応車種ではステアリングの車間ボタン" -"でこれらの性格を切り替えられます。" - -#: selfdrive/ui/onroad/alert_renderer.py:59 -#: selfdrive/ui/onroad/alert_renderer.py:65 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:59 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:65 #, python-format msgid "System Unresponsive" msgstr "システムが応答しません" -#: selfdrive/ui/onroad/alert_renderer.py:58 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:58 #, python-format msgid "TAKE CONTROL IMMEDIATELY" msgstr "すぐに手動介入してください" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 -#: selfdrive/ui/layouts/sidebar.py:127 selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "TEMP" msgstr "温度" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "Target Branch" msgstr "対象ブランチ" -#: system/ui/widgets/network.py:124 +#: system/ui/widgets/network.py:121 #, python-format msgid "Tethering Password" msgstr "テザリングのパスワード" -#: selfdrive/ui/layouts/settings/settings.py:64 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:61 msgid "Toggles" msgstr "トグル" -#: selfdrive/ui/layouts/settings/software.py:72 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:79 +#, python-format +msgid "UI Debug Mode" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "UNINSTALL" msgstr "アンインストール" -#: selfdrive/ui/layouts/home.py:155 +#: openpilot/selfdrive/ui/layouts/home.py:155 #, python-format msgid "UPDATE" msgstr "更新" -#: selfdrive/ui/layouts/settings/software.py:72 -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "Uninstall" msgstr "アンインストール" -#: selfdrive/ui/layouts/sidebar.py:117 +#: openpilot/selfdrive/ui/layouts/sidebar.py:117 msgid "Unknown" msgstr "不明" -#: selfdrive/ui/layouts/settings/software.py:48 +#: openpilot/selfdrive/ui/layouts/settings/software.py:55 #, python-format msgid "Updates are only downloaded while the car is off." msgstr "アップデートは車両の電源が切れている間のみダウンロードされます。" -#: selfdrive/ui/widgets/prime.py:33 +#: openpilot/selfdrive/ui/widgets/prime.py:33 #, python-format msgid "Upgrade Now" msgstr "今すぐアップグレード" -#: selfdrive/ui/layouts/settings/toggles.py:31 -msgid "" -"Upload data from the driver facing camera and help improve the driver " -"monitoring algorithm." -msgstr "" -"ドライバー向きカメラのデータをアップロードしてモニタリングアルゴリズムの改善" -"に協力してください。" +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:31 +msgid "Upload data from the driver facing camera and help improve the driver monitoring algorithm." +msgstr "ドライバー向きカメラのデータをアップロードしてモニタリングアルゴリズムの改善に協力してください。" -#: selfdrive/ui/layouts/settings/toggles.py:88 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:88 #, python-format msgid "Use Metric System" msgstr "メートル法を使用" -#: selfdrive/ui/layouts/settings/toggles.py:17 -msgid "" -"Use the openpilot system for adaptive cruise control and lane keep driver " -"assistance. Your attention is required at all times to use this feature." -msgstr "" -"ACCと車線維持支援にopenpilotを使用します。本機能の使用中は常に注意が必要で" -"す。" - -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 msgid "VEHICLE" msgstr "車両" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "VIEW" msgstr "表示" -#: selfdrive/ui/onroad/alert_renderer.py:52 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:52 #, python-format msgid "Waiting to start" msgstr "開始待機中" -#: selfdrive/ui/layouts/settings/developer.py:19 -msgid "" -"Warning: This grants SSH access to all public keys in your GitHub settings. " -"Never enter a GitHub username other than your own. A comma employee will " -"NEVER ask you to add their GitHub username." -msgstr "" -"警告: これはGitHub設定内のすべての公開鍵にSSHアクセスを与えます。自分以外の" -"GitHubユーザー名を絶対に入力しないでください。comma の従業員が自分のGitHub" -"ユーザー名を追加するよう求めることは決してありません。" - -#: selfdrive/ui/layouts/onboarding.py:111 +#: openpilot/selfdrive/ui/layouts/onboarding.py:115 #, python-format msgid "Welcome to openpilot" msgstr "openpilotへようこそ" -#: selfdrive/ui/layouts/settings/toggles.py:20 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:20 msgid "When enabled, pressing the accelerator pedal will disengage openpilot." msgstr "有効にすると、アクセルを踏むとopenpilotが解除されます。" -#: selfdrive/ui/layouts/sidebar.py:44 +#: openpilot/selfdrive/ui/layouts/sidebar.py:44 msgid "Wi-Fi" msgstr "Wi‑Fi" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Wi-Fi Network Metered" msgstr "Wi‑Fiネットワーク(従量課金)" -#: system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:320 #, python-format msgid "Wrong password" msgstr "パスワードが違います" -#: selfdrive/ui/layouts/onboarding.py:145 +#: openpilot/selfdrive/ui/layouts/onboarding.py:149 #, python-format msgid "You must accept the Terms and Conditions in order to use openpilot." msgstr "openpilotを使用するには、利用規約に同意する必要があります。" -#: selfdrive/ui/layouts/onboarding.py:112 +#: openpilot/selfdrive/ui/layouts/onboarding.py:116 #, python-format -msgid "" -"You must accept the Terms and Conditions to use openpilot. Read the latest " -"terms at https://comma.ai/terms before continuing." -msgstr "" -"openpilotを使用するには利用規約に同意する必要があります。続行する前に " -"https://comma.ai/terms の最新の規約をお読みください。" +msgid "You must accept the Terms and Conditions to use openpilot. Read the latest terms at https://comma.ai/terms before continuing." +msgstr "openpilotを使用するには利用規約に同意する必要があります。続行する前に https://comma.ai/terms の最新の規約をお読みください。" -#: selfdrive/ui/onroad/driver_camera_dialog.py:34 +#: openpilot/selfdrive/ui/onroad/driver_camera_dialog.py:38 #, python-format msgid "camera starting" msgstr "カメラを起動中" -#: selfdrive/ui/widgets/prime.py:63 +#: openpilot/selfdrive/ui/layouts/settings/software.py:19 +#, python-format +msgid "checking..." +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:63 #, python-format msgid "comma prime" msgstr "comma prime" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "default" msgstr "既定" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "down" msgstr "下" -#: selfdrive/ui/layouts/settings/software.py:106 +#: openpilot/selfdrive/ui/layouts/settings/software.py:20 +#, python-format +msgid "downloading..." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:116 #, python-format msgid "failed to check for update" msgstr "アップデートの確認に失敗しました" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: openpilot/selfdrive/ui/layouts/settings/software.py:21 +#, python-format +msgid "finalizing update..." +msgstr "" + +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:321 #, python-format msgid "for \"{}\"" msgstr "「{}」向け" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "km/h" msgstr "km/h" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "leave blank for automatic configuration" msgstr "自動設定の場合は空欄のままにしてください" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "left" msgstr "左" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "metered" msgstr "従量" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "mph" msgstr "mph" -#: selfdrive/ui/layouts/settings/software.py:20 +#: openpilot/selfdrive/ui/layouts/settings/software.py:27 #, python-format msgid "never" msgstr "なし" -#: selfdrive/ui/layouts/settings/software.py:31 +#: openpilot/selfdrive/ui/layouts/settings/software.py:38 #, python-format msgid "now" msgstr "今" -#: selfdrive/ui/layouts/settings/developer.py:71 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:71 #, python-format msgid "openpilot Longitudinal Control (Alpha)" msgstr "openpilot 縦制御(アルファ)" -#: selfdrive/ui/onroad/alert_renderer.py:51 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:51 #, python-format msgid "openpilot Unavailable" msgstr "openpilotは利用できません" -#: selfdrive/ui/layouts/settings/toggles.py:158 -#, python-format -msgid "" -"openpilot defaults to driving in chill mode. Experimental mode enables alpha-" -"level features that aren't ready for chill mode. Experimental features are " -"listed below:

End-to-End Longitudinal Control


Let the driving " -"model control the gas and brakes. openpilot will drive as it thinks a human " -"would, including stopping for red lights and stop signs. Since the driving " -"model decides the speed to drive, the set speed will only act as an upper " -"bound. This is an alpha quality feature; mistakes should be expected." -"

New Driving Visualization


The driving visualization will " -"transition to the road-facing wide-angle camera at low speeds to better show " -"some turns. The Experimental mode logo will also be shown in the top right " -"corner." -msgstr "" -"openpilotは既定でチルモードで走行します。実験モードでは、チルモードにはまだ準" -"備ができていないアルファレベルの機能が有効になります。実験的な機能は以下のと" -"おりです:

エンドツーエンド縦制御


運転モデルがアクセルとブレー" -"キを制御します。openpilotは人間のように走行し、赤信号や一時停止でも停止しま" -"す。走行速度は運転モデルが決めるため、設定速度は上限としてのみ機能します。こ" -"れはアルファ品質の機能であり、誤動作が発生する可能性があります。

新し" -"い運転ビジュアライゼーション


低速時には道路向きの広角カメラに切り替わ" -"り、一部の曲がりをより良く表示します。画面右上には実験モードのロゴも表示され" -"ます。" - -#: selfdrive/ui/layouts/settings/device.py:165 -#, python-format -msgid "" -"openpilot is continuously calibrating, resetting is rarely required. " -"Resetting calibration will restart openpilot if the car is powered on." -msgstr "" -"openpilotは継続的にキャリブレーションを行っており、リセットが必要になることは" -"稀です。車が起動中にキャリブレーションをリセットするとopenpilotが再起動しま" -"す。" - -#: selfdrive/ui/layouts/settings/firehose.py:20 -msgid "" -"openpilot learns to drive by watching humans, like you, drive.\n" -"\n" -"Firehose Mode allows you to maximize your training data uploads to improve " -"openpilot's driving models. More data means bigger models, which means " -"better Experimental Mode." -msgstr "" -"openpilotは、あなたのような人間の運転を見て運転を学習します。\n" -"\n" -"Firehoseモードを使うと、学習データのアップロードを最大化してopenpilotの運転モ" -"デルを改善できます。データが増えるほどモデルが大きくなり、実験モードがより良" -"くなります。" - -#: selfdrive/ui/layouts/settings/toggles.py:183 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:184 #, python-format msgid "openpilot longitudinal control may come in a future update." msgstr "openpilotの縦制御は将来のアップデートで提供される可能性があります。" -#: selfdrive/ui/layouts/settings/device.py:26 -msgid "" -"openpilot requires the device to be mounted within 4° left or right and " -"within 5° up or 9° down." -msgstr "" -"openpilotでは、デバイスの取り付け角度が左右±4°、上方向5°以内、下方向9°以内で" -"ある必要があります。" +#: openpilot/selfdrive/ui/layouts/settings/device.py:25 +msgid "openpilot requires the device to be mounted within 4° left or right and within 5° up or 9° down." +msgstr "openpilotでは、デバイスの取り付け角度が左右±4°、上方向5°以内、下方向9°以内である必要があります。" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "right" msgstr "右" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "unmetered" msgstr "非従量" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "up" msgstr "上" -#: selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:127 #, python-format msgid "up to date, last checked never" msgstr "最新です。最終確認: なし" -#: selfdrive/ui/layouts/settings/software.py:115 +#: openpilot/selfdrive/ui/layouts/settings/software.py:125 #, python-format msgid "up to date, last checked {}" msgstr "最新です。最終確認: {}" -#: selfdrive/ui/layouts/settings/software.py:109 +#: openpilot/selfdrive/ui/layouts/settings/software.py:119 #, python-format msgid "update available" msgstr "更新があります" -#: selfdrive/ui/layouts/home.py:169 +#: openpilot/selfdrive/ui/layouts/home.py:169 #, python-format msgid "{} ALERT" msgid_plural "{} ALERTS" msgstr[0] "{}件のアラート" -#: selfdrive/ui/layouts/settings/software.py:40 +#: openpilot/selfdrive/ui/layouts/settings/software.py:47 #, python-format msgid "{} day ago" msgid_plural "{} days ago" msgstr[0] "{}日前" -#: selfdrive/ui/layouts/settings/software.py:37 +#: openpilot/selfdrive/ui/layouts/settings/software.py:44 #, python-format msgid "{} hour ago" msgid_plural "{} hours ago" msgstr[0] "{}時間前" -#: selfdrive/ui/layouts/settings/software.py:34 +#: openpilot/selfdrive/ui/layouts/settings/software.py:41 #, python-format msgid "{} minute ago" msgid_plural "{} minutes ago" msgstr[0] "{}分前" -#: selfdrive/ui/layouts/settings/firehose.py:111 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:70 #, python-format msgid "{} segment of your driving is in the training dataset so far." msgid_plural "{} segments of your driving is in the training dataset so far." -msgstr[0] "" -"これまでにあなたの走行の{}セグメントが学習データセットに含まれています。" +msgstr[0] "これまでにあなたの走行の{}セグメントが学習データセットに含まれています。" -#: selfdrive/ui/widgets/prime.py:62 +#: openpilot/selfdrive/ui/widgets/prime.py:62 #, python-format msgid "✓ SUBSCRIBED" msgstr "✓ 登録済み" -#: selfdrive/ui/widgets/setup.py:22 +#: openpilot/selfdrive/ui/widgets/setup.py:21 #, python-format msgid "🔥 Firehose Mode 🔥" msgstr "🔥 Firehoseモード 🔥" + diff --git a/selfdrive/ui/translations/app_ko.po b/selfdrive/ui/translations/app_ko.po index f12aebaeb3..9b73a22387 100644 --- a/selfdrive/ui/translations/app_ko.po +++ b/selfdrive/ui/translations/app_ko.po @@ -17,1174 +17,1013 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=1; plural=0;\n" -#: selfdrive/ui/layouts/settings/device.py:160 +#: openpilot/selfdrive/ui/layouts/settings/device.py:152 #, python-format msgid " Steering torque response calibration is complete." msgstr " 스티어링 토크 응답 보정이 완료되었습니다." -#: selfdrive/ui/layouts/settings/device.py:158 +#: openpilot/selfdrive/ui/layouts/settings/device.py:150 #, python-format msgid " Steering torque response calibration is {}% complete." msgstr " 스티어링 토크 응답 보정이 {}% 완료되었습니다." -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid " Your device is pointed {:.1f}° {} and {:.1f}° {}." msgstr " 장치는 {:.1f}° {} 및 {:.1f}° {} 방향을 가리키고 있습니다." -#: selfdrive/ui/layouts/sidebar.py:43 +#: openpilot/selfdrive/ui/layouts/sidebar.py:43 msgid "--" msgstr "--" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "1 year of drive storage" msgstr "주행 데이터 1년 보관" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "24/7 LTE connectivity" msgstr "연중무휴 LTE 연결" -#: selfdrive/ui/layouts/sidebar.py:46 +#: openpilot/selfdrive/ui/layouts/sidebar.py:46 msgid "2G" msgstr "2G" -#: selfdrive/ui/layouts/sidebar.py:47 +#: openpilot/selfdrive/ui/layouts/sidebar.py:47 msgid "3G" msgstr "3G" -#: selfdrive/ui/layouts/sidebar.py:49 +#: openpilot/selfdrive/ui/layouts/sidebar.py:49 msgid "5G" msgstr "5G" -#: selfdrive/ui/layouts/settings/developer.py:23 -msgid "" -"WARNING: openpilot longitudinal control is in alpha for this car and will " -"disable Automatic Emergency Braking (AEB).

On this car, openpilot " -"defaults to the car's built-in ACC instead of openpilot's longitudinal " -"control. Enable this to switch to openpilot longitudinal control. Enabling " -"Experimental mode is recommended when enabling openpilot longitudinal " -"control alpha. Changing this setting will restart openpilot if the car is " -"powered on." -msgstr "" -"경고: 이 차량에서 openpilot의 롱컨 제어는 알파 버전이며 자동 긴급 제동" -"(AEB)을 비활성화합니다.

이 차량에서는 openpilot 롱컨 제어 대신 " -"차량 내장 ACC가 기본으로 사용됩니다. openpilot 롱컨 제어로 전환하려면 이 설" -"정을 켜세요. 롱컨 제어 알파를 켤 때는 실험 모드 사용을 권장합니다. 차량 전" -"원이 켜져 있는 경우 이 설정을 변경하면 openpilot이 재시작됩니다." - -#: selfdrive/ui/layouts/settings/device.py:148 +#: openpilot/selfdrive/ui/layouts/settings/device.py:140 #, python-format msgid "

Steering lag calibration is complete." msgstr "

스티어링 지연 보정이 완료되었습니다." -#: selfdrive/ui/layouts/settings/device.py:146 +#: openpilot/selfdrive/ui/layouts/settings/device.py:138 #, python-format msgid "

Steering lag calibration is {}% complete." msgstr "

스티어링 지연 보정이 {}% 완료되었습니다." -#: selfdrive/ui/layouts/settings/firehose.py:138 -#, python-format -msgid "ACTIVE" -msgstr "활성" - -#: selfdrive/ui/layouts/settings/developer.py:15 -msgid "" -"ADB (Android Debug Bridge) allows connecting to your device over USB or over " -"the network. See https://docs.comma.ai/how-to/connect-to-comma for more info." -msgstr "" -"ADB(Android Debug Bridge)를 사용하면 USB 또는 네트워크로 장치에 연결할 수 있" -"습니다. 자세한 내용은 https://docs.comma.ai/how-to/connect-to-comma 를 참고하" -"세요." - -#: selfdrive/ui/widgets/ssh_key.py:30 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:30 msgid "ADD" msgstr "추가" -#: system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:136 #, python-format msgid "APN Setting" msgstr "APN 설정" -#: selfdrive/ui/widgets/offroad_alerts.py:109 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:109 #, python-format msgid "Acknowledge Excessive Actuation" msgstr "과도한 작동을 확인" -#: system/ui/widgets/network.py:74 system/ui/widgets/network.py:95 +#: system/ui/widgets/network.py:92 +#: system/ui/widgets/network.py:74 #, python-format msgid "Advanced" msgstr "고급" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Aggressive" msgstr "공격적" -#: selfdrive/ui/layouts/onboarding.py:116 +#: openpilot/selfdrive/ui/layouts/onboarding.py:120 #, python-format msgid "Agree" msgstr "동의" -#: selfdrive/ui/layouts/settings/toggles.py:70 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:70 #, python-format msgid "Always-On Driver Monitoring" msgstr "운전자 모니터링 항상 켜짐" -#: selfdrive/ui/layouts/settings/toggles.py:186 -#, python-format -msgid "" -"An alpha version of openpilot longitudinal control can be tested, along with " -"Experimental mode, on non-release branches." -msgstr "" -"openpilot 롱컨 제어 알파 버전은 실험 모드와 함께 비릴리스 브랜치에서 테스트" -"할 수 있습니다." - -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 #, python-format msgid "Are you sure you want to power off?" msgstr "정말 전원을 끄시겠습니까?" -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 #, python-format msgid "Are you sure you want to reboot?" msgstr "정말 재시작하시겠습니까?" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Are you sure you want to reset calibration?" msgstr "정말 보정을 재설정하시겠습니까?" -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 #, python-format msgid "Are you sure you want to uninstall?" msgstr "정말 제거하시겠습니까?" -#: system/ui/widgets/network.py:99 selfdrive/ui/layouts/onboarding.py:147 +#: system/ui/widgets/network.py:96 +#: openpilot/selfdrive/ui/layouts/onboarding.py:151 #, python-format msgid "Back" msgstr "뒤로" -#: selfdrive/ui/widgets/prime.py:38 +#: openpilot/selfdrive/ui/widgets/prime.py:38 #, python-format msgid "Become a comma prime member at connect.comma.ai" msgstr "connect.comma.ai에서 comma prime 회원이 되세요" -#: selfdrive/ui/widgets/pairing_dialog.py:130 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:119 #, python-format msgid "Bookmark connect.comma.ai to your home screen to use it like an app" msgstr "connect.comma.ai를 홈 화면에 추가하여 앱처럼 사용하세요" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "CHANGE" msgstr "변경" -#: selfdrive/ui/layouts/settings/software.py:50 -#: selfdrive/ui/layouts/settings/software.py:107 -#: selfdrive/ui/layouts/settings/software.py:118 -#: selfdrive/ui/layouts/settings/software.py:147 +#: openpilot/selfdrive/ui/layouts/settings/software.py:157 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 +#: openpilot/selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:128 #, python-format msgid "CHECK" msgstr "확인" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "CHILL MODE ON" msgstr "안정적 모드 켜짐" -#: system/ui/widgets/network.py:155 selfdrive/ui/layouts/sidebar.py:73 -#: selfdrive/ui/layouts/sidebar.py:134 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:138 +#: system/ui/widgets/network.py:152 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 #, python-format msgid "CONNECT" msgstr "연결" -#: system/ui/widgets/network.py:369 +#: system/ui/widgets/network.py:376 #, python-format msgid "CONNECTING..." msgstr "연결 중..." -#: system/ui/widgets/confirm_dialog.py:23 system/ui/widgets/option_dialog.py:35 -#: system/ui/widgets/keyboard.py:81 system/ui/widgets/network.py:318 +#: system/ui/widgets/network.py:326 +#: system/ui/widgets/confirm_dialog.py:24 +#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/keyboard.py:83 #, python-format msgid "Cancel" msgstr "취소" -#: system/ui/widgets/network.py:134 +#: system/ui/widgets/network.py:131 #, python-format msgid "Cellular Metered" msgstr "종량제 셀룰러" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "Change Language" msgstr "언어 변경" -#: selfdrive/ui/layouts/settings/toggles.py:125 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:125 #, python-format msgid "Changing this setting will restart openpilot if the car is powered on." msgstr "차량 전원이 켜져 있으면 이 설정을 변경할 때 openpilot이 재시작됩니다." -#: selfdrive/ui/widgets/pairing_dialog.py:129 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:118 #, python-format msgid "Click \"add new device\" and scan the QR code on the right" msgstr "\"add new device\"를 눌러 오른쪽의 QR 코드를 스캔하세요" -#: selfdrive/ui/widgets/offroad_alerts.py:104 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:104 #, python-format msgid "Close" msgstr "닫기" -#: selfdrive/ui/layouts/settings/software.py:49 +#: openpilot/selfdrive/ui/layouts/settings/software.py:56 #, python-format msgid "Current Version" msgstr "현재 버전" -#: selfdrive/ui/layouts/settings/software.py:110 +#: openpilot/selfdrive/ui/layouts/settings/software.py:120 #, python-format msgid "DOWNLOAD" msgstr "다운로드" -#: selfdrive/ui/layouts/onboarding.py:115 +#: openpilot/selfdrive/ui/layouts/onboarding.py:119 #, python-format msgid "Decline" msgstr "거부" -#: selfdrive/ui/layouts/onboarding.py:148 +#: openpilot/selfdrive/ui/layouts/onboarding.py:152 #, python-format msgid "Decline, uninstall openpilot" msgstr "거부하고 openpilot 제거" -#: selfdrive/ui/layouts/settings/settings.py:67 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:64 msgid "Developer" msgstr "개발자" -#: selfdrive/ui/layouts/settings/settings.py:62 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:59 msgid "Device" msgstr "장치" -#: selfdrive/ui/layouts/settings/toggles.py:58 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:58 #, python-format msgid "Disengage on Accelerator Pedal" msgstr "가속 페달로 해제" -#: selfdrive/ui/layouts/settings/device.py:184 +#: openpilot/selfdrive/ui/layouts/settings/device.py:176 #, python-format msgid "Disengage to Power Off" msgstr "해제 후 전원 끄기" -#: selfdrive/ui/layouts/settings/device.py:172 +#: openpilot/selfdrive/ui/layouts/settings/device.py:164 #, python-format msgid "Disengage to Reboot" msgstr "해제 후 재시작" -#: selfdrive/ui/layouts/settings/device.py:103 +#: openpilot/selfdrive/ui/layouts/settings/device.py:95 #, python-format msgid "Disengage to Reset Calibration" msgstr "해제 후 캘리브레이션 재설정" -#: selfdrive/ui/layouts/settings/toggles.py:32 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:32 msgid "Display speed in km/h instead of mph." msgstr "속도를 mph 대신 km/h로 표시합니다." -#: selfdrive/ui/layouts/settings/device.py:59 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 #, python-format msgid "Dongle ID" msgstr "동글 ID" -#: selfdrive/ui/layouts/settings/software.py:50 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 #, python-format msgid "Download" msgstr "다운로드" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "Driver Camera" msgstr "운전자 카메라" -#: selfdrive/ui/layouts/settings/toggles.py:96 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:96 #, python-format msgid "Driving Personality" msgstr "주행 성향" -#: system/ui/widgets/network.py:123 system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:136 #, python-format msgid "EDIT" msgstr "편집" -#: selfdrive/ui/layouts/sidebar.py:138 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 msgid "ERROR" msgstr "오류" -#: selfdrive/ui/layouts/sidebar.py:45 +#: openpilot/selfdrive/ui/layouts/sidebar.py:45 msgid "ETH" msgstr "ETH" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "EXPERIMENTAL MODE ON" msgstr "실험 모드 켜짐" -#: selfdrive/ui/layouts/settings/developer.py:166 -#: selfdrive/ui/layouts/settings/toggles.py:228 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:229 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:180 #, python-format msgid "Enable" msgstr "사용" -#: selfdrive/ui/layouts/settings/developer.py:39 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:39 #, python-format msgid "Enable ADB" msgstr "ADB 사용" -#: selfdrive/ui/layouts/settings/toggles.py:64 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:64 #, python-format msgid "Enable Lane Departure Warnings" msgstr "차선 이탈 경고 사용" -#: system/ui/widgets/network.py:129 +#: system/ui/widgets/network.py:126 #, python-format msgid "Enable Roaming" msgstr "로밍 사용" -#: selfdrive/ui/layouts/settings/developer.py:48 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:48 #, python-format msgid "Enable SSH" msgstr "SSH 사용" -#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:117 #, python-format msgid "Enable Tethering" msgstr "테더링 사용" -#: selfdrive/ui/layouts/settings/toggles.py:30 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:30 msgid "Enable driver monitoring even when openpilot is not engaged." msgstr "openpilot이 작동 중이 아닐 때도 운전자 모니터링을 사용합니다." -#: selfdrive/ui/layouts/settings/toggles.py:46 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:46 #, python-format msgid "Enable openpilot" msgstr "openpilot 사용" -#: selfdrive/ui/layouts/settings/toggles.py:189 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:190 #, python-format -msgid "" -"Enable the openpilot longitudinal control (alpha) toggle to allow " -"Experimental mode." +msgid "Enable the openpilot longitudinal control (alpha) toggle to allow Experimental mode." msgstr "실험 모드를 사용하려면 openpilot 롱컨 제어(알파) 토글을 켜세요." -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "Enter APN" msgstr "APN 입력" -#: system/ui/widgets/network.py:241 +#: system/ui/widgets/network.py:243 #, python-format msgid "Enter SSID" msgstr "SSID 입력" -#: system/ui/widgets/network.py:254 +#: system/ui/widgets/network.py:257 #, python-format msgid "Enter new tethering password" msgstr "새 테더링 비밀번호 입력" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:320 #, python-format msgid "Enter password" msgstr "비밀번호 입력" -#: selfdrive/ui/widgets/ssh_key.py:89 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:89 #, python-format msgid "Enter your GitHub username" msgstr "GitHub 사용자 이름 입력" -#: system/ui/widgets/list_view.py:123 system/ui/widgets/list_view.py:160 +#: system/ui/widgets/list_view.py:123 +#: system/ui/widgets/list_view.py:160 #, python-format msgid "Error" msgstr "오류" -#: selfdrive/ui/layouts/settings/toggles.py:52 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:52 #, python-format msgid "Experimental Mode" msgstr "실험 모드" -#: selfdrive/ui/layouts/settings/toggles.py:181 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:182 #, python-format -msgid "" -"Experimental mode is currently unavailable on this car since the car's stock " -"ACC is used for longitudinal control." -msgstr "" -"이 차량은 롱컨 제어에 순정 ACC를 사용하므로 현재 실험 모드를 사용할 수 없습" -"니다." +msgid "Experimental mode is currently unavailable on this car since the car's stock ACC is used for longitudinal control." +msgstr "이 차량은 롱컨 제어에 순정 ACC를 사용하므로 현재 실험 모드를 사용할 수 없습니다." -#: system/ui/widgets/network.py:373 +#: system/ui/widgets/network.py:380 #, python-format msgid "FORGETTING..." msgstr "삭제 중..." -#: selfdrive/ui/widgets/setup.py:44 +#: openpilot/selfdrive/ui/widgets/setup.py:43 #, python-format msgid "Finish Setup" msgstr "설정 완료" -#: selfdrive/ui/layouts/settings/settings.py:66 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:63 msgid "Firehose" msgstr "파이어호스" -#: selfdrive/ui/layouts/settings/firehose.py:18 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:10 msgid "Firehose Mode" msgstr "파이어호스 모드" -#: selfdrive/ui/layouts/settings/firehose.py:25 -msgid "" -"For maximum effectiveness, bring your device inside and connect to a good " -"USB-C adapter and Wi-Fi weekly.\n" -"\n" -"Firehose Mode can also work while you're driving if connected to a hotspot " -"or unlimited SIM card.\n" -"\n" -"\n" -"Frequently Asked Questions\n" -"\n" -"Does it matter how or where I drive? Nope, just drive as you normally " -"would.\n" -"\n" -"Do all of my segments get pulled in Firehose Mode? No, we selectively pull a " -"subset of your segments.\n" -"\n" -"What's a good USB-C adapter? Any fast phone or laptop charger should be " -"fine.\n" -"\n" -"Does it matter which software I run? Yes, only upstream openpilot (and " -"particular forks) are able to be used for training." -msgstr "" -"최대의 효과를 위해 주 1회는 장치를 실내로 가져와 품질 좋은 USB‑C 어댑터와 " -"Wi‑Fi에 연결하세요.\n" -"\n" -"핫스팟이나 무제한 SIM에 연결되어 있다면 주행 중에도 파이어호스 모드가 동작합니" -"다.\n" -"\n" -"\n" -"자주 묻는 질문\n" -"\n" -"어떻게, 어디서 운전하는지가 중요한가요? 아니요. 평소처럼 운전하세요.\n" -"\n" -"파이어호스 모드에서 모든 구간을 가져가지나요? 아니요. 일부 구간만 선택" -"적으로 가져갑니다.\n" -"\n" -"좋은 USB‑C 어댑터는 무엇인가요? 빠른 휴대폰 또는 노트북 충전기면 충분합니" -"다.\n" -"\n" -"어떤 소프트웨어를 실행하는지가 중요한가요? 예. 학습에는 업스트림 " -"openpilot(및 일부 포크)만 사용할 수 있습니다." - -#: system/ui/widgets/network.py:318 system/ui/widgets/network.py:451 +#: system/ui/widgets/network.py:458 +#: system/ui/widgets/network.py:326 #, python-format msgid "Forget" msgstr "삭제" -#: system/ui/widgets/network.py:319 +#: system/ui/widgets/network.py:327 #, python-format msgid "Forget Wi-Fi Network \"{}\"?" msgstr "Wi‑Fi 네트워크 \"{}\"를 삭제하시겠습니까?" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 msgid "GOOD" msgstr "양호" -#: selfdrive/ui/widgets/pairing_dialog.py:128 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:117 #, python-format msgid "Go to https://connect.comma.ai on your phone" msgstr "휴대폰에서 https://connect.comma.ai 에 접속하세요" -#: selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "HIGH" msgstr "높음" -#: system/ui/widgets/network.py:155 +#: system/ui/widgets/network.py:152 #, python-format msgid "Hidden Network" msgstr "숨겨진 네트워크" -#: selfdrive/ui/layouts/settings/firehose.py:140 -#, python-format -msgid "INACTIVE: connect to an unmetered network" -msgstr "비활성: 비종량제 네트워크에 연결하세요" - -#: selfdrive/ui/layouts/settings/software.py:53 -#: selfdrive/ui/layouts/settings/software.py:136 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 +#: openpilot/selfdrive/ui/layouts/settings/software.py:146 #, python-format msgid "INSTALL" msgstr "설치" -#: system/ui/widgets/network.py:150 +#: system/ui/widgets/network.py:147 #, python-format msgid "IP Address" msgstr "IP 주소" -#: selfdrive/ui/layouts/settings/software.py:53 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 #, python-format msgid "Install Update" msgstr "업데이트 설치" -#: selfdrive/ui/layouts/settings/developer.py:56 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:56 #, python-format msgid "Joystick Debug Mode" msgstr "조이스틱 디버그 모드" -#: selfdrive/ui/widgets/ssh_key.py:29 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:29 msgid "LOADING" msgstr "로딩 중" -#: selfdrive/ui/layouts/sidebar.py:48 +#: openpilot/selfdrive/ui/layouts/sidebar.py:48 msgid "LTE" msgstr "LTE" -#: selfdrive/ui/layouts/settings/developer.py:64 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:64 #, python-format msgid "Longitudinal Maneuver Mode" msgstr "롱컨 기동 모드" -#: selfdrive/ui/onroad/hud_renderer.py:148 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:148 #, python-format msgid "MAX" msgstr "최대" -#: selfdrive/ui/widgets/setup.py:75 +#: openpilot/selfdrive/ui/widgets/setup.py:74 #, python-format -msgid "" -"Maximize your training data uploads to improve openpilot's driving models." +msgid "Maximize your training data uploads to improve openpilot's driving models." msgstr "학습 데이터 업로드를 최대화하여 openpilot의 주행 모델을 개선하세요." -#: selfdrive/ui/layouts/settings/device.py:59 -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "N/A" msgstr "해당 없음" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "NO" msgstr "아니오" -#: selfdrive/ui/layouts/settings/settings.py:63 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:60 msgid "Network" msgstr "네트워크" -#: selfdrive/ui/widgets/ssh_key.py:114 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:115 #, python-format msgid "No SSH keys found" msgstr "SSH 키를 찾을 수 없습니다" -#: selfdrive/ui/widgets/ssh_key.py:126 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:127 #, python-format msgid "No SSH keys found for user '{}'" msgstr "사용자 '{}'의 SSH 키를 찾을 수 없습니다" -#: selfdrive/ui/widgets/offroad_alerts.py:320 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:321 #, python-format msgid "No release notes available." msgstr "릴리스 노트가 없습니다." -#: selfdrive/ui/layouts/sidebar.py:73 selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 msgid "OFFLINE" msgstr "오프라인" -#: system/ui/widgets/html_render.py:263 system/ui/widgets/confirm_dialog.py:93 -#: selfdrive/ui/layouts/sidebar.py:127 +#: system/ui/widgets/confirm_dialog.py:93 +#: system/ui/widgets/html_render.py:263 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 #, python-format msgid "OK" msgstr "확인" -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 msgid "ONLINE" msgstr "온라인" -#: selfdrive/ui/widgets/setup.py:20 +#: openpilot/selfdrive/ui/widgets/setup.py:19 #, python-format msgid "Open" msgstr "열기" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "PAIR" msgstr "페어링" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "PANDA" msgstr "PANDA" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "PREVIEW" msgstr "미리보기" -#: selfdrive/ui/widgets/prime.py:44 +#: openpilot/selfdrive/ui/widgets/prime.py:44 #, python-format msgid "PRIME FEATURES:" msgstr "프라임 기능:" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "Pair Device" msgstr "장치 페어링" -#: selfdrive/ui/widgets/setup.py:19 +#: openpilot/selfdrive/ui/widgets/setup.py:18 #, python-format msgid "Pair device" msgstr "장치 페어링" -#: selfdrive/ui/widgets/pairing_dialog.py:103 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:92 #, python-format msgid "Pair your device to your comma account" msgstr "장치를 귀하의 comma 계정에 페어링하세요" -#: selfdrive/ui/widgets/setup.py:48 selfdrive/ui/layouts/settings/device.py:24 +#: openpilot/selfdrive/ui/widgets/setup.py:47 +#: openpilot/selfdrive/ui/layouts/settings/device.py:23 #, python-format -msgid "" -"Pair your device with comma connect (connect.comma.ai) and claim your comma " -"prime offer." -msgstr "" -"장치를 comma connect(connect.comma.ai)와 페어링하고 comma 프라임 혜택을 받으세" -"요." +msgid "Pair your device with comma connect (connect.comma.ai) and claim your comma prime offer." +msgstr "장치를 comma connect(connect.comma.ai)와 페어링하고 comma 프라임 혜택을 받으세요." -#: selfdrive/ui/widgets/setup.py:91 +#: openpilot/selfdrive/ui/widgets/setup.py:91 #, python-format msgid "Please connect to Wi-Fi to complete initial pairing" msgstr "초기 페어링을 완료하려면 Wi‑Fi에 연결하세요" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Power Off" msgstr "전원 끄기" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Prevent large data uploads when on a metered Wi-Fi connection" msgstr "종량제 Wi‑Fi 연결 시 대용량 업로드 방지" -#: system/ui/widgets/network.py:135 +#: system/ui/widgets/network.py:132 #, python-format msgid "Prevent large data uploads when on a metered cellular connection" msgstr "종량제 셀룰러 연결 시 대용량 업로드 방지" -#: selfdrive/ui/layouts/settings/device.py:25 -msgid "" -"Preview the driver facing camera to ensure that driver monitoring has good " -"visibility. (vehicle must be off)" -msgstr "" -"운전자 모니터링의 가시성을 확인하기 위해 운전자 카메라를 미리 봅니다. (차량" -"은 꺼져 있어야 합니다)" +#: openpilot/selfdrive/ui/layouts/settings/device.py:24 +msgid "Preview the driver facing camera to ensure that driver monitoring has good visibility. (vehicle must be off)" +msgstr "운전자 모니터링의 가시성을 확인하기 위해 운전자 카메라를 미리 봅니다. (차량은 꺼져 있어야 합니다)" -#: selfdrive/ui/widgets/pairing_dialog.py:161 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:150 #, python-format msgid "QR Code Error" msgstr "QR 코드 오류" -#: selfdrive/ui/widgets/ssh_key.py:31 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:31 msgid "REMOVE" msgstr "제거" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "RESET" msgstr "재설정" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "REVIEW" msgstr "검토" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Reboot" msgstr "재시작" -#: selfdrive/ui/onroad/alert_renderer.py:66 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:66 #, python-format msgid "Reboot Device" msgstr "장치 재시작" -#: selfdrive/ui/widgets/offroad_alerts.py:112 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:112 #, python-format msgid "Reboot and Update" msgstr "재시작 및 업데이트" -#: selfdrive/ui/layouts/settings/toggles.py:27 -msgid "" -"Receive alerts to steer back into the lane when your vehicle drifts over a " -"detected lane line without a turn signal activated while driving over 31 mph " -"(50 km/h)." -msgstr "" -"시속 31mph(50km/h) 이상에서 방향지시등 없이 감지된 차선 밖으로 벗어나면 차선" -"으로 복귀하라는 경고를 받습니다." - -#: selfdrive/ui/layouts/settings/toggles.py:76 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:76 #, python-format msgid "Record and Upload Driver Camera" msgstr "운전자 카메라 기록 및 업로드" -#: selfdrive/ui/layouts/settings/toggles.py:82 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:82 #, python-format msgid "Record and Upload Microphone Audio" msgstr "마이크 오디오 기록 및 업로드" -#: selfdrive/ui/layouts/settings/toggles.py:33 -msgid "" -"Record and store microphone audio while driving. The audio will be included " -"in the dashcam video in comma connect." -msgstr "" -"주행 중 마이크 오디오를 기록하고 저장합니다. 오디오는 comma connect의 대시캠 " -"영상에 포함됩니다." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:33 +msgid "Record and store microphone audio while driving. The audio will be included in the dashcam video in comma connect." +msgstr "주행 중 마이크 오디오를 기록하고 저장합니다. 오디오는 comma connect의 대시캠 영상에 포함됩니다." -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "Regulatory" msgstr "규제 정보" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Relaxed" msgstr "편안한" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote access" msgstr "원격 액세스" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote snapshots" msgstr "원격 스냅샷" -#: selfdrive/ui/widgets/ssh_key.py:123 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:124 #, python-format msgid "Request timed out" msgstr "요청 시간이 초과되었습니다" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Reset" msgstr "재설정" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "Reset Calibration" msgstr "캘리브레이션 재설정" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "Review Training Guide" msgstr "학습 가이드 검토" -#: selfdrive/ui/layouts/settings/device.py:27 +#: openpilot/selfdrive/ui/layouts/settings/device.py:26 msgid "Review the rules, features, and limitations of openpilot" msgstr "openpilot의 규칙, 기능 및 제한을 검토" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "SELECT" msgstr "선택" -#: selfdrive/ui/layouts/settings/developer.py:53 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:53 #, python-format msgid "SSH Keys" msgstr "SSH 키" -#: system/ui/widgets/network.py:310 +#: system/ui/widgets/network.py:316 #, python-format msgid "Scanning Wi-Fi networks..." msgstr "Wi‑Fi 네트워크 검색 중..." -#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/option_dialog.py:37 #, python-format msgid "Select" msgstr "선택" -#: selfdrive/ui/layouts/settings/software.py:183 +#: openpilot/selfdrive/ui/layouts/settings/software.py:203 #, python-format msgid "Select a branch" msgstr "브랜치 선택" -#: selfdrive/ui/layouts/settings/device.py:91 +#: openpilot/selfdrive/ui/layouts/settings/device.py:89 #, python-format msgid "Select a language" msgstr "언어 선택" -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "Serial" msgstr "시리얼" -#: selfdrive/ui/widgets/offroad_alerts.py:106 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:106 #, python-format msgid "Snooze Update" msgstr "업데이트 나중에 알림" -#: selfdrive/ui/layouts/settings/settings.py:65 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:62 msgid "Software" msgstr "소프트웨어" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Standard" msgstr "표준" -#: selfdrive/ui/layouts/settings/toggles.py:22 -msgid "" -"Standard is recommended. In aggressive mode, openpilot will follow lead cars " -"closer and be more aggressive with the gas and brake. In relaxed mode " -"openpilot will stay further away from lead cars. On supported cars, you can " -"cycle through these personalities with your steering wheel distance button." -msgstr "" -"표준을 권장합니다. 공격적 모드에서는 앞차를 더 가깝게 따라가고 가감속이 더 적" -"극적입니다. 편안한 모드에서는 앞차와 거리를 더 둡니다. 지원 차량에서는 스티어" -"링의 차간 버튼으로 이 성향들을 전환할 수 있습니다." - -#: selfdrive/ui/onroad/alert_renderer.py:59 -#: selfdrive/ui/onroad/alert_renderer.py:65 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:59 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:65 #, python-format msgid "System Unresponsive" msgstr "시스템 응답 없음" -#: selfdrive/ui/onroad/alert_renderer.py:58 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:58 #, python-format msgid "TAKE CONTROL IMMEDIATELY" msgstr "즉시 수동 조작하세요" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 -#: selfdrive/ui/layouts/sidebar.py:127 selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "TEMP" msgstr "온도" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "Target Branch" msgstr "대상 브랜치" -#: system/ui/widgets/network.py:124 +#: system/ui/widgets/network.py:121 #, python-format msgid "Tethering Password" msgstr "테더링 비밀번호" -#: selfdrive/ui/layouts/settings/settings.py:64 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:61 msgid "Toggles" msgstr "토글" -#: selfdrive/ui/layouts/settings/software.py:72 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:79 +#, python-format +msgid "UI Debug Mode" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "UNINSTALL" msgstr "제거" -#: selfdrive/ui/layouts/home.py:155 +#: openpilot/selfdrive/ui/layouts/home.py:155 #, python-format msgid "UPDATE" msgstr "업데이트" -#: selfdrive/ui/layouts/settings/software.py:72 -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "Uninstall" msgstr "제거" -#: selfdrive/ui/layouts/sidebar.py:117 +#: openpilot/selfdrive/ui/layouts/sidebar.py:117 msgid "Unknown" msgstr "알수없음" -#: selfdrive/ui/layouts/settings/software.py:48 +#: openpilot/selfdrive/ui/layouts/settings/software.py:55 #, python-format msgid "Updates are only downloaded while the car is off." msgstr "업데이트는 차량 전원이 꺼져 있을 때만 다운로드됩니다." -#: selfdrive/ui/widgets/prime.py:33 +#: openpilot/selfdrive/ui/widgets/prime.py:33 #, python-format msgid "Upgrade Now" msgstr "지금 업그레이드" -#: selfdrive/ui/layouts/settings/toggles.py:31 -msgid "" -"Upload data from the driver facing camera and help improve the driver " -"monitoring algorithm." -msgstr "" -"운전자 방향 카메라 데이터를 업로드하여 운전자 모니터링 알고리즘 개선에 도움" -"을 주세요." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:31 +msgid "Upload data from the driver facing camera and help improve the driver monitoring algorithm." +msgstr "운전자 방향 카메라 데이터를 업로드하여 운전자 모니터링 알고리즘 개선에 도움을 주세요." -#: selfdrive/ui/layouts/settings/toggles.py:88 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:88 #, python-format msgid "Use Metric System" msgstr "미터법 사용" -#: selfdrive/ui/layouts/settings/toggles.py:17 -msgid "" -"Use the openpilot system for adaptive cruise control and lane keep driver " -"assistance. Your attention is required at all times to use this feature." -msgstr "" -"ACC 및 차선 유지 보조에 openpilot을 사용합니다. 이 기능을 사용할 때는 항상 주" -"의가 필요합니다." - -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 msgid "VEHICLE" msgstr "차량" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "VIEW" msgstr "보기" -#: selfdrive/ui/onroad/alert_renderer.py:52 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:52 #, python-format msgid "Waiting to start" msgstr "시작 대기 중" -#: selfdrive/ui/layouts/settings/developer.py:19 -msgid "" -"Warning: This grants SSH access to all public keys in your GitHub settings. " -"Never enter a GitHub username other than your own. A comma employee will " -"NEVER ask you to add their GitHub username." -msgstr "" -"경고: 이는 GitHub 설정의 모든 공개 키에 SSH 액세스를 부여합니다. 자신의 것이 " -"아닌 GitHub 사용자 이름을 절대 입력하지 마세요. comma 직원이 본인의 GitHub 사" -"용자 이름 추가를 요구하는 일은 결코 없습니다." - -#: selfdrive/ui/layouts/onboarding.py:111 +#: openpilot/selfdrive/ui/layouts/onboarding.py:115 #, python-format msgid "Welcome to openpilot" msgstr "openpilot에 오신 것을 환영합니다" -#: selfdrive/ui/layouts/settings/toggles.py:20 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:20 msgid "When enabled, pressing the accelerator pedal will disengage openpilot." msgstr "이 옵션을 켜면 가속 페달을 밟을 때 openpilot이 해제됩니다." -#: selfdrive/ui/layouts/sidebar.py:44 +#: openpilot/selfdrive/ui/layouts/sidebar.py:44 msgid "Wi-Fi" msgstr "Wi‑Fi" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Wi-Fi Network Metered" msgstr "Wi‑Fi 네트워크 종량제" -#: system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:320 #, python-format msgid "Wrong password" msgstr "비밀번호가 올바르지 않습니다" -#: selfdrive/ui/layouts/onboarding.py:145 +#: openpilot/selfdrive/ui/layouts/onboarding.py:149 #, python-format msgid "You must accept the Terms and Conditions in order to use openpilot." msgstr "openpilot을 사용하려면 약관에 동의해야 합니다." -#: selfdrive/ui/layouts/onboarding.py:112 +#: openpilot/selfdrive/ui/layouts/onboarding.py:116 #, python-format -msgid "" -"You must accept the Terms and Conditions to use openpilot. Read the latest " -"terms at https://comma.ai/terms before continuing." -msgstr "" -"openpilot을 사용하려면 약관에 동의해야 합니다. 계속하기 전에 https://comma." -"ai/terms 에서 최신 약관을 읽어주세요." +msgid "You must accept the Terms and Conditions to use openpilot. Read the latest terms at https://comma.ai/terms before continuing." +msgstr "openpilot을 사용하려면 약관에 동의해야 합니다. 계속하기 전에 https://comma.ai/terms 에서 최신 약관을 읽어주세요." -#: selfdrive/ui/onroad/driver_camera_dialog.py:34 +#: openpilot/selfdrive/ui/onroad/driver_camera_dialog.py:38 #, python-format msgid "camera starting" msgstr "카메라 시작 중" -#: selfdrive/ui/widgets/prime.py:63 +#: openpilot/selfdrive/ui/layouts/settings/software.py:19 +#, python-format +msgid "checking..." +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:63 #, python-format msgid "comma prime" msgstr "comma 프라임" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "default" msgstr "기본값" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "down" msgstr "아래" -#: selfdrive/ui/layouts/settings/software.py:106 +#: openpilot/selfdrive/ui/layouts/settings/software.py:20 +#, python-format +msgid "downloading..." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:116 #, python-format msgid "failed to check for update" msgstr "업데이트 확인 실패" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: openpilot/selfdrive/ui/layouts/settings/software.py:21 +#, python-format +msgid "finalizing update..." +msgstr "" + +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:321 #, python-format msgid "for \"{}\"" msgstr "\"{}\"용" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "km/h" msgstr "km/h" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "leave blank for automatic configuration" msgstr "자동 구성을 사용하려면 비워 두세요" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "left" msgstr "왼쪽" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "metered" msgstr "종량제" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "mph" msgstr "mph" -#: selfdrive/ui/layouts/settings/software.py:20 +#: openpilot/selfdrive/ui/layouts/settings/software.py:27 #, python-format msgid "never" msgstr "없음" -#: selfdrive/ui/layouts/settings/software.py:31 +#: openpilot/selfdrive/ui/layouts/settings/software.py:38 #, python-format msgid "now" msgstr "지금" -#: selfdrive/ui/layouts/settings/developer.py:71 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:71 #, python-format msgid "openpilot Longitudinal Control (Alpha)" msgstr "openpilot 롱컨 제어(알파)" -#: selfdrive/ui/onroad/alert_renderer.py:51 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:51 #, python-format msgid "openpilot Unavailable" msgstr "openpilot 사용 불가" -#: selfdrive/ui/layouts/settings/toggles.py:158 -#, python-format -msgid "" -"openpilot defaults to driving in chill mode. Experimental mode enables alpha-" -"level features that aren't ready for chill mode. Experimental features are " -"listed below:

End-to-End Longitudinal Control


Let the driving " -"model control the gas and brakes. openpilot will drive as it thinks a human " -"would, including stopping for red lights and stop signs. Since the driving " -"model decides the speed to drive, the set speed will only act as an upper " -"bound. This is an alpha quality feature; mistakes should be expected." -"

New Driving Visualization


The driving visualization will " -"transition to the road-facing wide-angle camera at low speeds to better show " -"some turns. The Experimental mode logo will also be shown in the top right " -"corner." -msgstr "" -"openpilot은 기본적으로 안정적 모드로 주행합니다. 실험 모드를 사용하면 안정적 모드에 " -"아직 준비되지 않은 알파 수준의 기능이 활성화됩니다. 실험 기능은 아래와 같습니" -"다:

엔드투엔드 롱컨 제어


주행 모델이 가속과 제동을 제어합니" -"다. openpilot은 빨간 신호 및 정지 표지에서의 정지를 포함해 사람이 운전한다고 " -"판단하는 방식으로 주행합니다. 주행 속도는 모델이 결정하므로 설정 속도는 상한" -"으로만 동작합니다. 알파 품질 기능이므로 오작동이 발생할 수 있습니다.

" -"새로운 주행 시각화


저속에서는 도로 방향의 광각 카메라로 전환되어 일" -"부 회전을 더 잘 보여줍니다. 화면 오른쪽 위에는 실험 모드 로고도 표시됩니다." - -#: selfdrive/ui/layouts/settings/device.py:165 -#, python-format -msgid "" -"openpilot is continuously calibrating, resetting is rarely required. " -"Resetting calibration will restart openpilot if the car is powered on." -msgstr "" -"openpilot은 지속적으로 보정을 진행하므로 재설정이 필요한 경우는 드뭅니다. 차" -"량 전원이 켜져 있을 때 보정을 재설정하면 openpilot이 재시작됩니다." - -#: selfdrive/ui/layouts/settings/firehose.py:20 -msgid "" -"openpilot learns to drive by watching humans, like you, drive.\n" -"\n" -"Firehose Mode allows you to maximize your training data uploads to improve " -"openpilot's driving models. More data means bigger models, which means " -"better Experimental Mode." -msgstr "" -"openpilot은 당신과 같은 사람의 운전을 보며 운전을 학습합니다.\n" -"\n" -"Firehose 모드는 학습 데이터 업로드를 최대화하여 openpilot의 주행 모델을 개선" -"할 수 있게 해줍니다. 데이터가 많을수록 모델은 커지고, 실험 모드는 더 좋아집니" -"다." - -#: selfdrive/ui/layouts/settings/toggles.py:183 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:184 #, python-format msgid "openpilot longitudinal control may come in a future update." msgstr "openpilot 롱컨 제어는 향후 업데이트에서 제공될 수 있습니다." -#: selfdrive/ui/layouts/settings/device.py:26 -msgid "" -"openpilot requires the device to be mounted within 4° left or right and " -"within 5° up or 9° down." +#: openpilot/selfdrive/ui/layouts/settings/device.py:25 +msgid "openpilot requires the device to be mounted within 4° left or right and within 5° up or 9° down." msgstr "openpilot은 장치를 좌우 4°, 위쪽 5°, 아래쪽 9° 이내로 장착해야 합니다." -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "right" msgstr "오른쪽" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "unmetered" msgstr "비종량제" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "up" msgstr "위" -#: selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:127 #, python-format msgid "up to date, last checked never" msgstr "최신입니다. 마지막 확인: 없음" -#: selfdrive/ui/layouts/settings/software.py:115 +#: openpilot/selfdrive/ui/layouts/settings/software.py:125 #, python-format msgid "up to date, last checked {}" msgstr "최신입니다. 마지막 확인: {}" -#: selfdrive/ui/layouts/settings/software.py:109 +#: openpilot/selfdrive/ui/layouts/settings/software.py:119 #, python-format msgid "update available" msgstr "업데이트 가능" -#: selfdrive/ui/layouts/home.py:169 +#: openpilot/selfdrive/ui/layouts/home.py:169 #, python-format msgid "{} ALERT" msgid_plural "{} ALERTS" msgstr[0] "{}건의 알림" -#: selfdrive/ui/layouts/settings/software.py:40 +#: openpilot/selfdrive/ui/layouts/settings/software.py:47 #, python-format msgid "{} day ago" msgid_plural "{} days ago" msgstr[0] "{}일 전" -#: selfdrive/ui/layouts/settings/software.py:37 +#: openpilot/selfdrive/ui/layouts/settings/software.py:44 #, python-format msgid "{} hour ago" msgid_plural "{} hours ago" msgstr[0] "{}시간 전" -#: selfdrive/ui/layouts/settings/software.py:34 +#: openpilot/selfdrive/ui/layouts/settings/software.py:41 #, python-format msgid "{} minute ago" msgid_plural "{} minutes ago" msgstr[0] "{}분 전" -#: selfdrive/ui/layouts/settings/firehose.py:111 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:70 #, python-format msgid "{} segment of your driving is in the training dataset so far." msgid_plural "{} segments of your driving is in the training dataset so far." msgstr[0] "현재까지 귀하의 주행 {}구간이 학습 데이터셋에 포함되었습니다." -#: selfdrive/ui/widgets/prime.py:62 +#: openpilot/selfdrive/ui/widgets/prime.py:62 #, python-format msgid "✓ SUBSCRIBED" msgstr "✓ 구독됨" -#: selfdrive/ui/widgets/setup.py:22 +#: openpilot/selfdrive/ui/widgets/setup.py:21 #, python-format msgid "🔥 Firehose Mode 🔥" msgstr "🔥 파이어호스 모드 🔥" + diff --git a/selfdrive/ui/translations/app_pt-BR.po b/selfdrive/ui/translations/app_pt-BR.po index 84b53c6e8d..1adb797c88 100644 --- a/selfdrive/ui/translations/app_pt-BR.po +++ b/selfdrive/ui/translations/app_pt-BR.po @@ -19,1202 +19,1018 @@ msgstr "" "X-Language: pt_BR\n" "X-Source-Language: C\n" -#: selfdrive/ui/layouts/settings/device.py:160 +#: openpilot/selfdrive/ui/layouts/settings/device.py:152 #, python-format msgid " Steering torque response calibration is complete." msgstr " A calibração da resposta de torque da direção foi concluída." -#: selfdrive/ui/layouts/settings/device.py:158 +#: openpilot/selfdrive/ui/layouts/settings/device.py:150 #, python-format msgid " Steering torque response calibration is {}% complete." msgstr " A calibração da resposta de torque da direção está {}% concluída." -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid " Your device is pointed {:.1f}° {} and {:.1f}° {}." msgstr " Seu dispositivo está apontado {:.1f}° {} e {:.1f}° {}." -#: selfdrive/ui/layouts/sidebar.py:43 +#: openpilot/selfdrive/ui/layouts/sidebar.py:43 msgid "--" msgstr "--" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "1 year of drive storage" msgstr "1 ano de armazenamento de condução" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "24/7 LTE connectivity" msgstr "Conectividade LTE 24/7" -#: selfdrive/ui/layouts/sidebar.py:46 +#: openpilot/selfdrive/ui/layouts/sidebar.py:46 msgid "2G" msgstr "2G" -#: selfdrive/ui/layouts/sidebar.py:47 +#: openpilot/selfdrive/ui/layouts/sidebar.py:47 msgid "3G" msgstr "3G" -#: selfdrive/ui/layouts/sidebar.py:49 +#: openpilot/selfdrive/ui/layouts/sidebar.py:49 msgid "5G" msgstr "5G" -#: selfdrive/ui/layouts/settings/developer.py:23 -msgid "" -"WARNING: openpilot longitudinal control is in alpha for this car and will " -"disable Automatic Emergency Braking (AEB).

On this car, openpilot " -"defaults to the car's built-in ACC instead of openpilot's longitudinal " -"control. Enable this to switch to openpilot longitudinal control. Enabling " -"Experimental mode is recommended when enabling openpilot longitudinal " -"control alpha. Changing this setting will restart openpilot if the car is " -"powered on." -msgstr "" -"AVISO: o controle longitudinal do openpilot está em alpha para este carro " -"e desativará a Frenagem Automática de Emergência (AEB).

Neste " -"carro, o openpilot usa por padrão o ACC integrado do carro em vez do " -"controle longitudinal do openpilot. Ative isto para alternar para o controle " -"longitudinal do openpilot. Recomenda-se ativar o Modo Experimental ao ativar " -"o controle longitudinal do openpilot em alpha." - -#: selfdrive/ui/layouts/settings/device.py:148 +#: openpilot/selfdrive/ui/layouts/settings/device.py:140 #, python-format msgid "

Steering lag calibration is complete." msgstr "

A calibração da latência da direção está concluída." -#: selfdrive/ui/layouts/settings/device.py:146 +#: openpilot/selfdrive/ui/layouts/settings/device.py:138 #, python-format msgid "

Steering lag calibration is {}% complete." msgstr "

A calibração da latência da direção está {}% concluída." -#: selfdrive/ui/layouts/settings/firehose.py:138 -#, python-format -msgid "ACTIVE" -msgstr "ATIVO" - -#: selfdrive/ui/layouts/settings/developer.py:15 -msgid "" -"ADB (Android Debug Bridge) allows connecting to your device over USB or over " -"the network. See https://docs.comma.ai/how-to/connect-to-comma for more info." -msgstr "" -"ADB (Android Debug Bridge) permite conectar ao seu dispositivo via USB ou " -"pela rede. Veja https://docs.comma.ai/how-to/connect-to-comma para mais " -"informações." - -#: selfdrive/ui/widgets/ssh_key.py:30 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:30 msgid "ADD" msgstr "ADICIONAR" -#: system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:136 #, python-format msgid "APN Setting" msgstr "Configuração de APN" -#: selfdrive/ui/widgets/offroad_alerts.py:109 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:109 #, python-format msgid "Acknowledge Excessive Actuation" msgstr "Reconhecer Atuação Excessiva" -#: system/ui/widgets/network.py:74 system/ui/widgets/network.py:95 +#: system/ui/widgets/network.py:92 +#: system/ui/widgets/network.py:74 #, python-format msgid "Advanced" msgstr "Avançado" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Aggressive" msgstr "Agressivo" -#: selfdrive/ui/layouts/onboarding.py:116 +#: openpilot/selfdrive/ui/layouts/onboarding.py:120 #, python-format msgid "Agree" msgstr "Concordo" -#: selfdrive/ui/layouts/settings/toggles.py:70 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:70 #, python-format msgid "Always-On Driver Monitoring" msgstr "Monitoramento de Motorista Sempre Ativo" -#: selfdrive/ui/layouts/settings/toggles.py:186 -#, python-format -msgid "" -"An alpha version of openpilot longitudinal control can be tested, along with " -"Experimental mode, on non-release branches." -msgstr "" -"Uma versão alpha do controle longitudinal do openpilot pode ser testada, " -"junto com o Modo Experimental, em ramificações fora de release." - -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 #, python-format msgid "Are you sure you want to power off?" msgstr "Tem certeza de que deseja desligar?" -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 #, python-format msgid "Are you sure you want to reboot?" msgstr "Tem certeza de que deseja reiniciar?" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Are you sure you want to reset calibration?" msgstr "Tem certeza de que deseja redefinir a calibração?" -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 #, python-format msgid "Are you sure you want to uninstall?" msgstr "Tem certeza de que deseja desinstalar?" -#: system/ui/widgets/network.py:99 selfdrive/ui/layouts/onboarding.py:147 +#: system/ui/widgets/network.py:96 +#: openpilot/selfdrive/ui/layouts/onboarding.py:151 #, python-format msgid "Back" msgstr "Voltar" -#: selfdrive/ui/widgets/prime.py:38 +#: openpilot/selfdrive/ui/widgets/prime.py:38 #, python-format msgid "Become a comma prime member at connect.comma.ai" msgstr "Torne-se membro comma prime em connect.comma.ai" -#: selfdrive/ui/widgets/pairing_dialog.py:130 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:119 #, python-format msgid "Bookmark connect.comma.ai to your home screen to use it like an app" msgstr "Adicione connect.comma.ai à tela inicial para usá-lo como um app" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "CHANGE" msgstr "ALTERAR" -#: selfdrive/ui/layouts/settings/software.py:50 -#: selfdrive/ui/layouts/settings/software.py:107 -#: selfdrive/ui/layouts/settings/software.py:118 -#: selfdrive/ui/layouts/settings/software.py:147 +#: openpilot/selfdrive/ui/layouts/settings/software.py:157 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 +#: openpilot/selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:128 #, python-format msgid "CHECK" msgstr "VERIFICAR" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "CHILL MODE ON" msgstr "MODO CHILL ATIVO" -#: system/ui/widgets/network.py:155 selfdrive/ui/layouts/sidebar.py:73 -#: selfdrive/ui/layouts/sidebar.py:134 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:138 +#: system/ui/widgets/network.py:152 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 #, python-format msgid "CONNECT" msgstr "CONECTAR" -#: system/ui/widgets/network.py:369 +#: system/ui/widgets/network.py:376 #, python-format msgid "CONNECTING..." msgstr "CONECTANDO..." -#: system/ui/widgets/confirm_dialog.py:23 -#: system/ui/widgets/option_dialog.py:35 system/ui/widgets/keyboard.py:81 -#: system/ui/widgets/network.py:318 +#: system/ui/widgets/network.py:326 +#: system/ui/widgets/confirm_dialog.py:24 +#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/keyboard.py:83 #, python-format msgid "Cancel" msgstr "Cancelar" -#: system/ui/widgets/network.py:134 +#: system/ui/widgets/network.py:131 #, python-format msgid "Cellular Metered" msgstr "Dados móveis limitados" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "Change Language" msgstr "Alterar Idioma" -#: selfdrive/ui/layouts/settings/toggles.py:125 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:125 #, python-format msgid "Changing this setting will restart openpilot if the car is powered on." -msgstr "" -"Alterar esta configuração reiniciará o openpilot se o carro estiver ligado." +msgstr "Alterar esta configuração reiniciará o openpilot se o carro estiver ligado." -#: selfdrive/ui/widgets/pairing_dialog.py:129 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:118 #, python-format msgid "Click \"add new device\" and scan the QR code on the right" msgstr "Toque em \"adicionar novo dispositivo\" e escaneie o QR code à direita" -#: selfdrive/ui/widgets/offroad_alerts.py:104 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:104 #, python-format msgid "Close" msgstr "Fechar" -#: selfdrive/ui/layouts/settings/software.py:49 +#: openpilot/selfdrive/ui/layouts/settings/software.py:56 #, python-format msgid "Current Version" msgstr "Versão Atual" -#: selfdrive/ui/layouts/settings/software.py:110 +#: openpilot/selfdrive/ui/layouts/settings/software.py:120 #, python-format msgid "DOWNLOAD" msgstr "BAIXAR" -#: selfdrive/ui/layouts/onboarding.py:115 +#: openpilot/selfdrive/ui/layouts/onboarding.py:119 #, python-format msgid "Decline" msgstr "Recusar" -#: selfdrive/ui/layouts/onboarding.py:148 +#: openpilot/selfdrive/ui/layouts/onboarding.py:152 #, python-format msgid "Decline, uninstall openpilot" msgstr "Recusar, desinstalar o openpilot" -#: selfdrive/ui/layouts/settings/settings.py:67 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:64 msgid "Developer" msgstr "Desenvolv" -#: selfdrive/ui/layouts/settings/settings.py:62 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:59 msgid "Device" msgstr "Dispositivo" -#: selfdrive/ui/layouts/settings/toggles.py:58 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:58 #, python-format msgid "Disengage on Accelerator Pedal" msgstr "Desativar ao pressionar o acelerador" -#: selfdrive/ui/layouts/settings/device.py:184 +#: openpilot/selfdrive/ui/layouts/settings/device.py:176 #, python-format msgid "Disengage to Power Off" msgstr "Desativar para Desligar" -#: selfdrive/ui/layouts/settings/device.py:172 +#: openpilot/selfdrive/ui/layouts/settings/device.py:164 #, python-format msgid "Disengage to Reboot" msgstr "Desativar para Reiniciar" -#: selfdrive/ui/layouts/settings/device.py:103 +#: openpilot/selfdrive/ui/layouts/settings/device.py:95 #, python-format msgid "Disengage to Reset Calibration" msgstr "Desativar para Redefinir Calibração" -#: selfdrive/ui/layouts/settings/toggles.py:32 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:32 msgid "Display speed in km/h instead of mph." msgstr "Exibir velocidade em km/h em vez de mph." -#: selfdrive/ui/layouts/settings/device.py:59 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 #, python-format msgid "Dongle ID" msgstr "ID do Dongle" -#: selfdrive/ui/layouts/settings/software.py:50 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 #, python-format msgid "Download" msgstr "Baixar" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "Driver Camera" msgstr "Câmera do Motorista" -#: selfdrive/ui/layouts/settings/toggles.py:96 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:96 #, python-format msgid "Driving Personality" msgstr "Personalidade" -#: system/ui/widgets/network.py:123 system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:136 #, python-format msgid "EDIT" msgstr "EDITAR" -#: selfdrive/ui/layouts/sidebar.py:138 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 msgid "ERROR" msgstr "ERRO" -#: selfdrive/ui/layouts/sidebar.py:45 +#: openpilot/selfdrive/ui/layouts/sidebar.py:45 msgid "ETH" msgstr "ETH" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "EXPERIMENTAL MODE ON" msgstr "MODO EXPERIMENTAL ATIVO" -#: selfdrive/ui/layouts/settings/developer.py:166 -#: selfdrive/ui/layouts/settings/toggles.py:228 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:229 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:180 #, python-format msgid "Enable" msgstr "Ativar" -#: selfdrive/ui/layouts/settings/developer.py:39 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:39 #, python-format msgid "Enable ADB" msgstr "Ativar ADB" -#: selfdrive/ui/layouts/settings/toggles.py:64 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:64 #, python-format msgid "Enable Lane Departure Warnings" msgstr "Ativar alertas de saída de faixa" -#: system/ui/widgets/network.py:129 +#: system/ui/widgets/network.py:126 #, python-format msgid "Enable Roaming" msgstr "Ativar openpilot" -#: selfdrive/ui/layouts/settings/developer.py:48 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:48 #, python-format msgid "Enable SSH" msgstr "Ativar SSH" -#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:117 #, python-format msgid "Enable Tethering" msgstr "Ativar alertas de saída de faixa" -#: selfdrive/ui/layouts/settings/toggles.py:30 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:30 msgid "Enable driver monitoring even when openpilot is not engaged." -msgstr "" -"Ativar monitoramento do motorista mesmo quando o openpilot não está engajado." +msgstr "Ativar monitoramento do motorista mesmo quando o openpilot não está engajado." -#: selfdrive/ui/layouts/settings/toggles.py:46 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:46 #, python-format msgid "Enable openpilot" msgstr "Ativar openpilot" -#: selfdrive/ui/layouts/settings/toggles.py:189 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:190 #, python-format -msgid "" -"Enable the openpilot longitudinal control (alpha) toggle to allow " -"Experimental mode." -msgstr "" -"Ative a opção de controle longitudinal do openpilot (alpha) para permitir o " -"Modo Experimental." +msgid "Enable the openpilot longitudinal control (alpha) toggle to allow Experimental mode." +msgstr "Ative a opção de controle longitudinal do openpilot (alpha) para permitir o Modo Experimental." -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "Enter APN" msgstr "Digite APN" -#: system/ui/widgets/network.py:241 +#: system/ui/widgets/network.py:243 #, python-format msgid "Enter SSID" msgstr "Digite SSID" -#: system/ui/widgets/network.py:254 +#: system/ui/widgets/network.py:257 #, python-format msgid "Enter new tethering password" msgstr "Digite nova senha tethering" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:320 #, python-format msgid "Enter password" msgstr "Digite a senha" -#: selfdrive/ui/widgets/ssh_key.py:89 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:89 #, python-format msgid "Enter your GitHub username" msgstr "Digite seu nome de usuário do GitHub" -#: system/ui/widgets/list_view.py:123 system/ui/widgets/list_view.py:160 +#: system/ui/widgets/list_view.py:123 +#: system/ui/widgets/list_view.py:160 #, python-format msgid "Error" msgstr "Erro" -#: selfdrive/ui/layouts/settings/toggles.py:52 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:52 #, python-format msgid "Experimental Mode" msgstr "Modo Experimental" -#: selfdrive/ui/layouts/settings/toggles.py:181 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:182 #, python-format -msgid "" -"Experimental mode is currently unavailable on this car since the car's stock " -"ACC is used for longitudinal control." -msgstr "" -"O Modo Experimental está indisponível neste carro pois o ACC original do " -"carro é usado para controle longitudinal." +msgid "Experimental mode is currently unavailable on this car since the car's stock ACC is used for longitudinal control." +msgstr "O Modo Experimental está indisponível neste carro pois o ACC original do carro é usado para controle longitudinal." -#: system/ui/widgets/network.py:373 +#: system/ui/widgets/network.py:380 #, python-format msgid "FORGETTING..." msgstr "ESQUECENDO..." -#: selfdrive/ui/widgets/setup.py:44 +#: openpilot/selfdrive/ui/widgets/setup.py:43 #, python-format msgid "Finish Setup" msgstr "Configure" -#: selfdrive/ui/layouts/settings/settings.py:66 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:63 msgid "Firehose" msgstr "Firehose" -#: selfdrive/ui/layouts/settings/firehose.py:18 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:10 msgid "Firehose Mode" msgstr "Modo Firehose" -#: selfdrive/ui/layouts/settings/firehose.py:25 -msgid "" -"For maximum effectiveness, bring your device inside and connect to a good " -"USB-C adapter and Wi-Fi weekly.\n" -"\n" -"Firehose Mode can also work while you're driving if connected to a hotspot " -"or unlimited SIM card.\n" -"\n" -"\n" -"Frequently Asked Questions\n" -"\n" -"Does it matter how or where I drive? Nope, just drive as you normally " -"would.\n" -"\n" -"Do all of my segments get pulled in Firehose Mode? No, we selectively pull a " -"subset of your segments.\n" -"\n" -"What's a good USB-C adapter? Any fast phone or laptop charger should be " -"fine.\n" -"\n" -"Does it matter which software I run? Yes, only upstream openpilot (and " -"particular forks) are able to be used for training." -msgstr "" -"Para máxima efetividade, leve seu dispositivo para dentro e conecte a um bom " -"adaptador USB-C e Wi‑Fi semanalmente.\n" -"\n" -"O Modo Firehose também pode funcionar enquanto você dirige se estiver " -"conectado a um hotspot ou a um SIM ilimitado.\n" -"\n" -"\n" -"Perguntas Frequentes\n" -"\n" -"Importa como ou onde eu dirijo? Não, apenas dirija como normalmente.\n" -"\n" -"Todos os meus segmentos são puxados no Modo Firehose? Não, puxamos " -"seletivamente um subconjunto dos seus segmentos.\n" -"\n" -"Qual é um bom adaptador USB‑C? Qualquer carregador rápido de telefone ou " -"laptop serve.\n" -"\n" -"Importa qual software eu executo? Sim, apenas o openpilot upstream (e forks " -"específicos) podem ser usados para treinamento." - -#: system/ui/widgets/network.py:318 system/ui/widgets/network.py:451 +#: system/ui/widgets/network.py:458 +#: system/ui/widgets/network.py:326 #, python-format msgid "Forget" msgstr "Esquecer" -#: system/ui/widgets/network.py:319 +#: system/ui/widgets/network.py:327 #, python-format msgid "Forget Wi-Fi Network \"{}\"?" msgstr "Esquecer rede Wi-Fi \"{}\"?" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 msgid "GOOD" msgstr "BOM" -#: selfdrive/ui/widgets/pairing_dialog.py:128 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:117 #, python-format msgid "Go to https://connect.comma.ai on your phone" msgstr "Acesse https://connect.comma.ai no seu telefone" -#: selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "HIGH" msgstr "ALTO" -#: system/ui/widgets/network.py:155 +#: system/ui/widgets/network.py:152 #, python-format msgid "Hidden Network" msgstr "Rede" -#: selfdrive/ui/layouts/settings/firehose.py:140 -#, python-format -msgid "INACTIVE: connect to an unmetered network" -msgstr "INATIVO: conecte a uma rede sem franquia" - -#: selfdrive/ui/layouts/settings/software.py:53 -#: selfdrive/ui/layouts/settings/software.py:136 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 +#: openpilot/selfdrive/ui/layouts/settings/software.py:146 #, python-format msgid "INSTALL" msgstr "INSTALAR" -#: system/ui/widgets/network.py:150 +#: system/ui/widgets/network.py:147 #, python-format msgid "IP Address" msgstr "Endereço IP" -#: selfdrive/ui/layouts/settings/software.py:53 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 #, python-format msgid "Install Update" msgstr "Instalar Atualização" -#: selfdrive/ui/layouts/settings/developer.py:56 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:56 #, python-format msgid "Joystick Debug Mode" msgstr "Modo de Depuração do Joystick" -#: selfdrive/ui/widgets/ssh_key.py:29 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:29 msgid "LOADING" msgstr "CARREGANDO" -#: selfdrive/ui/layouts/sidebar.py:48 +#: openpilot/selfdrive/ui/layouts/sidebar.py:48 msgid "LTE" msgstr "LTE" -#: selfdrive/ui/layouts/settings/developer.py:64 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:64 #, python-format msgid "Longitudinal Maneuver Mode" msgstr "Modo de Manobra Longitudinal" -#: selfdrive/ui/onroad/hud_renderer.py:148 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:148 #, python-format msgid "MAX" msgstr "MÁX" -#: selfdrive/ui/widgets/setup.py:75 +#: openpilot/selfdrive/ui/widgets/setup.py:74 #, python-format -msgid "" -"Maximize your training data uploads to improve openpilot's driving models." -msgstr "" -"Maximize seus envios de dados de treinamento para melhorar os modelos de " -"condução do openpilot." +msgid "Maximize your training data uploads to improve openpilot's driving models." +msgstr "Maximize seus envios de dados de treinamento para melhorar os modelos de condução do openpilot." -#: selfdrive/ui/layouts/settings/device.py:59 -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "N/A" msgstr "N/A" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "NO" msgstr "NÃO" -#: selfdrive/ui/layouts/settings/settings.py:63 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:60 msgid "Network" msgstr "Rede" -#: selfdrive/ui/widgets/ssh_key.py:114 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:115 #, python-format msgid "No SSH keys found" msgstr "Nenhuma chave SSH encontrada" -#: selfdrive/ui/widgets/ssh_key.py:126 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:127 #, python-format msgid "No SSH keys found for user '{}'" msgstr "Nenhuma chave SSH encontrada para o usuário '{username}'" -#: selfdrive/ui/widgets/offroad_alerts.py:320 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:321 #, python-format msgid "No release notes available." msgstr "Sem notas de versão disponíveis." -#: selfdrive/ui/layouts/sidebar.py:73 selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 msgid "OFFLINE" msgstr "OFFLINE" -#: system/ui/widgets/html_render.py:263 system/ui/widgets/confirm_dialog.py:93 -#: selfdrive/ui/layouts/sidebar.py:127 +#: system/ui/widgets/confirm_dialog.py:93 +#: system/ui/widgets/html_render.py:263 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 #, python-format msgid "OK" msgstr "OK" -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 msgid "ONLINE" msgstr "ONLINE" -#: selfdrive/ui/widgets/setup.py:20 +#: openpilot/selfdrive/ui/widgets/setup.py:19 #, python-format msgid "Open" msgstr "Abrir" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "PAIR" msgstr "EMPARELHAR" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "PANDA" msgstr "PANDA" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "PREVIEW" msgstr "PRÉVIA" -#: selfdrive/ui/widgets/prime.py:44 +#: openpilot/selfdrive/ui/widgets/prime.py:44 #, python-format msgid "PRIME FEATURES:" msgstr "RECURSOS PRIME:" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "Pair Device" msgstr "Emparelhar Dispositivo" -#: selfdrive/ui/widgets/setup.py:19 +#: openpilot/selfdrive/ui/widgets/setup.py:18 #, python-format msgid "Pair device" msgstr "Emparelhar dispositivo" -#: selfdrive/ui/widgets/pairing_dialog.py:103 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:92 #, python-format msgid "Pair your device to your comma account" msgstr "Emparelhe seu dispositivo à sua conta comma" -#: selfdrive/ui/widgets/setup.py:48 selfdrive/ui/layouts/settings/device.py:24 +#: openpilot/selfdrive/ui/widgets/setup.py:47 +#: openpilot/selfdrive/ui/layouts/settings/device.py:23 #, python-format -msgid "" -"Pair your device with comma connect (connect.comma.ai) and claim your comma " -"prime offer." -msgstr "" -"Emparelhe seu dispositivo com o comma connect (connect.comma.ai) e resgate " -"sua oferta comma prime." +msgid "Pair your device with comma connect (connect.comma.ai) and claim your comma prime offer." +msgstr "Emparelhe seu dispositivo com o comma connect (connect.comma.ai) e resgate sua oferta comma prime." -#: selfdrive/ui/widgets/setup.py:91 +#: openpilot/selfdrive/ui/widgets/setup.py:91 #, python-format msgid "Please connect to Wi-Fi to complete initial pairing" msgstr "Conecte-se ao Wi‑Fi para concluir o emparelhamento inicial" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Power Off" msgstr "Desligar" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Prevent large data uploads when on a metered Wi-Fi connection" msgstr "Evitar uploads grandes de dados em conexões Wi-Fi limitadas" -#: system/ui/widgets/network.py:135 +#: system/ui/widgets/network.py:132 #, python-format msgid "Prevent large data uploads when on a metered cellular connection" msgstr "Evitar uploads grandes de dados em conexões móveis limitadas" -#: selfdrive/ui/layouts/settings/device.py:25 -msgid "" -"Preview the driver facing camera to ensure that driver monitoring has good " -"visibility. (vehicle must be off)" -msgstr "" -"Pré-visualize a câmera voltada para o motorista para garantir que o " -"monitoramento do motorista tenha boa visibilidade. (veículo deve estar " -"desligado)" +#: openpilot/selfdrive/ui/layouts/settings/device.py:24 +msgid "Preview the driver facing camera to ensure that driver monitoring has good visibility. (vehicle must be off)" +msgstr "Pré-visualize a câmera voltada para o motorista para garantir que o monitoramento do motorista tenha boa visibilidade. (veículo deve estar desligado)" -#: selfdrive/ui/widgets/pairing_dialog.py:161 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:150 #, python-format msgid "QR Code Error" msgstr "Erro no QR Code" -#: selfdrive/ui/widgets/ssh_key.py:31 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:31 msgid "REMOVE" msgstr "REMOVER" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "RESET" msgstr "REDEFINIR" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "REVIEW" msgstr "REVISAR" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Reboot" msgstr "Reiniciar" -#: selfdrive/ui/onroad/alert_renderer.py:66 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:66 #, python-format msgid "Reboot Device" msgstr "Reiniciar Dispositivo" -#: selfdrive/ui/widgets/offroad_alerts.py:112 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:112 #, python-format msgid "Reboot and Update" msgstr "Reiniciar e Atualizar" -#: selfdrive/ui/layouts/settings/toggles.py:27 -msgid "" -"Receive alerts to steer back into the lane when your vehicle drifts over a " -"detected lane line without a turn signal activated while driving over 31 mph " -"(50 km/h)." -msgstr "" -"Receba alertas para voltar à faixa quando seu veículo cruzar uma linha de " -"faixa detectada sem seta ativada ao dirigir acima de 31 mph (50 km/h)." - -#: selfdrive/ui/layouts/settings/toggles.py:76 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:76 #, python-format msgid "Record and Upload Driver Camera" msgstr "Gravar e Enviar Câmera do Motorista" -#: selfdrive/ui/layouts/settings/toggles.py:82 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:82 #, python-format msgid "Record and Upload Microphone Audio" msgstr "Gravar e Enviar Áudio do Microfone" -#: selfdrive/ui/layouts/settings/toggles.py:33 -msgid "" -"Record and store microphone audio while driving. The audio will be included " -"in the dashcam video in comma connect." -msgstr "" -"Grave e armazene o áudio do microfone enquanto dirige. O áudio será incluído " -"no vídeo da dashcam no comma connect." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:33 +msgid "Record and store microphone audio while driving. The audio will be included in the dashcam video in comma connect." +msgstr "Grave e armazene o áudio do microfone enquanto dirige. O áudio será incluído no vídeo da dashcam no comma connect." -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "Regulatory" msgstr "Regulatório" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Relaxed" msgstr "Relaxado" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote access" msgstr "Acesso remoto" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote snapshots" msgstr "Capturas remotas" -#: selfdrive/ui/widgets/ssh_key.py:123 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:124 #, python-format msgid "Request timed out" msgstr "Tempo da solicitação esgotado" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Reset" msgstr "Redefinir" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "Reset Calibration" msgstr "Redefinir Calibração" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "Review Training Guide" msgstr "Revisar Guia de Treinamento" -#: selfdrive/ui/layouts/settings/device.py:27 +#: openpilot/selfdrive/ui/layouts/settings/device.py:26 msgid "Review the rules, features, and limitations of openpilot" msgstr "Revise as regras, recursos e limitações do openpilot" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "SELECT" msgstr "SELECIONAR" -#: selfdrive/ui/layouts/settings/developer.py:53 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:53 #, python-format msgid "SSH Keys" msgstr "Chaves SSH" -#: system/ui/widgets/network.py:310 +#: system/ui/widgets/network.py:316 #, python-format msgid "Scanning Wi-Fi networks..." msgstr "Procurando redes Wi-Fi..." -#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/option_dialog.py:37 #, python-format msgid "Select" msgstr "Selecione" -#: selfdrive/ui/layouts/settings/software.py:183 +#: openpilot/selfdrive/ui/layouts/settings/software.py:203 #, python-format msgid "Select a branch" msgstr "Selecione uma branch" -#: selfdrive/ui/layouts/settings/device.py:91 +#: openpilot/selfdrive/ui/layouts/settings/device.py:89 #, python-format msgid "Select a language" msgstr "Selecione um idioma" -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "Serial" msgstr "Serial" -#: selfdrive/ui/widgets/offroad_alerts.py:106 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:106 #, python-format msgid "Snooze Update" msgstr "Adiar Atualização" -#: selfdrive/ui/layouts/settings/settings.py:65 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:62 msgid "Software" msgstr "Software" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Standard" msgstr "Padrão" -#: selfdrive/ui/layouts/settings/toggles.py:22 -msgid "" -"Standard is recommended. In aggressive mode, openpilot will follow lead cars " -"closer and be more aggressive with the gas and brake. In relaxed mode " -"openpilot will stay further away from lead cars. On supported cars, you can " -"cycle through these personalities with your steering wheel distance button." -msgstr "" -"Padrão é recomendado. No modo agressivo, o openpilot seguirá veículos à " -"frente mais de perto e será mais agressivo com acelerador e freio. No modo " -"relaxado, o openpilot ficará mais longe dos veículos à frente. Em carros " -"compatíveis, você pode alternar essas personalidades com o botão de " -"distância do volante." - -#: selfdrive/ui/onroad/alert_renderer.py:59 -#: selfdrive/ui/onroad/alert_renderer.py:65 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:59 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:65 #, python-format msgid "System Unresponsive" msgstr "Sistema sem resposta" -#: selfdrive/ui/onroad/alert_renderer.py:58 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:58 #, python-format msgid "TAKE CONTROL IMMEDIATELY" msgstr "ASSUMA O CONTROLE IMEDIATAMENTE" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 -#: selfdrive/ui/layouts/sidebar.py:127 selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "TEMP" msgstr "TEMP" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "Target Branch" msgstr "Branch Alvo" -#: system/ui/widgets/network.py:124 +#: system/ui/widgets/network.py:121 #, python-format msgid "Tethering Password" msgstr "Senha Tethering" -#: selfdrive/ui/layouts/settings/settings.py:64 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:61 msgid "Toggles" msgstr "Toggles" -#: selfdrive/ui/layouts/settings/software.py:72 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:79 +#, python-format +msgid "UI Debug Mode" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "UNINSTALL" msgstr "DESINSTALAR" -#: selfdrive/ui/layouts/home.py:155 +#: openpilot/selfdrive/ui/layouts/home.py:155 #, python-format msgid "UPDATE" msgstr "ATUALIZAR" -#: selfdrive/ui/layouts/settings/software.py:72 -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "Uninstall" msgstr "Desinstalar" -#: selfdrive/ui/layouts/sidebar.py:117 +#: openpilot/selfdrive/ui/layouts/sidebar.py:117 msgid "Unknown" msgstr "Desconhecido" -#: selfdrive/ui/layouts/settings/software.py:48 +#: openpilot/selfdrive/ui/layouts/settings/software.py:55 #, python-format msgid "Updates are only downloaded while the car is off." msgstr "Atualizações são baixadas apenas com o carro desligado." -#: selfdrive/ui/widgets/prime.py:33 +#: openpilot/selfdrive/ui/widgets/prime.py:33 #, python-format msgid "Upgrade Now" msgstr "Atualizar Agora" -#: selfdrive/ui/layouts/settings/toggles.py:31 -msgid "" -"Upload data from the driver facing camera and help improve the driver " -"monitoring algorithm." -msgstr "" -"Envie dados da câmera voltada para o motorista e ajude a melhorar o " -"algoritmo de monitoramento do motorista." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:31 +msgid "Upload data from the driver facing camera and help improve the driver monitoring algorithm." +msgstr "Envie dados da câmera voltada para o motorista e ajude a melhorar o algoritmo de monitoramento do motorista." -#: selfdrive/ui/layouts/settings/toggles.py:88 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:88 #, python-format msgid "Use Metric System" msgstr "Usar Sistema Métrico" -#: selfdrive/ui/layouts/settings/toggles.py:17 -msgid "" -"Use the openpilot system for adaptive cruise control and lane keep driver " -"assistance. Your attention is required at all times to use this feature." -msgstr "" -"Use o sistema openpilot para controle de cruzeiro adaptativo e assistência " -"de permanência em faixa. Sua atenção é necessária o tempo todo para usar " -"este recurso." - -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 msgid "VEHICLE" msgstr "VEÍCULO" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "VIEW" msgstr "VER" -#: selfdrive/ui/onroad/alert_renderer.py:52 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:52 #, python-format msgid "Waiting to start" msgstr "Aguardando para iniciar" -#: selfdrive/ui/layouts/settings/developer.py:19 -msgid "" -"Warning: This grants SSH access to all public keys in your GitHub settings. " -"Never enter a GitHub username other than your own. A comma employee will " -"NEVER ask you to add their GitHub username." -msgstr "" -"Aviso: Isso concede acesso SSH a todas as chaves públicas nas suas " -"configurações do GitHub. Nunca informe um nome de usuário do GitHub que não " -"seja o seu. Um funcionário da comma NUNCA pedirá para você adicionar o nome " -"de usuário do GitHub dele." - -#: selfdrive/ui/layouts/onboarding.py:111 +#: openpilot/selfdrive/ui/layouts/onboarding.py:115 #, python-format msgid "Welcome to openpilot" msgstr "Bem-vindo ao openpilot" -#: selfdrive/ui/layouts/settings/toggles.py:20 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:20 msgid "When enabled, pressing the accelerator pedal will disengage openpilot." -msgstr "" -"Quando ativado, pressionar o pedal do acelerador desengajará o openpilot." +msgstr "Quando ativado, pressionar o pedal do acelerador desengajará o openpilot." -#: selfdrive/ui/layouts/sidebar.py:44 +#: openpilot/selfdrive/ui/layouts/sidebar.py:44 msgid "Wi-Fi" msgstr "Wi‑Fi" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Wi-Fi Network Metered" msgstr "Rede Wi-Fi limitada" -#: system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:320 #, python-format msgid "Wrong password" msgstr "Senha errada" -#: selfdrive/ui/layouts/onboarding.py:145 +#: openpilot/selfdrive/ui/layouts/onboarding.py:149 #, python-format msgid "You must accept the Terms and Conditions in order to use openpilot." msgstr "Você deve aceitar os Termos e Condições para usar o openpilot." -#: selfdrive/ui/layouts/onboarding.py:112 +#: openpilot/selfdrive/ui/layouts/onboarding.py:116 #, python-format -msgid "" -"You must accept the Terms and Conditions to use openpilot. Read the latest " -"terms at https://comma.ai/terms before continuing." -msgstr "" -"Você deve aceitar os Termos e Condições para usar o openpilot. Leia os " -"termos mais recentes em https://comma.ai/terms antes de continuar." +msgid "You must accept the Terms and Conditions to use openpilot. Read the latest terms at https://comma.ai/terms before continuing." +msgstr "Você deve aceitar os Termos e Condições para usar o openpilot. Leia os termos mais recentes em https://comma.ai/terms antes de continuar." -#: selfdrive/ui/onroad/driver_camera_dialog.py:34 +#: openpilot/selfdrive/ui/onroad/driver_camera_dialog.py:38 #, python-format msgid "camera starting" msgstr "câmera iniciando" -#: selfdrive/ui/widgets/prime.py:63 +#: openpilot/selfdrive/ui/layouts/settings/software.py:19 +#, python-format +msgid "checking..." +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:63 #, python-format msgid "comma prime" msgstr "comma prime" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "default" msgstr "default" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "down" msgstr "para baixo" -#: selfdrive/ui/layouts/settings/software.py:106 +#: openpilot/selfdrive/ui/layouts/settings/software.py:20 +#, python-format +msgid "downloading..." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:116 #, python-format msgid "failed to check for update" msgstr "falha ao verificar atualização" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: openpilot/selfdrive/ui/layouts/settings/software.py:21 +#, python-format +msgid "finalizing update..." +msgstr "" + +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:321 #, python-format msgid "for \"{}\"" msgstr "para \"{}\"" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "km/h" msgstr "km/h" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "leave blank for automatic configuration" msgstr "deixe em branco para configuração automática" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "left" msgstr "à esquerda" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "metered" msgstr "limitados" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "mph" msgstr "mph" -#: selfdrive/ui/layouts/settings/software.py:20 +#: openpilot/selfdrive/ui/layouts/settings/software.py:27 #, python-format msgid "never" msgstr "nunca" -#: selfdrive/ui/layouts/settings/software.py:31 +#: openpilot/selfdrive/ui/layouts/settings/software.py:38 #, python-format msgid "now" msgstr "agora" -#: selfdrive/ui/layouts/settings/developer.py:71 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:71 #, python-format msgid "openpilot Longitudinal Control (Alpha)" msgstr "Controle Longitudinal do openpilot (Alpha)" -#: selfdrive/ui/onroad/alert_renderer.py:51 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:51 #, python-format msgid "openpilot Unavailable" msgstr "openpilot Indisponível" -#: selfdrive/ui/layouts/settings/toggles.py:158 -#, python-format -msgid "" -"openpilot defaults to driving in chill mode. Experimental mode enables " -"alpha-level features that aren't ready for chill mode. Experimental features " -"are listed below:

End-to-End Longitudinal Control


Let the " -"driving model control the gas and brakes. openpilot will drive as it thinks " -"a human would, including stopping for red lights and stop signs. Since the " -"driving model decides the speed to drive, the set speed will only act as an " -"upper bound. This is an alpha quality feature; mistakes should be " -"expected.

New Driving Visualization


The driving visualization " -"will transition to the road-facing wide-angle camera at low speeds to better " -"show some turns. The Experimental mode logo will also be shown in the top " -"right corner." -msgstr "" -"o openpilot dirige por padrão no modo chill. O Modo Experimental habilita " -"recursos em nível alpha que não estão prontos para o modo chill. Os recursos " -"experimentais são listados abaixo:

Controle Longitudinal " -"End-to-End


Permita que o modelo de condução controle o acelerador e " -"os freios. O openpilot dirigirá como acha que um humano faria, incluindo " -"parar em sinais e semáforos vermelhos. Como o modelo decide a velocidade, a " -"velocidade definida atuará apenas como limite superior. Este é um recurso de " -"qualidade alpha; erros devem ser esperados.

Nova Visualização de " -"Condução


A visualização de condução mudará para a câmera " -"grande-angular voltada para a estrada em baixas velocidades para mostrar " -"melhor algumas curvas. O logotipo do Modo Experimental também será exibido " -"no canto superior direito." - -#: selfdrive/ui/layouts/settings/device.py:165 -#, python-format -msgid "" -"openpilot is continuously calibrating, resetting is rarely required. " -"Resetting calibration will restart openpilot if the car is powered on." -msgstr "" -"O openpilot está continuamente calibrando, resetar é raramente solicitado. " -"Alterar esta configuração reiniciará o openpilot se o carro estiver ligado." - -#: selfdrive/ui/layouts/settings/firehose.py:20 -msgid "" -"openpilot learns to drive by watching humans, like you, drive.\n" -"\n" -"Firehose Mode allows you to maximize your training data uploads to improve " -"openpilot's driving models. More data means bigger models, which means " -"better Experimental Mode." -msgstr "" -"o openpilot aprende a dirigir observando humanos, como você, dirigirem.\n" -"\n" -"O Modo Firehose permite maximizar seus envios de dados de treinamento para " -"melhorar os modelos de condução do openpilot. Mais dados significam modelos " -"maiores, o que significa um Modo Experimental melhor." - -#: selfdrive/ui/layouts/settings/toggles.py:183 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:184 #, python-format msgid "openpilot longitudinal control may come in a future update." -msgstr "" -"o controle longitudinal do openpilot pode vir em uma atualização futura." +msgstr "o controle longitudinal do openpilot pode vir em uma atualização futura." -#: selfdrive/ui/layouts/settings/device.py:26 -msgid "" -"openpilot requires the device to be mounted within 4° left or right and " -"within 5° up or 9° down." -msgstr "" -"o openpilot requer que o dispositivo seja montado dentro de 4° para a " -"esquerda ou direita e dentro de 5° para cima ou 9° para baixo." +#: openpilot/selfdrive/ui/layouts/settings/device.py:25 +msgid "openpilot requires the device to be mounted within 4° left or right and within 5° up or 9° down." +msgstr "o openpilot requer que o dispositivo seja montado dentro de 4° para a esquerda ou direita e dentro de 5° para cima ou 9° para baixo." -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "right" msgstr "à direita" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "unmetered" msgstr "ilimitados" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "up" msgstr "para cima" -#: selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:127 #, python-format msgid "up to date, last checked never" msgstr "atualizado, última verificação: nunca" -#: selfdrive/ui/layouts/settings/software.py:115 +#: openpilot/selfdrive/ui/layouts/settings/software.py:125 #, python-format msgid "up to date, last checked {}" msgstr "atualizado, última verificação: {}" -#: selfdrive/ui/layouts/settings/software.py:109 +#: openpilot/selfdrive/ui/layouts/settings/software.py:119 #, python-format msgid "update available" msgstr "atualização disponível" -#: selfdrive/ui/layouts/home.py:169 +#: openpilot/selfdrive/ui/layouts/home.py:169 #, python-format msgid "{} ALERT" msgid_plural "{} ALERTS" msgstr[0] "{} ALERTA" msgstr[1] "{} ALERTAS" -#: selfdrive/ui/layouts/settings/software.py:40 +#: openpilot/selfdrive/ui/layouts/settings/software.py:47 #, python-format msgid "{} day ago" msgid_plural "{} days ago" msgstr[0] "{} dia atrás" msgstr[1] "{} dias atrás" -#: selfdrive/ui/layouts/settings/software.py:37 +#: openpilot/selfdrive/ui/layouts/settings/software.py:44 #, python-format msgid "{} hour ago" msgid_plural "{} hours ago" msgstr[0] "{} hora atrás" msgstr[1] "{} horas atrás" -#: selfdrive/ui/layouts/settings/software.py:34 +#: openpilot/selfdrive/ui/layouts/settings/software.py:41 #, python-format msgid "{} minute ago" msgid_plural "{} minutes ago" msgstr[0] "{} minuto atrás" msgstr[1] "{} minutos atrás" -#: selfdrive/ui/layouts/settings/firehose.py:111 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:70 #, python-format msgid "{} segment of your driving is in the training dataset so far." msgid_plural "{} segments of your driving is in the training dataset so far." -msgstr[0] "" -"{} segmento da sua condução está no conjunto de treinamento até agora." -msgstr[1] "" -"{} segmentos da sua condução estão no conjunto de treinamento até agora." +msgstr[0] "{} segmento da sua condução está no conjunto de treinamento até agora." +msgstr[1] "{} segmentos da sua condução estão no conjunto de treinamento até agora." -#: selfdrive/ui/widgets/prime.py:62 +#: openpilot/selfdrive/ui/widgets/prime.py:62 #, python-format msgid "✓ SUBSCRIBED" msgstr "✓ ASSINADO" -#: selfdrive/ui/widgets/setup.py:22 +#: openpilot/selfdrive/ui/widgets/setup.py:21 #, python-format msgid "🔥 Firehose Mode 🔥" msgstr "🔥 Modo Firehose 🔥" + diff --git a/selfdrive/ui/translations/app_th.po b/selfdrive/ui/translations/app_th.po index f2e56f2882..facf52d922 100644 --- a/selfdrive/ui/translations/app_th.po +++ b/selfdrive/ui/translations/app_th.po @@ -17,1113 +17,1018 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=1; plural=0;\n" -#: selfdrive/ui/layouts/settings/device.py:160 +#: openpilot/selfdrive/ui/layouts/settings/device.py:152 #, python-format msgid " Steering torque response calibration is complete." msgstr "" -#: selfdrive/ui/layouts/settings/device.py:158 +#: openpilot/selfdrive/ui/layouts/settings/device.py:150 #, python-format msgid " Steering torque response calibration is {}% complete." msgstr "" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid " Your device is pointed {:.1f}° {} and {:.1f}° {}." msgstr "" -#: selfdrive/ui/layouts/sidebar.py:43 +#: openpilot/selfdrive/ui/layouts/sidebar.py:43 msgid "--" msgstr "" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "1 year of drive storage" msgstr "" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "24/7 LTE connectivity" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:46 +#: openpilot/selfdrive/ui/layouts/sidebar.py:46 msgid "2G" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:47 +#: openpilot/selfdrive/ui/layouts/sidebar.py:47 msgid "3G" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:49 +#: openpilot/selfdrive/ui/layouts/sidebar.py:49 msgid "5G" msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:23 -msgid "" -"WARNING: openpilot longitudinal control is in alpha for this car and will " -"disable Automatic Emergency Braking (AEB).

On this car, openpilot " -"defaults to the car's built-in ACC instead of openpilot's longitudinal " -"control. Enable this to switch to openpilot longitudinal control. Enabling " -"Experimental mode is recommended when enabling openpilot longitudinal " -"control alpha. Changing this setting will restart openpilot if the car is " -"powered on." -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:148 +#: openpilot/selfdrive/ui/layouts/settings/device.py:140 #, python-format msgid "

Steering lag calibration is complete." msgstr "" -#: selfdrive/ui/layouts/settings/device.py:146 +#: openpilot/selfdrive/ui/layouts/settings/device.py:138 #, python-format msgid "

Steering lag calibration is {}% complete." msgstr "" -#: selfdrive/ui/layouts/settings/firehose.py:138 -#, python-format -msgid "ACTIVE" -msgstr "" - -#: selfdrive/ui/layouts/settings/developer.py:15 -msgid "" -"ADB (Android Debug Bridge) allows connecting to your device over USB or over " -"the network. See https://docs.comma.ai/how-to/connect-to-comma for more info." -msgstr "" - -#: selfdrive/ui/widgets/ssh_key.py:30 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:30 msgid "ADD" msgstr "" -#: system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:136 #, python-format msgid "APN Setting" msgstr "" -#: selfdrive/ui/widgets/offroad_alerts.py:109 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:109 #, python-format msgid "Acknowledge Excessive Actuation" msgstr "" -#: system/ui/widgets/network.py:74 system/ui/widgets/network.py:95 +#: system/ui/widgets/network.py:92 +#: system/ui/widgets/network.py:74 #, python-format msgid "Advanced" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Aggressive" msgstr "" -#: selfdrive/ui/layouts/onboarding.py:116 +#: openpilot/selfdrive/ui/layouts/onboarding.py:120 #, python-format msgid "Agree" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:70 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:70 #, python-format msgid "Always-On Driver Monitoring" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:186 -#, python-format -msgid "" -"An alpha version of openpilot longitudinal control can be tested, along with " -"Experimental mode, on non-release branches." -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 #, python-format msgid "Are you sure you want to power off?" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 #, python-format msgid "Are you sure you want to reboot?" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Are you sure you want to reset calibration?" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 #, python-format msgid "Are you sure you want to uninstall?" msgstr "" -#: system/ui/widgets/network.py:99 selfdrive/ui/layouts/onboarding.py:147 +#: system/ui/widgets/network.py:96 +#: openpilot/selfdrive/ui/layouts/onboarding.py:151 #, python-format msgid "Back" msgstr "" -#: selfdrive/ui/widgets/prime.py:38 +#: openpilot/selfdrive/ui/widgets/prime.py:38 #, python-format msgid "Become a comma prime member at connect.comma.ai" msgstr "" -#: selfdrive/ui/widgets/pairing_dialog.py:130 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:119 #, python-format msgid "Bookmark connect.comma.ai to your home screen to use it like an app" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "CHANGE" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:50 -#: selfdrive/ui/layouts/settings/software.py:107 -#: selfdrive/ui/layouts/settings/software.py:118 -#: selfdrive/ui/layouts/settings/software.py:147 +#: openpilot/selfdrive/ui/layouts/settings/software.py:157 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 +#: openpilot/selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:128 #, python-format msgid "CHECK" msgstr "" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "CHILL MODE ON" msgstr "" -#: system/ui/widgets/network.py:155 selfdrive/ui/layouts/sidebar.py:73 -#: selfdrive/ui/layouts/sidebar.py:134 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:138 +#: system/ui/widgets/network.py:152 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 #, python-format msgid "CONNECT" msgstr "" -#: system/ui/widgets/network.py:369 +#: system/ui/widgets/network.py:376 #, python-format msgid "CONNECTING..." msgstr "" -#: system/ui/widgets/confirm_dialog.py:23 system/ui/widgets/option_dialog.py:35 -#: system/ui/widgets/keyboard.py:81 system/ui/widgets/network.py:318 +#: system/ui/widgets/network.py:326 +#: system/ui/widgets/confirm_dialog.py:24 +#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/keyboard.py:83 #, python-format msgid "Cancel" msgstr "" -#: system/ui/widgets/network.py:134 +#: system/ui/widgets/network.py:131 #, python-format msgid "Cellular Metered" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "Change Language" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:125 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:125 #, python-format msgid "Changing this setting will restart openpilot if the car is powered on." msgstr "" -#: selfdrive/ui/widgets/pairing_dialog.py:129 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:118 #, python-format msgid "Click \"add new device\" and scan the QR code on the right" msgstr "" -#: selfdrive/ui/widgets/offroad_alerts.py:104 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:104 #, python-format msgid "Close" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:49 +#: openpilot/selfdrive/ui/layouts/settings/software.py:56 #, python-format msgid "Current Version" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:110 +#: openpilot/selfdrive/ui/layouts/settings/software.py:120 #, python-format msgid "DOWNLOAD" msgstr "" -#: selfdrive/ui/layouts/onboarding.py:115 +#: openpilot/selfdrive/ui/layouts/onboarding.py:119 #, python-format msgid "Decline" msgstr "" -#: selfdrive/ui/layouts/onboarding.py:148 +#: openpilot/selfdrive/ui/layouts/onboarding.py:152 #, python-format msgid "Decline, uninstall openpilot" msgstr "" -#: selfdrive/ui/layouts/settings/settings.py:67 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:64 msgid "Developer" msgstr "" -#: selfdrive/ui/layouts/settings/settings.py:62 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:59 msgid "Device" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:58 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:58 #, python-format msgid "Disengage on Accelerator Pedal" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:184 +#: openpilot/selfdrive/ui/layouts/settings/device.py:176 #, python-format msgid "Disengage to Power Off" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:172 +#: openpilot/selfdrive/ui/layouts/settings/device.py:164 #, python-format msgid "Disengage to Reboot" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:103 +#: openpilot/selfdrive/ui/layouts/settings/device.py:95 #, python-format msgid "Disengage to Reset Calibration" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:32 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:32 msgid "Display speed in km/h instead of mph." msgstr "" -#: selfdrive/ui/layouts/settings/device.py:59 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 #, python-format msgid "Dongle ID" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:50 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 #, python-format msgid "Download" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "Driver Camera" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:96 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:96 #, python-format msgid "Driving Personality" msgstr "" -#: system/ui/widgets/network.py:123 system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:136 #, python-format msgid "EDIT" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:138 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 msgid "ERROR" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:45 +#: openpilot/selfdrive/ui/layouts/sidebar.py:45 msgid "ETH" msgstr "" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "EXPERIMENTAL MODE ON" msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:166 -#: selfdrive/ui/layouts/settings/toggles.py:228 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:229 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:180 #, python-format msgid "Enable" msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:39 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:39 #, python-format msgid "Enable ADB" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:64 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:64 #, python-format msgid "Enable Lane Departure Warnings" msgstr "" -#: system/ui/widgets/network.py:129 +#: system/ui/widgets/network.py:126 #, python-format msgid "Enable Roaming" msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:48 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:48 #, python-format msgid "Enable SSH" msgstr "" -#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:117 #, python-format msgid "Enable Tethering" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:30 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:30 msgid "Enable driver monitoring even when openpilot is not engaged." msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:46 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:46 #, python-format msgid "Enable openpilot" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:189 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:190 #, python-format -msgid "" -"Enable the openpilot longitudinal control (alpha) toggle to allow " -"Experimental mode." +msgid "Enable the openpilot longitudinal control (alpha) toggle to allow Experimental mode." msgstr "" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "Enter APN" msgstr "" -#: system/ui/widgets/network.py:241 +#: system/ui/widgets/network.py:243 #, python-format msgid "Enter SSID" msgstr "" -#: system/ui/widgets/network.py:254 +#: system/ui/widgets/network.py:257 #, python-format msgid "Enter new tethering password" msgstr "" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:320 #, python-format msgid "Enter password" msgstr "" -#: selfdrive/ui/widgets/ssh_key.py:89 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:89 #, python-format msgid "Enter your GitHub username" msgstr "" -#: system/ui/widgets/list_view.py:123 system/ui/widgets/list_view.py:160 +#: system/ui/widgets/list_view.py:123 +#: system/ui/widgets/list_view.py:160 #, python-format msgid "Error" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:52 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:52 #, python-format msgid "Experimental Mode" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:181 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:182 #, python-format -msgid "" -"Experimental mode is currently unavailable on this car since the car's stock " -"ACC is used for longitudinal control." +msgid "Experimental mode is currently unavailable on this car since the car's stock ACC is used for longitudinal control." msgstr "" -#: system/ui/widgets/network.py:373 +#: system/ui/widgets/network.py:380 #, python-format msgid "FORGETTING..." msgstr "" -#: selfdrive/ui/widgets/setup.py:44 +#: openpilot/selfdrive/ui/widgets/setup.py:43 #, python-format msgid "Finish Setup" msgstr "" -#: selfdrive/ui/layouts/settings/settings.py:66 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:63 msgid "Firehose" msgstr "" -#: selfdrive/ui/layouts/settings/firehose.py:18 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:10 msgid "Firehose Mode" msgstr "" -#: selfdrive/ui/layouts/settings/firehose.py:25 -msgid "" -"For maximum effectiveness, bring your device inside and connect to a good " -"USB-C adapter and Wi-Fi weekly.\n" -"\n" -"Firehose Mode can also work while you're driving if connected to a hotspot " -"or unlimited SIM card.\n" -"\n" -"\n" -"Frequently Asked Questions\n" -"\n" -"Does it matter how or where I drive? Nope, just drive as you normally " -"would.\n" -"\n" -"Do all of my segments get pulled in Firehose Mode? No, we selectively pull a " -"subset of your segments.\n" -"\n" -"What's a good USB-C adapter? Any fast phone or laptop charger should be " -"fine.\n" -"\n" -"Does it matter which software I run? Yes, only upstream openpilot (and " -"particular forks) are able to be used for training." -msgstr "" - -#: system/ui/widgets/network.py:318 system/ui/widgets/network.py:451 +#: system/ui/widgets/network.py:458 +#: system/ui/widgets/network.py:326 #, python-format msgid "Forget" msgstr "" -#: system/ui/widgets/network.py:319 +#: system/ui/widgets/network.py:327 #, python-format msgid "Forget Wi-Fi Network \"{}\"?" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 msgid "GOOD" msgstr "" -#: selfdrive/ui/widgets/pairing_dialog.py:128 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:117 #, python-format msgid "Go to https://connect.comma.ai on your phone" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "HIGH" msgstr "" -#: system/ui/widgets/network.py:155 +#: system/ui/widgets/network.py:152 #, python-format msgid "Hidden Network" msgstr "" -#: selfdrive/ui/layouts/settings/firehose.py:140 -#, python-format -msgid "INACTIVE: connect to an unmetered network" -msgstr "" - -#: selfdrive/ui/layouts/settings/software.py:53 -#: selfdrive/ui/layouts/settings/software.py:136 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 +#: openpilot/selfdrive/ui/layouts/settings/software.py:146 #, python-format msgid "INSTALL" msgstr "" -#: system/ui/widgets/network.py:150 +#: system/ui/widgets/network.py:147 #, python-format msgid "IP Address" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:53 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 #, python-format msgid "Install Update" msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:56 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:56 #, python-format msgid "Joystick Debug Mode" msgstr "" -#: selfdrive/ui/widgets/ssh_key.py:29 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:29 msgid "LOADING" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:48 +#: openpilot/selfdrive/ui/layouts/sidebar.py:48 msgid "LTE" msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:64 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:64 #, python-format msgid "Longitudinal Maneuver Mode" msgstr "" -#: selfdrive/ui/onroad/hud_renderer.py:148 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:148 #, python-format msgid "MAX" msgstr "" -#: selfdrive/ui/widgets/setup.py:75 +#: openpilot/selfdrive/ui/widgets/setup.py:74 #, python-format -msgid "" -"Maximize your training data uploads to improve openpilot's driving models." +msgid "Maximize your training data uploads to improve openpilot's driving models." msgstr "" -#: selfdrive/ui/layouts/settings/device.py:59 -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "N/A" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "NO" msgstr "" -#: selfdrive/ui/layouts/settings/settings.py:63 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:60 msgid "Network" msgstr "" -#: selfdrive/ui/widgets/ssh_key.py:114 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:115 #, python-format msgid "No SSH keys found" msgstr "" -#: selfdrive/ui/widgets/ssh_key.py:126 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:127 #, python-format msgid "No SSH keys found for user '{}'" msgstr "" -#: selfdrive/ui/widgets/offroad_alerts.py:320 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:321 #, python-format msgid "No release notes available." msgstr "" -#: selfdrive/ui/layouts/sidebar.py:73 selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 msgid "OFFLINE" msgstr "" -#: system/ui/widgets/html_render.py:263 system/ui/widgets/confirm_dialog.py:93 -#: selfdrive/ui/layouts/sidebar.py:127 +#: system/ui/widgets/confirm_dialog.py:93 +#: system/ui/widgets/html_render.py:263 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 #, python-format msgid "OK" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 msgid "ONLINE" msgstr "" -#: selfdrive/ui/widgets/setup.py:20 +#: openpilot/selfdrive/ui/widgets/setup.py:19 #, python-format msgid "Open" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "PAIR" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "PANDA" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "PREVIEW" msgstr "" -#: selfdrive/ui/widgets/prime.py:44 +#: openpilot/selfdrive/ui/widgets/prime.py:44 #, python-format msgid "PRIME FEATURES:" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "Pair Device" msgstr "" -#: selfdrive/ui/widgets/setup.py:19 +#: openpilot/selfdrive/ui/widgets/setup.py:18 #, python-format msgid "Pair device" msgstr "" -#: selfdrive/ui/widgets/pairing_dialog.py:103 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:92 #, python-format msgid "Pair your device to your comma account" msgstr "" -#: selfdrive/ui/widgets/setup.py:48 selfdrive/ui/layouts/settings/device.py:24 +#: openpilot/selfdrive/ui/widgets/setup.py:47 +#: openpilot/selfdrive/ui/layouts/settings/device.py:23 #, python-format -msgid "" -"Pair your device with comma connect (connect.comma.ai) and claim your comma " -"prime offer." +msgid "Pair your device with comma connect (connect.comma.ai) and claim your comma prime offer." msgstr "" -#: selfdrive/ui/widgets/setup.py:91 +#: openpilot/selfdrive/ui/widgets/setup.py:91 #, python-format msgid "Please connect to Wi-Fi to complete initial pairing" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Power Off" msgstr "" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Prevent large data uploads when on a metered Wi-Fi connection" msgstr "" -#: system/ui/widgets/network.py:135 +#: system/ui/widgets/network.py:132 #, python-format msgid "Prevent large data uploads when on a metered cellular connection" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:25 -msgid "" -"Preview the driver facing camera to ensure that driver monitoring has good " -"visibility. (vehicle must be off)" +#: openpilot/selfdrive/ui/layouts/settings/device.py:24 +msgid "Preview the driver facing camera to ensure that driver monitoring has good visibility. (vehicle must be off)" msgstr "" -#: selfdrive/ui/widgets/pairing_dialog.py:161 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:150 #, python-format msgid "QR Code Error" msgstr "" -#: selfdrive/ui/widgets/ssh_key.py:31 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:31 msgid "REMOVE" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "RESET" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "REVIEW" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Reboot" msgstr "" -#: selfdrive/ui/onroad/alert_renderer.py:66 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:66 #, python-format msgid "Reboot Device" msgstr "" -#: selfdrive/ui/widgets/offroad_alerts.py:112 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:112 #, python-format msgid "Reboot and Update" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:27 -msgid "" -"Receive alerts to steer back into the lane when your vehicle drifts over a " -"detected lane line without a turn signal activated while driving over 31 mph " -"(50 km/h)." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:76 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:76 #, python-format msgid "Record and Upload Driver Camera" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:82 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:82 #, python-format msgid "Record and Upload Microphone Audio" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:33 -msgid "" -"Record and store microphone audio while driving. The audio will be included " -"in the dashcam video in comma connect." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:33 +msgid "Record and store microphone audio while driving. The audio will be included in the dashcam video in comma connect." msgstr "" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "Regulatory" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Relaxed" msgstr "" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote access" msgstr "" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote snapshots" msgstr "" -#: selfdrive/ui/widgets/ssh_key.py:123 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:124 #, python-format msgid "Request timed out" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Reset" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "Reset Calibration" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "Review Training Guide" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:27 +#: openpilot/selfdrive/ui/layouts/settings/device.py:26 msgid "Review the rules, features, and limitations of openpilot" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "SELECT" msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:53 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:53 #, python-format msgid "SSH Keys" msgstr "" -#: system/ui/widgets/network.py:310 +#: system/ui/widgets/network.py:316 #, python-format msgid "Scanning Wi-Fi networks..." msgstr "" -#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/option_dialog.py:37 #, python-format msgid "Select" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:183 +#: openpilot/selfdrive/ui/layouts/settings/software.py:203 #, python-format msgid "Select a branch" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:91 +#: openpilot/selfdrive/ui/layouts/settings/device.py:89 #, python-format msgid "Select a language" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "Serial" msgstr "" -#: selfdrive/ui/widgets/offroad_alerts.py:106 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:106 #, python-format msgid "Snooze Update" msgstr "" -#: selfdrive/ui/layouts/settings/settings.py:65 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:62 msgid "Software" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Standard" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:22 -msgid "" -"Standard is recommended. In aggressive mode, openpilot will follow lead cars " -"closer and be more aggressive with the gas and brake. In relaxed mode " -"openpilot will stay further away from lead cars. On supported cars, you can " -"cycle through these personalities with your steering wheel distance button." -msgstr "" - -#: selfdrive/ui/onroad/alert_renderer.py:59 -#: selfdrive/ui/onroad/alert_renderer.py:65 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:59 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:65 #, python-format msgid "System Unresponsive" msgstr "" -#: selfdrive/ui/onroad/alert_renderer.py:58 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:58 #, python-format msgid "TAKE CONTROL IMMEDIATELY" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 -#: selfdrive/ui/layouts/sidebar.py:127 selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "TEMP" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "Target Branch" msgstr "" -#: system/ui/widgets/network.py:124 +#: system/ui/widgets/network.py:121 #, python-format msgid "Tethering Password" msgstr "" -#: selfdrive/ui/layouts/settings/settings.py:64 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:61 msgid "Toggles" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:72 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:79 +#, python-format +msgid "UI Debug Mode" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "UNINSTALL" msgstr "" -#: selfdrive/ui/layouts/home.py:155 +#: openpilot/selfdrive/ui/layouts/home.py:155 #, python-format msgid "UPDATE" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:72 -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "Uninstall" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:117 +#: openpilot/selfdrive/ui/layouts/sidebar.py:117 msgid "Unknown" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:48 +#: openpilot/selfdrive/ui/layouts/settings/software.py:55 #, python-format msgid "Updates are only downloaded while the car is off." msgstr "" -#: selfdrive/ui/widgets/prime.py:33 +#: openpilot/selfdrive/ui/widgets/prime.py:33 #, python-format msgid "Upgrade Now" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:31 -msgid "" -"Upload data from the driver facing camera and help improve the driver " -"monitoring algorithm." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:31 +msgid "Upload data from the driver facing camera and help improve the driver monitoring algorithm." msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:88 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:88 #, python-format msgid "Use Metric System" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:17 -msgid "" -"Use the openpilot system for adaptive cruise control and lane keep driver " -"assistance. Your attention is required at all times to use this feature." -msgstr "" - -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 msgid "VEHICLE" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "VIEW" msgstr "" -#: selfdrive/ui/onroad/alert_renderer.py:52 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:52 #, python-format msgid "Waiting to start" msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:19 -msgid "" -"Warning: This grants SSH access to all public keys in your GitHub settings. " -"Never enter a GitHub username other than your own. A comma employee will " -"NEVER ask you to add their GitHub username." -msgstr "" - -#: selfdrive/ui/layouts/onboarding.py:111 +#: openpilot/selfdrive/ui/layouts/onboarding.py:115 #, python-format msgid "Welcome to openpilot" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:20 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:20 msgid "When enabled, pressing the accelerator pedal will disengage openpilot." msgstr "" -#: selfdrive/ui/layouts/sidebar.py:44 +#: openpilot/selfdrive/ui/layouts/sidebar.py:44 msgid "Wi-Fi" msgstr "" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Wi-Fi Network Metered" msgstr "" -#: system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:320 #, python-format msgid "Wrong password" msgstr "" -#: selfdrive/ui/layouts/onboarding.py:145 +#: openpilot/selfdrive/ui/layouts/onboarding.py:149 #, python-format msgid "You must accept the Terms and Conditions in order to use openpilot." msgstr "" -#: selfdrive/ui/layouts/onboarding.py:112 +#: openpilot/selfdrive/ui/layouts/onboarding.py:116 #, python-format -msgid "" -"You must accept the Terms and Conditions to use openpilot. Read the latest " -"terms at https://comma.ai/terms before continuing." +msgid "You must accept the Terms and Conditions to use openpilot. Read the latest terms at https://comma.ai/terms before continuing." msgstr "" -#: selfdrive/ui/onroad/driver_camera_dialog.py:34 +#: openpilot/selfdrive/ui/onroad/driver_camera_dialog.py:38 #, python-format msgid "camera starting" msgstr "" -#: selfdrive/ui/widgets/prime.py:63 +#: openpilot/selfdrive/ui/layouts/settings/software.py:19 +#, python-format +msgid "checking..." +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:63 #, python-format msgid "comma prime" msgstr "" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "default" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "down" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:106 +#: openpilot/selfdrive/ui/layouts/settings/software.py:20 +#, python-format +msgid "downloading..." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:116 #, python-format msgid "failed to check for update" msgstr "" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: openpilot/selfdrive/ui/layouts/settings/software.py:21 +#, python-format +msgid "finalizing update..." +msgstr "" + +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:321 #, python-format msgid "for \"{}\"" msgstr "" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "km/h" msgstr "" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "leave blank for automatic configuration" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "left" msgstr "" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "metered" msgstr "" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "mph" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:20 +#: openpilot/selfdrive/ui/layouts/settings/software.py:27 #, python-format msgid "never" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:31 +#: openpilot/selfdrive/ui/layouts/settings/software.py:38 #, python-format msgid "now" msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:71 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:71 #, python-format msgid "openpilot Longitudinal Control (Alpha)" msgstr "" -#: selfdrive/ui/onroad/alert_renderer.py:51 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:51 #, python-format msgid "openpilot Unavailable" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:158 -#, python-format -msgid "" -"openpilot defaults to driving in chill mode. Experimental mode enables alpha-" -"level features that aren't ready for chill mode. Experimental features are " -"listed below:

End-to-End Longitudinal Control


Let the driving " -"model control the gas and brakes. openpilot will drive as it thinks a human " -"would, including stopping for red lights and stop signs. Since the driving " -"model decides the speed to drive, the set speed will only act as an upper " -"bound. This is an alpha quality feature; mistakes should be expected." -"

New Driving Visualization


The driving visualization will " -"transition to the road-facing wide-angle camera at low speeds to better show " -"some turns. The Experimental mode logo will also be shown in the top right " -"corner." -msgstr "" - -#: selfdrive/ui/layouts/settings/device.py:165 -#, python-format -msgid "" -"openpilot is continuously calibrating, resetting is rarely required. " -"Resetting calibration will restart openpilot if the car is powered on." -msgstr "" - -#: selfdrive/ui/layouts/settings/firehose.py:20 -msgid "" -"openpilot learns to drive by watching humans, like you, drive.\n" -"\n" -"Firehose Mode allows you to maximize your training data uploads to improve " -"openpilot's driving models. More data means bigger models, which means " -"better Experimental Mode." -msgstr "" - -#: selfdrive/ui/layouts/settings/toggles.py:183 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:184 #, python-format msgid "openpilot longitudinal control may come in a future update." msgstr "" -#: selfdrive/ui/layouts/settings/device.py:26 -msgid "" -"openpilot requires the device to be mounted within 4° left or right and " -"within 5° up or 9° down." +#: openpilot/selfdrive/ui/layouts/settings/device.py:25 +msgid "openpilot requires the device to be mounted within 4° left or right and within 5° up or 9° down." msgstr "" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "right" msgstr "" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "unmetered" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "up" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:127 #, python-format msgid "up to date, last checked never" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:115 +#: openpilot/selfdrive/ui/layouts/settings/software.py:125 #, python-format msgid "up to date, last checked {}" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:109 +#: openpilot/selfdrive/ui/layouts/settings/software.py:119 #, python-format msgid "update available" msgstr "" -#: selfdrive/ui/layouts/home.py:169 +#: openpilot/selfdrive/ui/layouts/home.py:169 #, python-format msgid "{} ALERT" msgid_plural "{} ALERTS" msgstr[0] "" msgstr[1] "" -#: selfdrive/ui/layouts/settings/software.py:40 +#: openpilot/selfdrive/ui/layouts/settings/software.py:47 #, python-format msgid "{} day ago" msgid_plural "{} days ago" msgstr[0] "" msgstr[1] "" -#: selfdrive/ui/layouts/settings/software.py:37 +#: openpilot/selfdrive/ui/layouts/settings/software.py:44 #, python-format msgid "{} hour ago" msgid_plural "{} hours ago" msgstr[0] "" msgstr[1] "" -#: selfdrive/ui/layouts/settings/software.py:34 +#: openpilot/selfdrive/ui/layouts/settings/software.py:41 #, python-format msgid "{} minute ago" msgid_plural "{} minutes ago" msgstr[0] "" msgstr[1] "" -#: selfdrive/ui/layouts/settings/firehose.py:111 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:70 #, python-format msgid "{} segment of your driving is in the training dataset so far." msgid_plural "{} segments of your driving is in the training dataset so far." msgstr[0] "" msgstr[1] "" -#: selfdrive/ui/widgets/prime.py:62 +#: openpilot/selfdrive/ui/widgets/prime.py:62 #, python-format msgid "✓ SUBSCRIBED" msgstr "" -#: selfdrive/ui/widgets/setup.py:22 +#: openpilot/selfdrive/ui/widgets/setup.py:21 #, python-format msgid "🔥 Firehose Mode 🔥" msgstr "" + diff --git a/selfdrive/ui/translations/app_tr.po b/selfdrive/ui/translations/app_tr.po index 10191234a1..137d350c2a 100644 --- a/selfdrive/ui/translations/app_tr.po +++ b/selfdrive/ui/translations/app_tr.po @@ -17,1194 +17,1018 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1);\n" -#: selfdrive/ui/layouts/settings/device.py:160 +#: openpilot/selfdrive/ui/layouts/settings/device.py:152 #, python-format msgid " Steering torque response calibration is complete." msgstr " Direksiyon tork tepkisi kalibrasyonu tamamlandı." -#: selfdrive/ui/layouts/settings/device.py:158 +#: openpilot/selfdrive/ui/layouts/settings/device.py:150 #, python-format msgid " Steering torque response calibration is {}% complete." msgstr " Direksiyon tork tepkisi kalibrasyonu {}% tamamlandı." -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid " Your device is pointed {:.1f}° {} and {:.1f}° {}." msgstr " Cihazınız {:.1f}° {} ve {:.1f}° {} yönünde konumlandırılmış." -#: selfdrive/ui/layouts/sidebar.py:43 +#: openpilot/selfdrive/ui/layouts/sidebar.py:43 msgid "--" msgstr "--" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "1 year of drive storage" msgstr "1 yıl sürüş depolaması" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "24/7 LTE connectivity" msgstr "7/24 LTE bağlantısı" -#: selfdrive/ui/layouts/sidebar.py:46 +#: openpilot/selfdrive/ui/layouts/sidebar.py:46 msgid "2G" msgstr "2G" -#: selfdrive/ui/layouts/sidebar.py:47 +#: openpilot/selfdrive/ui/layouts/sidebar.py:47 msgid "3G" msgstr "3G" -#: selfdrive/ui/layouts/sidebar.py:49 +#: openpilot/selfdrive/ui/layouts/sidebar.py:49 msgid "5G" msgstr "5G" -#: selfdrive/ui/layouts/settings/developer.py:23 -msgid "" -"WARNING: openpilot longitudinal control is in alpha for this car and will " -"disable Automatic Emergency Braking (AEB).

On this car, openpilot " -"defaults to the car's built-in ACC instead of openpilot's longitudinal " -"control. Enable this to switch to openpilot longitudinal control. Enabling " -"Experimental mode is recommended when enabling openpilot longitudinal " -"control alpha. Changing this setting will restart openpilot if the car is " -"powered on." -msgstr "" -"UYARI: Bu araç için openpilot boylamsal kontrolü alfa aşamasındadır ve " -"Otomatik Acil Frenlemeyi (AEB) devre dışı bırakacaktır.

Bu araçta " -"openpilot, openpilot'un boylamsal kontrolü yerine aracın yerleşik ACC'sini " -"varsayılan olarak kullanır. openpilot boylamsal kontrolüne geçmek için bunu " -"etkinleştirin. openpilot boylamsal kontrol alfayı etkinleştirirken Deneysel " -"modu etkinleştirmeniz önerilir." - -#: selfdrive/ui/layouts/settings/device.py:148 +#: openpilot/selfdrive/ui/layouts/settings/device.py:140 #, python-format msgid "

Steering lag calibration is complete." msgstr "" -#: selfdrive/ui/layouts/settings/device.py:146 +#: openpilot/selfdrive/ui/layouts/settings/device.py:138 #, python-format msgid "

Steering lag calibration is {}% complete." msgstr "" -#: selfdrive/ui/layouts/settings/firehose.py:138 -#, python-format -msgid "ACTIVE" -msgstr "AKTİF" - -#: selfdrive/ui/layouts/settings/developer.py:15 -msgid "" -"ADB (Android Debug Bridge) allows connecting to your device over USB or over " -"the network. See https://docs.comma.ai/how-to/connect-to-comma for more info." -msgstr "" -"ADB (Android Debug Bridge), cihazınıza USB veya ağ üzerinden bağlanmayı " -"sağlar. Daha fazla bilgi için https://docs.comma.ai/how-to/connect-to-comma " -"adresine bakın." - -#: selfdrive/ui/widgets/ssh_key.py:30 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:30 msgid "ADD" msgstr "EKLE" -#: system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:136 #, python-format msgid "APN Setting" msgstr "" -#: selfdrive/ui/widgets/offroad_alerts.py:109 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:109 #, python-format msgid "Acknowledge Excessive Actuation" msgstr "Aşırı Müdahaleyi Onayla" -#: system/ui/widgets/network.py:74 system/ui/widgets/network.py:95 +#: system/ui/widgets/network.py:92 +#: system/ui/widgets/network.py:74 #, python-format msgid "Advanced" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Aggressive" msgstr "Agresif" -#: selfdrive/ui/layouts/onboarding.py:116 +#: openpilot/selfdrive/ui/layouts/onboarding.py:120 #, python-format msgid "Agree" msgstr "Kabul et" -#: selfdrive/ui/layouts/settings/toggles.py:70 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:70 #, python-format msgid "Always-On Driver Monitoring" msgstr "Sürekli Sürücü İzleme" -#: selfdrive/ui/layouts/settings/toggles.py:186 -#, python-format -msgid "" -"An alpha version of openpilot longitudinal control can be tested, along with " -"Experimental mode, on non-release branches." -msgstr "" -"openpilot boylamsal kontrolünün alfa sürümü, Deneysel mod ile birlikte, " -"yayın dışı dallarda test edilebilir." - -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 #, python-format msgid "Are you sure you want to power off?" msgstr "Kapatmak istediğinizden emin misiniz?" -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 #, python-format msgid "Are you sure you want to reboot?" msgstr "Yeniden başlatmak istediğinizden emin misiniz?" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Are you sure you want to reset calibration?" msgstr "Kalibrasyonu sıfırlamak istediğinizden emin misiniz?" -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 #, python-format msgid "Are you sure you want to uninstall?" msgstr "Kaldırmak istediğinizden emin misiniz?" -#: system/ui/widgets/network.py:99 selfdrive/ui/layouts/onboarding.py:147 +#: system/ui/widgets/network.py:96 +#: openpilot/selfdrive/ui/layouts/onboarding.py:151 #, python-format msgid "Back" msgstr "Geri" -#: selfdrive/ui/widgets/prime.py:38 +#: openpilot/selfdrive/ui/widgets/prime.py:38 #, python-format msgid "Become a comma prime member at connect.comma.ai" msgstr "connect.comma.ai adresinde comma prime üyesi olun" -#: selfdrive/ui/widgets/pairing_dialog.py:130 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:119 #, python-format msgid "Bookmark connect.comma.ai to your home screen to use it like an app" -msgstr "" -"connect.comma.ai'yi ana ekranınıza ekleyerek bir uygulama gibi kullanın" +msgstr "connect.comma.ai'yi ana ekranınıza ekleyerek bir uygulama gibi kullanın" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "CHANGE" msgstr "DEĞİŞTİR" -#: selfdrive/ui/layouts/settings/software.py:50 -#: selfdrive/ui/layouts/settings/software.py:107 -#: selfdrive/ui/layouts/settings/software.py:118 -#: selfdrive/ui/layouts/settings/software.py:147 +#: openpilot/selfdrive/ui/layouts/settings/software.py:157 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 +#: openpilot/selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:128 #, python-format msgid "CHECK" msgstr "KONTROL ET" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "CHILL MODE ON" msgstr "CHILL MODU AÇIK" -#: system/ui/widgets/network.py:155 selfdrive/ui/layouts/sidebar.py:73 -#: selfdrive/ui/layouts/sidebar.py:134 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:138 +#: system/ui/widgets/network.py:152 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 #, python-format msgid "CONNECT" msgstr "BAĞLAN" -#: system/ui/widgets/network.py:369 +#: system/ui/widgets/network.py:376 #, python-format msgid "CONNECTING..." msgstr "BAĞLAN" -#: system/ui/widgets/confirm_dialog.py:23 system/ui/widgets/option_dialog.py:35 -#: system/ui/widgets/keyboard.py:81 system/ui/widgets/network.py:318 +#: system/ui/widgets/network.py:326 +#: system/ui/widgets/confirm_dialog.py:24 +#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/keyboard.py:83 #, python-format msgid "Cancel" msgstr "" -#: system/ui/widgets/network.py:134 +#: system/ui/widgets/network.py:131 #, python-format msgid "Cellular Metered" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "Change Language" msgstr "Dili Değiştir" -#: selfdrive/ui/layouts/settings/toggles.py:125 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:125 #, python-format msgid "Changing this setting will restart openpilot if the car is powered on." -msgstr "" -" Bu ayarı değiştirmek, araç çalışıyorsa openpilot'u yeniden başlatacaktır." +msgstr " Bu ayarı değiştirmek, araç çalışıyorsa openpilot'u yeniden başlatacaktır." -#: selfdrive/ui/widgets/pairing_dialog.py:129 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:118 #, python-format msgid "Click \"add new device\" and scan the QR code on the right" msgstr "\"yeni cihaz ekle\"ye tıklayın ve sağdaki QR kodunu tarayın" -#: selfdrive/ui/widgets/offroad_alerts.py:104 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:104 #, python-format msgid "Close" msgstr "Kapat" -#: selfdrive/ui/layouts/settings/software.py:49 +#: openpilot/selfdrive/ui/layouts/settings/software.py:56 #, python-format msgid "Current Version" msgstr "Geçerli Sürüm" -#: selfdrive/ui/layouts/settings/software.py:110 +#: openpilot/selfdrive/ui/layouts/settings/software.py:120 #, python-format msgid "DOWNLOAD" msgstr "İNDİR" -#: selfdrive/ui/layouts/onboarding.py:115 +#: openpilot/selfdrive/ui/layouts/onboarding.py:119 #, python-format msgid "Decline" msgstr "Reddet" -#: selfdrive/ui/layouts/onboarding.py:148 +#: openpilot/selfdrive/ui/layouts/onboarding.py:152 #, python-format msgid "Decline, uninstall openpilot" msgstr "Reddet, openpilot'u kaldır" -#: selfdrive/ui/layouts/settings/settings.py:67 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:64 msgid "Developer" msgstr "Geliştirici" -#: selfdrive/ui/layouts/settings/settings.py:62 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:59 msgid "Device" msgstr "Cihaz" -#: selfdrive/ui/layouts/settings/toggles.py:58 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:58 #, python-format msgid "Disengage on Accelerator Pedal" msgstr "Gaz Pedalında Devreden Çık" -#: selfdrive/ui/layouts/settings/device.py:184 +#: openpilot/selfdrive/ui/layouts/settings/device.py:176 #, python-format msgid "Disengage to Power Off" msgstr "Kapatmak için Devreden Çıkın" -#: selfdrive/ui/layouts/settings/device.py:172 +#: openpilot/selfdrive/ui/layouts/settings/device.py:164 #, python-format msgid "Disengage to Reboot" msgstr "Yeniden Başlatmak için Devreden Çıkın" -#: selfdrive/ui/layouts/settings/device.py:103 +#: openpilot/selfdrive/ui/layouts/settings/device.py:95 #, python-format msgid "Disengage to Reset Calibration" msgstr "Kalibrasyonu Sıfırlamak için Devreden Çıkın" -#: selfdrive/ui/layouts/settings/toggles.py:32 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:32 msgid "Display speed in km/h instead of mph." msgstr "Hızı mph yerine km/h olarak göster." -#: selfdrive/ui/layouts/settings/device.py:59 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 #, python-format msgid "Dongle ID" msgstr "Dongle ID" -#: selfdrive/ui/layouts/settings/software.py:50 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 #, python-format msgid "Download" msgstr "İndir" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "Driver Camera" msgstr "Sürücü Kamerası" -#: selfdrive/ui/layouts/settings/toggles.py:96 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:96 #, python-format msgid "Driving Personality" msgstr "Sürüş Kişiliği" -#: system/ui/widgets/network.py:123 system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:136 #, python-format msgid "EDIT" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:138 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 msgid "ERROR" msgstr "HATA" -#: selfdrive/ui/layouts/sidebar.py:45 +#: openpilot/selfdrive/ui/layouts/sidebar.py:45 msgid "ETH" msgstr "ETH" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "EXPERIMENTAL MODE ON" msgstr "DENEYSEL MOD AÇIK" -#: selfdrive/ui/layouts/settings/developer.py:166 -#: selfdrive/ui/layouts/settings/toggles.py:228 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:229 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:180 #, python-format msgid "Enable" msgstr "Etkinleştir" -#: selfdrive/ui/layouts/settings/developer.py:39 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:39 #, python-format msgid "Enable ADB" msgstr "ADB'yi Etkinleştir" -#: selfdrive/ui/layouts/settings/toggles.py:64 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:64 #, python-format msgid "Enable Lane Departure Warnings" msgstr "Şerit Terk Uyarılarını Etkinleştir" -#: system/ui/widgets/network.py:129 +#: system/ui/widgets/network.py:126 #, python-format msgid "Enable Roaming" msgstr "openpilot'u etkinleştir" -#: selfdrive/ui/layouts/settings/developer.py:48 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:48 #, python-format msgid "Enable SSH" msgstr "SSH'yi Etkinleştir" -#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:117 #, python-format msgid "Enable Tethering" msgstr "Şerit Terk Uyarılarını Etkinleştir" -#: selfdrive/ui/layouts/settings/toggles.py:30 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:30 msgid "Enable driver monitoring even when openpilot is not engaged." msgstr "openpilot devrede değilken bile sürücü izlemesini etkinleştir." -#: selfdrive/ui/layouts/settings/toggles.py:46 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:46 #, python-format msgid "Enable openpilot" msgstr "openpilot'u etkinleştir" -#: selfdrive/ui/layouts/settings/toggles.py:189 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:190 #, python-format -msgid "" -"Enable the openpilot longitudinal control (alpha) toggle to allow " -"Experimental mode." -msgstr "" -"Deneysel modu etkinleştirmek için openpilot boylamsal kontrolünü (alfa) açın." +msgid "Enable the openpilot longitudinal control (alpha) toggle to allow Experimental mode." +msgstr "Deneysel modu etkinleştirmek için openpilot boylamsal kontrolünü (alfa) açın." -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "Enter APN" msgstr "" -#: system/ui/widgets/network.py:241 +#: system/ui/widgets/network.py:243 #, python-format msgid "Enter SSID" msgstr "" -#: system/ui/widgets/network.py:254 +#: system/ui/widgets/network.py:257 #, python-format msgid "Enter new tethering password" msgstr "" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:320 #, python-format msgid "Enter password" msgstr "" -#: selfdrive/ui/widgets/ssh_key.py:89 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:89 #, python-format msgid "Enter your GitHub username" msgstr "GitHub kullanıcı adınızı girin" -#: system/ui/widgets/list_view.py:123 system/ui/widgets/list_view.py:160 +#: system/ui/widgets/list_view.py:123 +#: system/ui/widgets/list_view.py:160 #, python-format msgid "Error" msgstr "" -#: selfdrive/ui/layouts/settings/toggles.py:52 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:52 #, python-format msgid "Experimental Mode" msgstr "Deneysel Mod" -#: selfdrive/ui/layouts/settings/toggles.py:181 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:182 #, python-format -msgid "" -"Experimental mode is currently unavailable on this car since the car's stock " -"ACC is used for longitudinal control." -msgstr "" -"Bu araçta boylamsal kontrol için stok ACC kullanıldığından şu anda Deneysel " -"mod kullanılamıyor." +msgid "Experimental mode is currently unavailable on this car since the car's stock ACC is used for longitudinal control." +msgstr "Bu araçta boylamsal kontrol için stok ACC kullanıldığından şu anda Deneysel mod kullanılamıyor." -#: system/ui/widgets/network.py:373 +#: system/ui/widgets/network.py:380 #, python-format msgid "FORGETTING..." msgstr "" -#: selfdrive/ui/widgets/setup.py:44 +#: openpilot/selfdrive/ui/widgets/setup.py:43 #, python-format msgid "Finish Setup" msgstr "Kurulumu Bitir" -#: selfdrive/ui/layouts/settings/settings.py:66 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:63 msgid "Firehose" msgstr "Firehose" -#: selfdrive/ui/layouts/settings/firehose.py:18 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:10 msgid "Firehose Mode" msgstr "Firehose Modu" -#: selfdrive/ui/layouts/settings/firehose.py:25 -msgid "" -"For maximum effectiveness, bring your device inside and connect to a good " -"USB-C adapter and Wi-Fi weekly.\n" -"\n" -"Firehose Mode can also work while you're driving if connected to a hotspot " -"or unlimited SIM card.\n" -"\n" -"\n" -"Frequently Asked Questions\n" -"\n" -"Does it matter how or where I drive? Nope, just drive as you normally " -"would.\n" -"\n" -"Do all of my segments get pulled in Firehose Mode? No, we selectively pull a " -"subset of your segments.\n" -"\n" -"What's a good USB-C adapter? Any fast phone or laptop charger should be " -"fine.\n" -"\n" -"Does it matter which software I run? Yes, only upstream openpilot (and " -"particular forks) are able to be used for training." -msgstr "" -"Maksimum verim için cihazınızı içeri alın ve haftalık olarak iyi bir USB-C " -"adaptörüne ve Wi‑Fi'a bağlayın.\n" -"\n" -"Firehose Modu, bir hotspot'a veya sınırsız SIM karta bağlıyken sürüş " -"sırasında da çalışabilir.\n" -"\n" -"\n" -"Sıkça Sorulan Sorular\n" -"\n" -"Nasıl veya nerede sürdüğüm önemli mi? Hayır, normalde nasıl sürüyorsanız " -"öyle sürün.\n" -"\n" -"Firehose Modu'nda tüm segmentlerim çekiliyor mu? Hayır, segmentlerinizin bir " -"alt kümesini seçerek çekiyoruz.\n" -"\n" -"İyi bir USB‑C adaptörü nedir? Hızlı bir telefon veya dizüstü şarj cihazı " -"uygundur.\n" -"\n" -"Hangi yazılımı çalıştırdığım önemli mi? Evet, yalnızca upstream openpilot " -"(ve bazı fork'lar) eğitim için kullanılabilir." - -#: system/ui/widgets/network.py:318 system/ui/widgets/network.py:451 +#: system/ui/widgets/network.py:458 +#: system/ui/widgets/network.py:326 #, python-format msgid "Forget" msgstr "" -#: system/ui/widgets/network.py:319 +#: system/ui/widgets/network.py:327 #, python-format msgid "Forget Wi-Fi Network \"{}\"?" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 msgid "GOOD" msgstr "İYİ" -#: selfdrive/ui/widgets/pairing_dialog.py:128 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:117 #, python-format msgid "Go to https://connect.comma.ai on your phone" msgstr "Telefonunuzda https://connect.comma.ai adresine gidin" -#: selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "HIGH" msgstr "YÜKSEK" -#: system/ui/widgets/network.py:155 +#: system/ui/widgets/network.py:152 #, python-format msgid "Hidden Network" msgstr "Ağ" -#: selfdrive/ui/layouts/settings/firehose.py:140 -#, python-format -msgid "INACTIVE: connect to an unmetered network" -msgstr "PASİF: sınırsız bir ağa bağlanın" - -#: selfdrive/ui/layouts/settings/software.py:53 -#: selfdrive/ui/layouts/settings/software.py:136 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 +#: openpilot/selfdrive/ui/layouts/settings/software.py:146 #, python-format msgid "INSTALL" msgstr "YÜKLE" -#: system/ui/widgets/network.py:150 +#: system/ui/widgets/network.py:147 #, python-format msgid "IP Address" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:53 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 #, python-format msgid "Install Update" msgstr "Güncellemeyi Yükle" -#: selfdrive/ui/layouts/settings/developer.py:56 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:56 #, python-format msgid "Joystick Debug Mode" msgstr "Joystick Hata Ayıklama Modu" -#: selfdrive/ui/widgets/ssh_key.py:29 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:29 msgid "LOADING" msgstr "YÜKLENİYOR" -#: selfdrive/ui/layouts/sidebar.py:48 +#: openpilot/selfdrive/ui/layouts/sidebar.py:48 msgid "LTE" msgstr "LTE" -#: selfdrive/ui/layouts/settings/developer.py:64 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:64 #, python-format msgid "Longitudinal Maneuver Mode" msgstr "Boylamsal Manevra Modu" -#: selfdrive/ui/onroad/hud_renderer.py:148 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:148 #, python-format msgid "MAX" msgstr "MAKS" -#: selfdrive/ui/widgets/setup.py:75 +#: openpilot/selfdrive/ui/widgets/setup.py:74 #, python-format -msgid "" -"Maximize your training data uploads to improve openpilot's driving models." -msgstr "" -"openpilot'un sürüş modellerini iyileştirmek için eğitim veri yüklemelerinizi " -"en üst düzeye çıkarın." +msgid "Maximize your training data uploads to improve openpilot's driving models." +msgstr "openpilot'un sürüş modellerini iyileştirmek için eğitim veri yüklemelerinizi en üst düzeye çıkarın." -#: selfdrive/ui/layouts/settings/device.py:59 -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "N/A" msgstr "" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "NO" msgstr "HAYIR" -#: selfdrive/ui/layouts/settings/settings.py:63 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:60 msgid "Network" msgstr "Ağ" -#: selfdrive/ui/widgets/ssh_key.py:114 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:115 #, python-format msgid "No SSH keys found" msgstr "SSH anahtarı bulunamadı" -#: selfdrive/ui/widgets/ssh_key.py:126 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:127 #, python-format msgid "No SSH keys found for user '{}'" msgstr "'{username}' için SSH anahtarı bulunamadı" -#: selfdrive/ui/widgets/offroad_alerts.py:320 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:321 #, python-format msgid "No release notes available." msgstr "Sürüm notu mevcut değil." -#: selfdrive/ui/layouts/sidebar.py:73 selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 msgid "OFFLINE" msgstr "ÇEVRİMDIŞI" -#: system/ui/widgets/html_render.py:263 system/ui/widgets/confirm_dialog.py:93 -#: selfdrive/ui/layouts/sidebar.py:127 +#: system/ui/widgets/confirm_dialog.py:93 +#: system/ui/widgets/html_render.py:263 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 #, python-format msgid "OK" msgstr "OK" -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 msgid "ONLINE" msgstr "ÇEVRİMİÇİ" -#: selfdrive/ui/widgets/setup.py:20 +#: openpilot/selfdrive/ui/widgets/setup.py:19 #, python-format msgid "Open" msgstr "Aç" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "PAIR" msgstr "EŞLE" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "PANDA" msgstr "PANDA" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "PREVIEW" msgstr "ÖNİZLEME" -#: selfdrive/ui/widgets/prime.py:44 +#: openpilot/selfdrive/ui/widgets/prime.py:44 #, python-format msgid "PRIME FEATURES:" msgstr "PRIME ÖZELLİKLERİ:" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "Pair Device" msgstr "Cihazı Eşle" -#: selfdrive/ui/widgets/setup.py:19 +#: openpilot/selfdrive/ui/widgets/setup.py:18 #, python-format msgid "Pair device" msgstr "Cihazı eşle" -#: selfdrive/ui/widgets/pairing_dialog.py:103 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:92 #, python-format msgid "Pair your device to your comma account" msgstr "Cihazınızı comma hesabınızla eşleştirin" -#: selfdrive/ui/widgets/setup.py:48 selfdrive/ui/layouts/settings/device.py:24 +#: openpilot/selfdrive/ui/widgets/setup.py:47 +#: openpilot/selfdrive/ui/layouts/settings/device.py:23 #, python-format -msgid "" -"Pair your device with comma connect (connect.comma.ai) and claim your comma " -"prime offer." -msgstr "" -"Cihazınızı comma connect (connect.comma.ai) ile eşleştirin ve comma prime " -"teklifinizi alın." +msgid "Pair your device with comma connect (connect.comma.ai) and claim your comma prime offer." +msgstr "Cihazınızı comma connect (connect.comma.ai) ile eşleştirin ve comma prime teklifinizi alın." -#: selfdrive/ui/widgets/setup.py:91 +#: openpilot/selfdrive/ui/widgets/setup.py:91 #, python-format msgid "Please connect to Wi-Fi to complete initial pairing" msgstr "İlk eşleştirmeyi tamamlamak için lütfen Wi‑Fi'a bağlanın" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Power Off" msgstr "Kapat" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Prevent large data uploads when on a metered Wi-Fi connection" msgstr "" -#: system/ui/widgets/network.py:135 +#: system/ui/widgets/network.py:132 #, python-format msgid "Prevent large data uploads when on a metered cellular connection" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:25 -msgid "" -"Preview the driver facing camera to ensure that driver monitoring has good " -"visibility. (vehicle must be off)" -msgstr "" -"Sürücü izleme görünürlüğünün iyi olduğundan emin olmak için sürücüye bakan " -"kamerayı önizleyin. (araç kapalı olmalıdır)" +#: openpilot/selfdrive/ui/layouts/settings/device.py:24 +msgid "Preview the driver facing camera to ensure that driver monitoring has good visibility. (vehicle must be off)" +msgstr "Sürücü izleme görünürlüğünün iyi olduğundan emin olmak için sürücüye bakan kamerayı önizleyin. (araç kapalı olmalıdır)" -#: selfdrive/ui/widgets/pairing_dialog.py:161 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:150 #, python-format msgid "QR Code Error" msgstr "QR Kod Hatası" -#: selfdrive/ui/widgets/ssh_key.py:31 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:31 msgid "REMOVE" msgstr "KALDIR" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "RESET" msgstr "SIFIRLA" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "REVIEW" msgstr "GÖZDEN GEÇİR" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Reboot" msgstr "Yeniden Başlat" -#: selfdrive/ui/onroad/alert_renderer.py:66 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:66 #, python-format msgid "Reboot Device" msgstr "Cihazı Yeniden Başlat" -#: selfdrive/ui/widgets/offroad_alerts.py:112 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:112 #, python-format msgid "Reboot and Update" msgstr "Yeniden Başlat ve Güncelle" -#: selfdrive/ui/layouts/settings/toggles.py:27 -msgid "" -"Receive alerts to steer back into the lane when your vehicle drifts over a " -"detected lane line without a turn signal activated while driving over 31 mph " -"(50 km/h)." -msgstr "" -"Araç 31 mph (50 km/h) üzerindeyken sinyal verilmeden algılanan şerit " -"çizgisini aştığınızda şeride geri dönmeniz için uyarılar alın." - -#: selfdrive/ui/layouts/settings/toggles.py:76 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:76 #, python-format msgid "Record and Upload Driver Camera" msgstr "Sürücü Kamerasını Kaydet ve Yükle" -#: selfdrive/ui/layouts/settings/toggles.py:82 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:82 #, python-format msgid "Record and Upload Microphone Audio" msgstr "Mikrofon Sesini Kaydet ve Yükle" -#: selfdrive/ui/layouts/settings/toggles.py:33 -msgid "" -"Record and store microphone audio while driving. The audio will be included " -"in the dashcam video in comma connect." -msgstr "" -"Sürüş sırasında mikrofon sesini kaydedip saklayın. Ses, comma connect'teki " -"ön kamera videosuna dahil edilecektir." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:33 +msgid "Record and store microphone audio while driving. The audio will be included in the dashcam video in comma connect." +msgstr "Sürüş sırasında mikrofon sesini kaydedip saklayın. Ses, comma connect'teki ön kamera videosuna dahil edilecektir." -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "Regulatory" msgstr "Mevzuat" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Relaxed" msgstr "Rahat" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote access" msgstr "Uzaktan erişim" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote snapshots" msgstr "Uzaktan anlık görüntüler" -#: selfdrive/ui/widgets/ssh_key.py:123 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:124 #, python-format msgid "Request timed out" msgstr "İstek zaman aşımına uğradı" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Reset" msgstr "Sıfırla" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "Reset Calibration" msgstr "Kalibrasyonu Sıfırla" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "Review Training Guide" msgstr "Eğitim Kılavuzunu İncele" -#: selfdrive/ui/layouts/settings/device.py:27 +#: openpilot/selfdrive/ui/layouts/settings/device.py:26 msgid "Review the rules, features, and limitations of openpilot" -msgstr "" -"openpilot'un kurallarını, özelliklerini ve sınırlamalarını gözden geçirin" +msgstr "openpilot'un kurallarını, özelliklerini ve sınırlamalarını gözden geçirin" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "SELECT" msgstr "" -#: selfdrive/ui/layouts/settings/developer.py:53 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:53 #, python-format msgid "SSH Keys" msgstr "" -#: system/ui/widgets/network.py:310 +#: system/ui/widgets/network.py:316 #, python-format msgid "Scanning Wi-Fi networks..." msgstr "" -#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/option_dialog.py:37 #, python-format msgid "Select" msgstr "" -#: selfdrive/ui/layouts/settings/software.py:183 +#: openpilot/selfdrive/ui/layouts/settings/software.py:203 #, python-format msgid "Select a branch" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:91 +#: openpilot/selfdrive/ui/layouts/settings/device.py:89 #, python-format msgid "Select a language" msgstr "Bir dil seçin" -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "Serial" msgstr "Seri" -#: selfdrive/ui/widgets/offroad_alerts.py:106 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:106 #, python-format msgid "Snooze Update" msgstr "Güncellemeyi Ertele" -#: selfdrive/ui/layouts/settings/settings.py:65 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:62 msgid "Software" msgstr "Yazılım" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Standard" msgstr "Standart" -#: selfdrive/ui/layouts/settings/toggles.py:22 -msgid "" -"Standard is recommended. In aggressive mode, openpilot will follow lead cars " -"closer and be more aggressive with the gas and brake. In relaxed mode " -"openpilot will stay further away from lead cars. On supported cars, you can " -"cycle through these personalities with your steering wheel distance button." -msgstr "" -"Standart önerilir. Agresif modda openpilot öndeki aracı daha yakından takip " -"eder ve gaz/fren kullanımında daha ataktır. Rahat modda openpilot öndeki " -"araçlardan daha uzak durur. Desteklenen araçlarda bu kişilikler arasında " -"direksiyon mesafe düğmesiyle geçiş yapabilirsiniz." - -#: selfdrive/ui/onroad/alert_renderer.py:59 -#: selfdrive/ui/onroad/alert_renderer.py:65 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:59 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:65 #, python-format msgid "System Unresponsive" msgstr "Sistem Yanıt Vermiyor" -#: selfdrive/ui/onroad/alert_renderer.py:58 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:58 #, python-format msgid "TAKE CONTROL IMMEDIATELY" msgstr "HEMEN KONTROLÜ DEVRALIN" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 -#: selfdrive/ui/layouts/sidebar.py:127 selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "TEMP" msgstr "TEMP" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "Target Branch" msgstr "" -#: system/ui/widgets/network.py:124 +#: system/ui/widgets/network.py:121 #, python-format msgid "Tethering Password" msgstr "" -#: selfdrive/ui/layouts/settings/settings.py:64 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:61 msgid "Toggles" msgstr "Seçenekler" -#: selfdrive/ui/layouts/settings/software.py:72 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:79 +#, python-format +msgid "UI Debug Mode" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "UNINSTALL" msgstr "KALDIR" -#: selfdrive/ui/layouts/home.py:155 +#: openpilot/selfdrive/ui/layouts/home.py:155 #, python-format msgid "UPDATE" msgstr "GÜNCELLE" -#: selfdrive/ui/layouts/settings/software.py:72 -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "Uninstall" msgstr "Kaldır" -#: selfdrive/ui/layouts/sidebar.py:117 +#: openpilot/selfdrive/ui/layouts/sidebar.py:117 msgid "Unknown" msgstr "Bilinmiyor" -#: selfdrive/ui/layouts/settings/software.py:48 +#: openpilot/selfdrive/ui/layouts/settings/software.py:55 #, python-format msgid "Updates are only downloaded while the car is off." msgstr "Güncellemeler yalnızca araç kapalıyken indirilir." -#: selfdrive/ui/widgets/prime.py:33 +#: openpilot/selfdrive/ui/widgets/prime.py:33 #, python-format msgid "Upgrade Now" msgstr "Şimdi Yükselt" -#: selfdrive/ui/layouts/settings/toggles.py:31 -msgid "" -"Upload data from the driver facing camera and help improve the driver " -"monitoring algorithm." -msgstr "" -"Sürücüye bakan kameradan veri yükleyin ve sürücü izleme algoritmasını " -"geliştirmeye yardımcı olun." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:31 +msgid "Upload data from the driver facing camera and help improve the driver monitoring algorithm." +msgstr "Sürücüye bakan kameradan veri yükleyin ve sürücü izleme algoritmasını geliştirmeye yardımcı olun." -#: selfdrive/ui/layouts/settings/toggles.py:88 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:88 #, python-format msgid "Use Metric System" msgstr "Metrik Sistemi Kullan" -#: selfdrive/ui/layouts/settings/toggles.py:17 -msgid "" -"Use the openpilot system for adaptive cruise control and lane keep driver " -"assistance. Your attention is required at all times to use this feature." -msgstr "" -"Uyarlanabilir hız sabitleyici ve şerit koruma sürücü yardımında openpilot " -"sistemini kullanın. Bu özelliği kullanırken her zaman dikkatli olmanız " -"gerekir." - -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 msgid "VEHICLE" msgstr "ARAÇ" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "VIEW" msgstr "GÖRÜNTÜLE" -#: selfdrive/ui/onroad/alert_renderer.py:52 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:52 #, python-format msgid "Waiting to start" msgstr "Başlatma bekleniyor" -#: selfdrive/ui/layouts/settings/developer.py:19 -msgid "" -"Warning: This grants SSH access to all public keys in your GitHub settings. " -"Never enter a GitHub username other than your own. A comma employee will " -"NEVER ask you to add their GitHub username." -msgstr "" -"Uyarı: Bu, GitHub ayarlarınızdaki tüm açık anahtarlara SSH erişimi verir. " -"Kendi adınız dışında asla bir GitHub kullanıcı adı girmeyin. Bir comma " -"çalışanı sizden asla GitHub kullanıcı adlarını eklemenizi İSTEMEZ." - -#: selfdrive/ui/layouts/onboarding.py:111 +#: openpilot/selfdrive/ui/layouts/onboarding.py:115 #, python-format msgid "Welcome to openpilot" msgstr "openpilot'a hoş geldiniz" -#: selfdrive/ui/layouts/settings/toggles.py:20 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:20 msgid "When enabled, pressing the accelerator pedal will disengage openpilot." -msgstr "" -"Etkinleştirildiğinde, gaz pedalına basmak openpilot'u devreden çıkarır." +msgstr "Etkinleştirildiğinde, gaz pedalına basmak openpilot'u devreden çıkarır." -#: selfdrive/ui/layouts/sidebar.py:44 +#: openpilot/selfdrive/ui/layouts/sidebar.py:44 msgid "Wi-Fi" msgstr "Wi‑Fi" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Wi-Fi Network Metered" msgstr "" -#: system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:320 #, python-format msgid "Wrong password" msgstr "" -#: selfdrive/ui/layouts/onboarding.py:145 +#: openpilot/selfdrive/ui/layouts/onboarding.py:149 #, python-format msgid "You must accept the Terms and Conditions in order to use openpilot." msgstr "openpilot'u kullanmak için Şartlar ve Koşulları kabul etmelisiniz." -#: selfdrive/ui/layouts/onboarding.py:112 +#: openpilot/selfdrive/ui/layouts/onboarding.py:116 #, python-format -msgid "" -"You must accept the Terms and Conditions to use openpilot. Read the latest " -"terms at https://comma.ai/terms before continuing." -msgstr "" -"openpilot'u kullanmak için Şartlar ve Koşulları kabul etmelisiniz. Devam " -"etmeden önce en güncel şartları https://comma.ai/terms adresinde okuyun." +msgid "You must accept the Terms and Conditions to use openpilot. Read the latest terms at https://comma.ai/terms before continuing." +msgstr "openpilot'u kullanmak için Şartlar ve Koşulları kabul etmelisiniz. Devam etmeden önce en güncel şartları https://comma.ai/terms adresinde okuyun." -#: selfdrive/ui/onroad/driver_camera_dialog.py:34 +#: openpilot/selfdrive/ui/onroad/driver_camera_dialog.py:38 #, python-format msgid "camera starting" msgstr "kamera başlatılıyor" -#: selfdrive/ui/widgets/prime.py:63 +#: openpilot/selfdrive/ui/layouts/settings/software.py:19 +#, python-format +msgid "checking..." +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:63 #, python-format msgid "comma prime" msgstr "comma prime" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "default" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "down" msgstr "aşağı" -#: selfdrive/ui/layouts/settings/software.py:106 +#: openpilot/selfdrive/ui/layouts/settings/software.py:20 +#, python-format +msgid "downloading..." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:116 #, python-format msgid "failed to check for update" msgstr "güncelleme kontrolü başarısız" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: openpilot/selfdrive/ui/layouts/settings/software.py:21 +#, python-format +msgid "finalizing update..." +msgstr "" + +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:321 #, python-format msgid "for \"{}\"" msgstr "" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "km/h" msgstr "km/h" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "leave blank for automatic configuration" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "left" msgstr "sol" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "metered" msgstr "" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "mph" msgstr "mph" -#: selfdrive/ui/layouts/settings/software.py:20 +#: openpilot/selfdrive/ui/layouts/settings/software.py:27 #, python-format msgid "never" msgstr "asla" -#: selfdrive/ui/layouts/settings/software.py:31 +#: openpilot/selfdrive/ui/layouts/settings/software.py:38 #, python-format msgid "now" msgstr "şimdi" -#: selfdrive/ui/layouts/settings/developer.py:71 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:71 #, python-format msgid "openpilot Longitudinal Control (Alpha)" msgstr "openpilot Boylamsal Kontrol (Alfa)" -#: selfdrive/ui/onroad/alert_renderer.py:51 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:51 #, python-format msgid "openpilot Unavailable" msgstr "openpilot Kullanılamıyor" -#: selfdrive/ui/layouts/settings/toggles.py:158 -#, python-format -msgid "" -"openpilot defaults to driving in chill mode. Experimental mode enables alpha-" -"level features that aren't ready for chill mode. Experimental features are " -"listed below:

End-to-End Longitudinal Control


Let the driving " -"model control the gas and brakes. openpilot will drive as it thinks a human " -"would, including stopping for red lights and stop signs. Since the driving " -"model decides the speed to drive, the set speed will only act as an upper " -"bound. This is an alpha quality feature; mistakes should be expected." -"

New Driving Visualization


The driving visualization will " -"transition to the road-facing wide-angle camera at low speeds to better show " -"some turns. The Experimental mode logo will also be shown in the top right " -"corner." -msgstr "" -"openpilot varsayılan olarak chill modunda sürer. Deneysel mod, chill moduna " -"hazır olmayan alfa seviyesindeki özellikleri etkinleştirir. Deneysel " -"özellikler aşağıda listelenmiştir:

Uçtan Uca Boylamsal Kontrol
Sürüş modelinin gaz ve frenleri kontrol etmesine izin verin. " -"openpilot, kırmızı ışıklarda ve dur işaretlerinde durmak dahil, bir insan " -"nasıl sürer diye düşündüğüne göre sürer. Hızı sürüş modeli belirlediğinden, " -"ayarlanan hız yalnızca üst sınır olarak işlev görür. Bu bir alfa kalitesinde " -"özelliktir; hatalar beklenmelidir.

Yeni Sürüş Görselleştirmesi
Sürüş görselleştirmesi, düşük hızlarda bazı dönüşleri daha iyi " -"göstermek için yola bakan geniş açılı kameraya geçer. Deneysel mod logosu " -"sağ üst köşede de gösterilecektir." - -#: selfdrive/ui/layouts/settings/device.py:165 -#, python-format -msgid "" -"openpilot is continuously calibrating, resetting is rarely required. " -"Resetting calibration will restart openpilot if the car is powered on." -msgstr "" -" Bu ayarı değiştirmek, araç çalışıyorsa openpilot'u yeniden başlatacaktır." - -#: selfdrive/ui/layouts/settings/firehose.py:20 -msgid "" -"openpilot learns to drive by watching humans, like you, drive.\n" -"\n" -"Firehose Mode allows you to maximize your training data uploads to improve " -"openpilot's driving models. More data means bigger models, which means " -"better Experimental Mode." -msgstr "" -"openpilot, sizin gibi insanların nasıl sürdüğünü izleyerek sürmeyi öğrenir.\n" -"\n" -"Firehose Modu, openpilot'un sürüş modellerini geliştirmek için eğitim veri " -"yüklemelerinizi en üst düzeye çıkarmanıza olanak tanır. Daha fazla veri, " -"daha büyük modeller demektir; bu da daha iyi Deneysel Mod anlamına gelir." - -#: selfdrive/ui/layouts/settings/toggles.py:183 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:184 #, python-format msgid "openpilot longitudinal control may come in a future update." msgstr "openpilot boylamsal kontrolü gelecekteki bir güncellemede gelebilir." -#: selfdrive/ui/layouts/settings/device.py:26 -msgid "" -"openpilot requires the device to be mounted within 4° left or right and " -"within 5° up or 9° down." -msgstr "" -"openpilot, cihazın sağa/sola 4° ve yukarı 5° veya aşağı 9° içinde monte " -"edilmesini gerektirir." +#: openpilot/selfdrive/ui/layouts/settings/device.py:25 +msgid "openpilot requires the device to be mounted within 4° left or right and within 5° up or 9° down." +msgstr "openpilot, cihazın sağa/sola 4° ve yukarı 5° veya aşağı 9° içinde monte edilmesini gerektirir." -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "right" msgstr "sağ" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "unmetered" msgstr "" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "up" msgstr "yukarı" -#: selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:127 #, python-format msgid "up to date, last checked never" msgstr "güncel, son kontrol asla" -#: selfdrive/ui/layouts/settings/software.py:115 +#: openpilot/selfdrive/ui/layouts/settings/software.py:125 #, python-format msgid "up to date, last checked {}" msgstr "güncel, son kontrol {}" -#: selfdrive/ui/layouts/settings/software.py:109 +#: openpilot/selfdrive/ui/layouts/settings/software.py:119 #, python-format msgid "update available" msgstr "güncelleme mevcut" -#: selfdrive/ui/layouts/home.py:169 +#: openpilot/selfdrive/ui/layouts/home.py:169 #, python-format msgid "{} ALERT" msgid_plural "{} ALERTS" msgstr[0] "{} UYARI" msgstr[1] "{} UYARILAR" -#: selfdrive/ui/layouts/settings/software.py:40 +#: openpilot/selfdrive/ui/layouts/settings/software.py:47 #, python-format msgid "{} day ago" msgid_plural "{} days ago" msgstr[0] "{} gün önce" msgstr[1] "{} gün önce" -#: selfdrive/ui/layouts/settings/software.py:37 +#: openpilot/selfdrive/ui/layouts/settings/software.py:44 #, python-format msgid "{} hour ago" msgid_plural "{} hours ago" msgstr[0] "{} saat önce" msgstr[1] "{} saat önce" -#: selfdrive/ui/layouts/settings/software.py:34 +#: openpilot/selfdrive/ui/layouts/settings/software.py:41 #, python-format msgid "{} minute ago" msgid_plural "{} minutes ago" msgstr[0] "{} dakika önce" msgstr[1] "{} dakika önce" -#: selfdrive/ui/layouts/settings/firehose.py:111 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:70 #, python-format msgid "{} segment of your driving is in the training dataset so far." msgid_plural "{} segments of your driving is in the training dataset so far." msgstr[0] "{} segment sürüşünüz eğitim veri setinde." msgstr[1] "{} segment sürüşünüz eğitim veri setinde." -#: selfdrive/ui/widgets/prime.py:62 +#: openpilot/selfdrive/ui/widgets/prime.py:62 #, python-format msgid "✓ SUBSCRIBED" msgstr "✓ ABONE" -#: selfdrive/ui/widgets/setup.py:22 +#: openpilot/selfdrive/ui/widgets/setup.py:21 #, python-format msgid "🔥 Firehose Mode 🔥" msgstr "🔥 Firehose Modu 🔥" + diff --git a/selfdrive/ui/translations/app_uk.po b/selfdrive/ui/translations/app_uk.po index cf78fb5a33..e36ceac2ce 100644 --- a/selfdrive/ui/translations/app_uk.po +++ b/selfdrive/ui/translations/app_uk.po @@ -15,1193 +15,980 @@ msgstr "" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" -"Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && " -"n%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2);\n" +"Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && n%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2);\n" "X-Generator: Poedit 3.8\n" -#: selfdrive/ui/layouts/settings/device.py:160 +#: openpilot/selfdrive/ui/layouts/settings/device.py:152 #, python-format msgid " Steering torque response calibration is complete." msgstr " Калібрування реакції крутного моменту керма завершено." -#: selfdrive/ui/layouts/settings/device.py:158 +#: openpilot/selfdrive/ui/layouts/settings/device.py:150 #, python-format msgid " Steering torque response calibration is {}% complete." msgstr "Калібрування реакції крутного моменту керма завершено на {}%." -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid " Your device is pointed {:.1f}° {} and {:.1f}° {}." msgstr " Ваш пристрій нахилено на {:.1f}° {} та {:.1f}° {}." -#: selfdrive/ui/layouts/sidebar.py:43 +#: openpilot/selfdrive/ui/layouts/sidebar.py:43 msgid "--" msgstr "--" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "1 year of drive storage" msgstr "1 рік зберігання поїздок" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "24/7 LTE connectivity" msgstr "Підключення LTE 24/7" -#: selfdrive/ui/layouts/sidebar.py:46 +#: openpilot/selfdrive/ui/layouts/sidebar.py:46 msgid "2G" msgstr "2G" -#: selfdrive/ui/layouts/sidebar.py:47 +#: openpilot/selfdrive/ui/layouts/sidebar.py:47 msgid "3G" msgstr "3G" -#: selfdrive/ui/layouts/sidebar.py:49 +#: openpilot/selfdrive/ui/layouts/sidebar.py:49 msgid "5G" msgstr "5G" -#: selfdrive/ui/layouts/settings/developer.py:23 -msgid "" -"WARNING: openpilot longitudinal control is in alpha for this car and will " -"disable Automatic Emergency Braking (AEB).

On this car, openpilot " -"defaults to the car's built-in ACC instead of openpilot's longitudinal " -"control. Enable this to switch to openpilot longitudinal control. Enabling " -"Experimental mode is recommended when enabling openpilot longitudinal " -"control alpha. Changing this setting will restart openpilot if the car is " -"powered on." -msgstr "" -"ПОПЕРЕДЖЕННЯ: поздовжнє керування openpilot для цього автомобіля знаходиться " -"в стадії альфа-тестування і вимкне автоматичне екстрене гальмування (AEB)." - -#: selfdrive/ui/layouts/settings/device.py:148 +#: openpilot/selfdrive/ui/layouts/settings/device.py:140 #, python-format msgid "

Steering lag calibration is complete." msgstr "

Калібрування затримки кермування завершено." -#: selfdrive/ui/layouts/settings/device.py:146 +#: openpilot/selfdrive/ui/layouts/settings/device.py:138 #, python-format msgid "

Steering lag calibration is {}% complete." msgstr "

Калібрування затримки кермування завершено на {}%." -#: selfdrive/ui/layouts/settings/firehose.py:138 -#, python-format -msgid "ACTIVE" -msgstr "АКТИВНИЙ" - -#: selfdrive/ui/layouts/settings/developer.py:15 -msgid "" -"ADB (Android Debug Bridge) allows connecting to your device over USB or over " -"the network. See https://docs.comma.ai/how-to/connect-to-comma for more info." -msgstr "" -"ADB (Android Debug Bridge) дозволяє підключатися до вашого пристрою через " -"USB або мережу. Дивіться https://docs.comma.ai/how-to/connect-to-comma для " -"отримання додаткової інформації." - -#: selfdrive/ui/widgets/ssh_key.py:30 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:30 msgid "ADD" msgstr "ДОДАТИ" -#: system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:136 #, python-format msgid "APN Setting" msgstr "Налаштування APN" -#: selfdrive/ui/widgets/offroad_alerts.py:109 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:109 #, python-format msgid "Acknowledge Excessive Actuation" msgstr "Визнайте надмірне спрацьовування" -#: system/ui/widgets/network.py:74 system/ui/widgets/network.py:95 +#: system/ui/widgets/network.py:92 +#: system/ui/widgets/network.py:74 #, python-format msgid "Advanced" msgstr "Розширені" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Aggressive" msgstr "Агресивн." -#: selfdrive/ui/layouts/onboarding.py:116 +#: openpilot/selfdrive/ui/layouts/onboarding.py:120 #, python-format msgid "Agree" msgstr "Погодитися" -#: selfdrive/ui/layouts/settings/toggles.py:70 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:70 #, python-format msgid "Always-On Driver Monitoring" msgstr "Постійний моніторинг водія" -#: selfdrive/ui/layouts/settings/toggles.py:186 -#, python-format -msgid "" -"An alpha version of openpilot longitudinal control can be tested, along with " -"Experimental mode, on non-release branches." -msgstr "" -"Альфа-версію поздовжнього керування openpilot можна протестувати разом з " -"експериментальним режимом на нерелізних гілках." - -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 #, python-format msgid "Are you sure you want to power off?" msgstr "Ви впевнені, що хочете вимкнути?" -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 #, python-format msgid "Are you sure you want to reboot?" msgstr "Ви впевнені, що хочете перезавантажити?" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Are you sure you want to reset calibration?" msgstr "Ви впевнені, що хочете скинути калібрування?" -#: selfdrive/ui/layouts/settings/software.py:171 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 #, python-format msgid "Are you sure you want to uninstall?" msgstr "Ви впевнені, що хочете видалити?" -#: system/ui/widgets/network.py:99 -#: selfdrive/ui/layouts/onboarding.py:147 +#: system/ui/widgets/network.py:96 +#: openpilot/selfdrive/ui/layouts/onboarding.py:151 #, python-format msgid "Back" msgstr "Назад" -#: selfdrive/ui/widgets/prime.py:38 +#: openpilot/selfdrive/ui/widgets/prime.py:38 #, python-format msgid "Become a comma prime member at connect.comma.ai" msgstr "Станьте членом comma prime на connect.comma.ai" -#: selfdrive/ui/widgets/pairing_dialog.py:119 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:119 #, python-format msgid "Bookmark connect.comma.ai to your home screen to use it like an app" -msgstr "" -"Додайте connect.comma.ai до головного екрану, щоб використовувати його як " -"додаток." +msgstr "Додайте connect.comma.ai до головного екрану, щоб використовувати його як додаток." -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "CHANGE" msgstr "ЗМІНИТИ" -#: selfdrive/ui/layouts/settings/software.py:50 -#: selfdrive/ui/layouts/settings/software.py:115 -#: selfdrive/ui/layouts/settings/software.py:126 -#: selfdrive/ui/layouts/settings/software.py:155 +#: openpilot/selfdrive/ui/layouts/settings/software.py:157 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 +#: openpilot/selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:128 #, python-format msgid "CHECK" msgstr "ПЕРЕВІРИТИ" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "CHILL MODE ON" msgstr "СПОКІЙНИЙ РЕЖИМ" -#: system/ui/widgets/network.py:155 -#: selfdrive/ui/layouts/sidebar.py:73 -#: selfdrive/ui/layouts/sidebar.py:134 -#: selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:138 +#: system/ui/widgets/network.py:152 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 #, python-format msgid "CONNECT" msgstr "CONNECT" -#: system/ui/widgets/network.py:369 +#: system/ui/widgets/network.py:376 #, python-format msgid "CONNECTING..." msgstr "ПІДКЛЮЧА..." -#: system/ui/widgets/confirm_dialog.py:23 system/ui/widgets/option_dialog.py:35 -#: system/ui/widgets/network.py:318 system/ui/widgets/keyboard.py:81 +#: system/ui/widgets/network.py:326 +#: system/ui/widgets/confirm_dialog.py:24 +#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/keyboard.py:83 #, python-format msgid "Cancel" msgstr "Скасувати" -#: system/ui/widgets/network.py:134 +#: system/ui/widgets/network.py:131 #, python-format msgid "Cellular Metered" msgstr "Лімітне стільникове з'єднання" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "Change Language" msgstr "Змінити мову" -#: selfdrive/ui/layouts/settings/toggles.py:125 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:125 #, python-format msgid "Changing this setting will restart openpilot if the car is powered on." -msgstr "" -"Зміна цього параметра призведе до перезапуску openpilot, якщо автомобіль " -"увімкнено." +msgstr "Зміна цього параметра призведе до перезапуску openpilot, якщо автомобіль увімкнено." -#: selfdrive/ui/widgets/pairing_dialog.py:118 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:118 #, python-format msgid "Click \"add new device\" and scan the QR code on the right" msgstr "Натисніть «додати новий пристрій» і відскануйте QR-код праворуч." -#: selfdrive/ui/widgets/offroad_alerts.py:104 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:104 #, python-format msgid "Close" msgstr "Закрити" -#: selfdrive/ui/layouts/settings/software.py:49 +#: openpilot/selfdrive/ui/layouts/settings/software.py:56 #, python-format msgid "Current Version" msgstr "Поточна версія" -#: selfdrive/ui/layouts/settings/software.py:118 +#: openpilot/selfdrive/ui/layouts/settings/software.py:120 #, python-format msgid "DOWNLOAD" msgstr "ВАНТАЖ" -#: selfdrive/ui/layouts/onboarding.py:115 +#: openpilot/selfdrive/ui/layouts/onboarding.py:119 #, python-format msgid "Decline" msgstr "Відхилити" -#: selfdrive/ui/layouts/onboarding.py:148 +#: openpilot/selfdrive/ui/layouts/onboarding.py:152 #, python-format msgid "Decline, uninstall openpilot" msgstr "Відхилити, видалити openpilot" -#: selfdrive/ui/layouts/settings/settings.py:64 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:64 msgid "Developer" msgstr "Розробник" -#: selfdrive/ui/layouts/settings/settings.py:59 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:59 msgid "Device" msgstr "Пристрій" -#: selfdrive/ui/layouts/settings/toggles.py:58 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:58 #, python-format msgid "Disengage on Accelerator Pedal" msgstr "Вимкнення при натисканні на педаль газу" -#: selfdrive/ui/layouts/settings/device.py:184 +#: openpilot/selfdrive/ui/layouts/settings/device.py:176 #, python-format msgid "Disengage to Power Off" msgstr "Вимкніть openpilot, щоб вимкнути пристрій" -#: selfdrive/ui/layouts/settings/device.py:172 +#: openpilot/selfdrive/ui/layouts/settings/device.py:164 #, python-format msgid "Disengage to Reboot" msgstr "Вимкніть openpilot, щоб перезавантажити" -#: selfdrive/ui/layouts/settings/device.py:103 +#: openpilot/selfdrive/ui/layouts/settings/device.py:95 #, python-format msgid "Disengage to Reset Calibration" msgstr "Деактивуйте для скидання калібрування" -#: selfdrive/ui/layouts/settings/toggles.py:32 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:32 msgid "Display speed in km/h instead of mph." msgstr "Відображати швидкість у км/год замість миль/год." -#: selfdrive/ui/layouts/settings/device.py:59 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 #, python-format msgid "Dongle ID" msgstr "ID ключа" -#: selfdrive/ui/layouts/settings/software.py:50 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 #, python-format msgid "Download" msgstr "Завантажити" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "Driver Camera" msgstr "Камера водія" -#: selfdrive/ui/layouts/settings/toggles.py:96 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:96 #, python-format msgid "Driving Personality" msgstr "Стиль водіння" -#: system/ui/widgets/network.py:123 system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:136 #, python-format msgid "EDIT" msgstr "РЕДАГ." -#: selfdrive/ui/layouts/sidebar.py:138 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 msgid "ERROR" msgstr "ПОМИЛКА" -#: selfdrive/ui/layouts/sidebar.py:45 +#: openpilot/selfdrive/ui/layouts/sidebar.py:45 msgid "ETH" msgstr "ETH" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "EXPERIMENTAL MODE ON" msgstr "ЕКСПЕРИМЕНТ. РЕЖИМ" -#: selfdrive/ui/layouts/settings/toggles.py:228 -#: selfdrive/ui/layouts/settings/developer.py:166 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:229 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:180 #, python-format msgid "Enable" msgstr "Увімкнути" -#: selfdrive/ui/layouts/settings/developer.py:39 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:39 #, python-format msgid "Enable ADB" msgstr "Увімкнути ADB" -#: selfdrive/ui/layouts/settings/toggles.py:64 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:64 #, python-format msgid "Enable Lane Departure Warnings" msgstr "Увімкнути попередження про виїзд зі смуги" -#: system/ui/widgets/network.py:129 +#: system/ui/widgets/network.py:126 #, python-format msgid "Enable Roaming" msgstr "Увімкнути роумінг" -#: selfdrive/ui/layouts/settings/developer.py:48 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:48 #, python-format msgid "Enable SSH" msgstr "Увімкнути SSH" -#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:117 #, python-format msgid "Enable Tethering" msgstr "Увімкнути точку доступу" -#: selfdrive/ui/layouts/settings/toggles.py:30 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:30 msgid "Enable driver monitoring even when openpilot is not engaged." msgstr "Увімкнути моніторинг водія, навіть коли openpilot не ввімкнено." -#: selfdrive/ui/layouts/settings/toggles.py:46 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:46 #, python-format msgid "Enable openpilot" msgstr "Увімкнути openpilot" -#: selfdrive/ui/layouts/settings/toggles.py:189 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:190 #, python-format -msgid "" -"Enable the openpilot longitudinal control (alpha) toggle to allow " -"Experimental mode." -msgstr "" -"Увімкніть перемикач поздовжнього керування openpilot (альфа), щоб увімкнути " -"експериментальний режим." +msgid "Enable the openpilot longitudinal control (alpha) toggle to allow Experimental mode." +msgstr "Увімкніть перемикач поздовжнього керування openpilot (альфа), щоб увімкнути експериментальний режим." -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "Enter APN" msgstr "Введіть APN" -#: system/ui/widgets/network.py:241 +#: system/ui/widgets/network.py:243 #, python-format msgid "Enter SSID" msgstr "Введіть SSID" -#: system/ui/widgets/network.py:254 +#: system/ui/widgets/network.py:257 #, python-format msgid "Enter new tethering password" msgstr "Введіть новий пароль для модему" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:320 #, python-format msgid "Enter password" msgstr "Введіть пароль" -#: selfdrive/ui/widgets/ssh_key.py:89 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:89 #, python-format msgid "Enter your GitHub username" msgstr "Введіть ваш логін GitHub" -#: system/ui/widgets/list_view.py:123 system/ui/widgets/list_view.py:160 +#: system/ui/widgets/list_view.py:123 +#: system/ui/widgets/list_view.py:160 #, python-format msgid "Error" msgstr "Помилка" -#: selfdrive/ui/layouts/settings/toggles.py:52 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:52 #, python-format msgid "Experimental Mode" msgstr "Експериментальний режим" -#: selfdrive/ui/layouts/settings/toggles.py:181 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:182 #, python-format -msgid "" -"Experimental mode is currently unavailable on this car since the car's stock " -"ACC is used for longitudinal control." -msgstr "" -"Експериментальний режим наразі недоступний для цього автомобіля, оскільки " -"для поздовжнього керування використовується штатний адаптивний круїз-" -"контроль (ACC)." +msgid "Experimental mode is currently unavailable on this car since the car's stock ACC is used for longitudinal control." +msgstr "Експериментальний режим наразі недоступний для цього автомобіля, оскільки для поздовжнього керування використовується штатний адаптивний круїз-контроль (ACC)." -#: system/ui/widgets/network.py:373 +#: system/ui/widgets/network.py:380 #, python-format msgid "FORGETTING..." msgstr "ЗАБУВАЮ..." -#: selfdrive/ui/widgets/setup.py:44 +#: openpilot/selfdrive/ui/widgets/setup.py:43 #, python-format msgid "Finish Setup" msgstr "Завершити налаштування" -#: selfdrive/ui/layouts/settings/settings.py:63 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:63 msgid "Firehose" msgstr "Злива" -#: selfdrive/ui/layouts/settings/firehose.py:18 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:10 msgid "Firehose Mode" msgstr "Режим зливи" -#: selfdrive/ui/layouts/settings/firehose.py:25 -msgid "" -"For maximum effectiveness, bring your device inside and connect to a good " -"USB-C adapter and Wi-Fi weekly.\n" -"\n" -"Firehose Mode can also work while you're driving if connected to a hotspot " -"or unlimited SIM card.\n" -"\n" -"\n" -"Frequently Asked Questions\n" -"\n" -"Does it matter how or where I drive? Nope, just drive as you normally " -"would.\n" -"\n" -"Do all of my segments get pulled in Firehose Mode? No, we selectively pull a " -"subset of your segments.\n" -"\n" -"What's a good USB-C adapter? Any fast phone or laptop charger should be " -"fine.\n" -"\n" -"Does it matter which software I run? Yes, only upstream openpilot (and " -"particular forks) are able to be used for training." -msgstr "" -"Для максимальної ефективності щотижня заносьте пристрій у приміщення та " -"підключайте його до якісного адаптера USB-C і Wi-Fi.\n" -"\n" -"Режим Зливи також може працювати під час руху, якщо пристрій підключено до " -"точки доступу або SIM-картки з необмеженим трафіком.\n" -"\n" -"\n" -"Поширені запитання\n" -"\n" -"Чи має значення, як і де я їду? Ні, просто їдьте, як зазвичай.\n" -"\n" -"Чи всі мої сегменти потрапляють у режим Зливи? Ні, ми вибірково вибираємо " -"підмножину ваших сегментів.\n" -"\n" -"Що таке хороший адаптер USB-C? Будь-який швидкий зарядний пристрій для " -"телефону або ноутбука підійде.\n" -"\n" -"Чи має значення, яке програмне забезпечення я використовую? Так, для " -"навчання можна використовувати тільки upstream openpilot (і певні його " -"форки)." - -#: system/ui/widgets/network.py:318 system/ui/widgets/network.py:451 +#: system/ui/widgets/network.py:458 +#: system/ui/widgets/network.py:326 #, python-format msgid "Forget" msgstr "Заб-и" -#: system/ui/widgets/network.py:319 +#: system/ui/widgets/network.py:327 #, python-format msgid "Forget Wi-Fi Network \"{}\"?" msgstr "Забути мережу Wi-Fi \"{}\"?" -#: selfdrive/ui/layouts/sidebar.py:71 -#: selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 msgid "GOOD" msgstr "ДОБРА" -#: selfdrive/ui/widgets/pairing_dialog.py:117 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:117 #, python-format msgid "Go to https://connect.comma.ai on your phone" msgstr "Перейдіть на сайт https://connect.comma.ai на своєму телефоні." -#: selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "HIGH" msgstr "ВИСОКА" -#: system/ui/widgets/network.py:155 +#: system/ui/widgets/network.py:152 #, python-format msgid "Hidden Network" msgstr "Прихована мережа" -#: selfdrive/ui/layouts/settings/firehose.py:140 -#, python-format -msgid "INACTIVE: connect to an unmetered network" -msgstr "НЕАКТИВНО: підключення до мережі без ліміту трафіку" - -#: selfdrive/ui/layouts/settings/software.py:53 -#: selfdrive/ui/layouts/settings/software.py:144 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 +#: openpilot/selfdrive/ui/layouts/settings/software.py:146 #, python-format msgid "INSTALL" msgstr "ВСТАНОВ." -#: system/ui/widgets/network.py:150 +#: system/ui/widgets/network.py:147 #, python-format msgid "IP Address" msgstr "IP-адреса" -#: selfdrive/ui/layouts/settings/software.py:53 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 #, python-format msgid "Install Update" msgstr "Встановити оновлення" -#: selfdrive/ui/layouts/settings/developer.py:56 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:56 #, python-format msgid "Joystick Debug Mode" msgstr "Режим зневадження джойстика" -#: selfdrive/ui/widgets/ssh_key.py:29 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:29 msgid "LOADING" msgstr "ЗАВАНТАЖЕННЯ" -#: selfdrive/ui/layouts/sidebar.py:48 +#: openpilot/selfdrive/ui/layouts/sidebar.py:48 msgid "LTE" msgstr "LTE" -#: selfdrive/ui/layouts/settings/developer.py:64 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:64 #, python-format msgid "Longitudinal Maneuver Mode" msgstr "Режим поздовжнього маневрування" -#: selfdrive/ui/onroad/hud_renderer.py:148 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:148 #, python-format msgid "MAX" msgstr "МАКС" -#: selfdrive/ui/widgets/setup.py:75 +#: openpilot/selfdrive/ui/widgets/setup.py:74 #, python-format -msgid "" -"Maximize your training data uploads to improve openpilot's driving models." -msgstr "" -"Максимізуйте завантаження навчальних даних, щоб поліпшити моделі openpilot." +msgid "Maximize your training data uploads to improve openpilot's driving models." +msgstr "Максимізуйте завантаження навчальних даних, щоб поліпшити моделі openpilot." -#: selfdrive/ui/layouts/settings/device.py:59 -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "N/A" msgstr "Н/Д" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "NO" msgstr "НЕМАЄ" -#: selfdrive/ui/layouts/settings/settings.py:60 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:60 msgid "Network" msgstr "Мережа" -#: selfdrive/ui/widgets/ssh_key.py:114 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:115 #, python-format msgid "No SSH keys found" msgstr "Не знайдено ключів SSH" -#: selfdrive/ui/widgets/ssh_key.py:126 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:127 #, python-format msgid "No SSH keys found for user '{}'" msgstr "Користувач '{}' не має ключів на GitHub" -#: selfdrive/ui/widgets/offroad_alerts.py:320 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:321 #, python-format msgid "No release notes available." msgstr "Інформація про випуск відсутня." -#: selfdrive/ui/layouts/sidebar.py:73 -#: selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 msgid "OFFLINE" msgstr "ОФЛАЙН" -#: system/ui/widgets/confirm_dialog.py:93 system/ui/widgets/html_render.py:263 -#: selfdrive/ui/layouts/sidebar.py:127 +#: system/ui/widgets/confirm_dialog.py:93 +#: system/ui/widgets/html_render.py:263 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 #, python-format msgid "OK" msgstr "OK" -#: selfdrive/ui/layouts/sidebar.py:72 -#: selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 msgid "ONLINE" msgstr "ОНЛАЙН" -#: selfdrive/ui/widgets/setup.py:20 +#: openpilot/selfdrive/ui/widgets/setup.py:19 #, python-format msgid "Open" msgstr "ВІДКРИТИ" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "PAIR" msgstr "ПІДКЛЮЧИТИ" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "PANDA" msgstr "PANDA" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "PREVIEW" msgstr "ПОКАЖИ" -#: selfdrive/ui/widgets/prime.py:44 +#: openpilot/selfdrive/ui/widgets/prime.py:44 #, python-format msgid "PRIME FEATURES:" msgstr "XАРАКТЕРИСТИКИ PRIME:" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "Pair Device" msgstr "Підключити пристрій" -#: selfdrive/ui/widgets/setup.py:19 +#: openpilot/selfdrive/ui/widgets/setup.py:18 #, python-format msgid "Pair device" msgstr "Підключити пристрій" -#: selfdrive/ui/widgets/pairing_dialog.py:92 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:92 #, python-format msgid "Pair your device to your comma account" msgstr "Підключіть свій пристрій до обліковки comma connect" -#: selfdrive/ui/widgets/setup.py:48 -#: selfdrive/ui/layouts/settings/device.py:24 +#: openpilot/selfdrive/ui/widgets/setup.py:47 +#: openpilot/selfdrive/ui/layouts/settings/device.py:23 #, python-format -msgid "" -"Pair your device with comma connect (connect.comma.ai) and claim your comma " -"prime offer." -msgstr "" -"Підключіть свій пристрій до comma connect (connect.comma.ai) і отримайте " -"свою пропозицію comma prime." +msgid "Pair your device with comma connect (connect.comma.ai) and claim your comma prime offer." +msgstr "Підключіть свій пристрій до comma connect (connect.comma.ai) і отримайте свою пропозицію comma prime." -#: selfdrive/ui/widgets/setup.py:91 +#: openpilot/selfdrive/ui/widgets/setup.py:91 #, python-format msgid "Please connect to Wi-Fi to complete initial pairing" msgstr "Будь ласка, підключіться до Wi-Fi, щоб завершити початкове сполучення." -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Power Off" msgstr "Вимкнути" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Prevent large data uploads when on a metered Wi-Fi connection" -msgstr "" -"Запобігайте завантаженню великих обсягів даних під час використання Wi-Fi-" -"з'єднання з обмеженим трафіком" +msgstr "Запобігайте завантаженню великих обсягів даних під час використання Wi-Fi-з'єднання з обмеженим трафіком" -#: system/ui/widgets/network.py:135 +#: system/ui/widgets/network.py:132 #, python-format msgid "Prevent large data uploads when on a metered cellular connection" -msgstr "" -"Запобігати великим завантаженням даних під час лімітного стільникового " -"з'єднання" +msgstr "Запобігати великим завантаженням даних під час лімітного стільникового з'єднання" -#: selfdrive/ui/layouts/settings/device.py:25 -msgid "" -"Preview the driver facing camera to ensure that driver monitoring has good " -"visibility. (vehicle must be off)" -msgstr "" -"Попередньо перегляньте камеру, спрямовану на водія, щоб переконатися, що " -"система моніторингу водія має добру видимість. (автомобіль повинен бути " -"вимкнений)" +#: openpilot/selfdrive/ui/layouts/settings/device.py:24 +msgid "Preview the driver facing camera to ensure that driver monitoring has good visibility. (vehicle must be off)" +msgstr "Попередньо перегляньте камеру, спрямовану на водія, щоб переконатися, що система моніторингу водія має добру видимість. (автомобіль повинен бути вимкнений)" -#: selfdrive/ui/widgets/pairing_dialog.py:150 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:150 #, python-format msgid "QR Code Error" msgstr "Помилка QR-коду" -#: selfdrive/ui/widgets/ssh_key.py:31 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:31 msgid "REMOVE" msgstr "ВИДАЛИТИ" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "RESET" msgstr "Скинути" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "REVIEW" msgstr "ДИВИТИСЬ" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Reboot" msgstr "Перезавантажити" -#: selfdrive/ui/onroad/alert_renderer.py:66 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:66 #, python-format msgid "Reboot Device" msgstr "Перезавантажте пристрій" -#: selfdrive/ui/widgets/offroad_alerts.py:112 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:112 #, python-format msgid "Reboot and Update" msgstr "Перезавантажити та оновити" -#: selfdrive/ui/layouts/settings/toggles.py:27 -msgid "" -"Receive alerts to steer back into the lane when your vehicle drifts over a " -"detected lane line without a turn signal activated while driving over 31 mph " -"(50 km/h)." -msgstr "" -"Отримувати попередження про необхідність повернутися в смугу, коли ваш " -"автомобіль перетинає виявлену лінію розмітки без увімкненого сигналу " -"повороту під час руху зі швидкістю понад 31 миль/год (50 км/год)." - -#: selfdrive/ui/layouts/settings/toggles.py:76 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:76 #, python-format msgid "Record and Upload Driver Camera" msgstr "Писати та вантажити відео з камери водія" -#: selfdrive/ui/layouts/settings/toggles.py:82 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:82 #, python-format msgid "Record and Upload Microphone Audio" msgstr "Запис та завантаження аудіо з мікрофона" -#: selfdrive/ui/layouts/settings/toggles.py:33 -msgid "" -"Record and store microphone audio while driving. The audio will be included " -"in the dashcam video in comma connect." -msgstr "" -"Записуйте та зберігайте аудіо з мікрофона під час руху. Аудіо буде включено " -"до відео з відеореєстратора в comma connect." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:33 +msgid "Record and store microphone audio while driving. The audio will be included in the dashcam video in comma connect." +msgstr "Записуйте та зберігайте аудіо з мікрофона під час руху. Аудіо буде включено до відео з відеореєстратора в comma connect." -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "Regulatory" msgstr "Нормативні документи" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Relaxed" msgstr "Спокійний" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote access" msgstr "Віддалений доступ" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote snapshots" msgstr "Віддалені знімки" -#: selfdrive/ui/widgets/ssh_key.py:123 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:124 #, python-format msgid "Request timed out" msgstr "Час запиту вичерпано" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Reset" msgstr "Скинути" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "Reset Calibration" msgstr "Скинути калібрування" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "Review Training Guide" msgstr "Переглянути посібник з навчання" -#: selfdrive/ui/layouts/settings/device.py:27 +#: openpilot/selfdrive/ui/layouts/settings/device.py:26 msgid "Review the rules, features, and limitations of openpilot" msgstr "Перегляньте правила, функції та обмеження openpilot" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "SELECT" msgstr "ВИБРАТИ" -#: selfdrive/ui/layouts/settings/developer.py:53 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:53 #, python-format msgid "SSH Keys" msgstr "SSH ключі" -#: system/ui/widgets/network.py:310 +#: system/ui/widgets/network.py:316 #, python-format msgid "Scanning Wi-Fi networks..." msgstr "Пошук мереж..." -#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/option_dialog.py:37 #, python-format msgid "Select" msgstr "Вибрати" -#: selfdrive/ui/layouts/settings/software.py:191 +#: openpilot/selfdrive/ui/layouts/settings/software.py:203 #, python-format msgid "Select a branch" msgstr "Виберіть гілку" -#: selfdrive/ui/layouts/settings/device.py:91 +#: openpilot/selfdrive/ui/layouts/settings/device.py:89 #, python-format msgid "Select a language" msgstr "Виберіть мову" -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "Serial" msgstr "Серійний номер" -#: selfdrive/ui/widgets/offroad_alerts.py:106 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:106 #, python-format msgid "Snooze Update" msgstr "Відкласти оновлення" -#: selfdrive/ui/layouts/settings/settings.py:62 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:62 msgid "Software" msgstr "Програма" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Standard" msgstr "Стандарт" -#: selfdrive/ui/layouts/settings/toggles.py:22 -msgid "" -"Standard is recommended. In aggressive mode, openpilot will follow lead cars " -"closer and be more aggressive with the gas and brake. In relaxed mode " -"openpilot will stay further away from lead cars. On supported cars, you can " -"cycle through these personalities with your steering wheel distance button." -msgstr "" -"Рекомендується стандартний режим. В агресивному режимі openpilot буде " -"триматися ближче до автомобілів попереду і більш агресивно використовувати " -"газ і гальма. У спокійному режимі openpilot буде триматися на більшій " -"відстані від автомобілів попереду. На підтримуваних автомобілях ви можете " -"перемикатися між цими режимами за допомогою кнопки дистанції на кермі." - -#: selfdrive/ui/onroad/alert_renderer.py:59 -#: selfdrive/ui/onroad/alert_renderer.py:65 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:59 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:65 #, python-format msgid "System Unresponsive" msgstr "Система не реагує" -#: selfdrive/ui/onroad/alert_renderer.py:58 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:58 #, python-format msgid "TAKE CONTROL IMMEDIATELY" msgstr "КЕРМУЙТЕ НЕГАЙНО" -#: selfdrive/ui/layouts/sidebar.py:71 -#: selfdrive/ui/layouts/sidebar.py:125 -#: selfdrive/ui/layouts/sidebar.py:127 -#: selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "TEMP" msgstr "ТЕМП" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "Target Branch" msgstr "Цільова гілка" -#: system/ui/widgets/network.py:124 +#: system/ui/widgets/network.py:121 #, python-format msgid "Tethering Password" msgstr "Пароль для точки доступу" -#: selfdrive/ui/layouts/settings/settings.py:61 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:61 msgid "Toggles" msgstr "Перемикачі" -#: selfdrive/ui/layouts/settings/software.py:72 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:79 +#, python-format +msgid "UI Debug Mode" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "UNINSTALL" msgstr "ВИДАЛИТИ" -#: selfdrive/ui/layouts/home.py:155 +#: openpilot/selfdrive/ui/layouts/home.py:155 #, python-format msgid "UPDATE" msgstr "ОНОВИТИ" -#: selfdrive/ui/layouts/settings/software.py:72 -#: selfdrive/ui/layouts/settings/software.py:171 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "Uninstall" msgstr "Видалити" -#: selfdrive/ui/layouts/sidebar.py:117 +#: openpilot/selfdrive/ui/layouts/sidebar.py:117 msgid "Unknown" msgstr "Невідомо" -#: selfdrive/ui/layouts/settings/software.py:48 +#: openpilot/selfdrive/ui/layouts/settings/software.py:55 #, python-format msgid "Updates are only downloaded while the car is off." msgstr "Оновлення завантажуються лише тоді, коли автомобіль вимкнено." -#: selfdrive/ui/widgets/prime.py:33 +#: openpilot/selfdrive/ui/widgets/prime.py:33 #, python-format msgid "Upgrade Now" msgstr "Оновити зараз" -#: selfdrive/ui/layouts/settings/toggles.py:31 -msgid "" -"Upload data from the driver facing camera and help improve the driver " -"monitoring algorithm." -msgstr "" -"Завантажуйте дані з камери, спрямованої на водія, та допоможіть покращити " -"алгоритм моніторингу водія." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:31 +msgid "Upload data from the driver facing camera and help improve the driver monitoring algorithm." +msgstr "Завантажуйте дані з камери, спрямованої на водія, та допоможіть покращити алгоритм моніторингу водія." -#: selfdrive/ui/layouts/settings/toggles.py:88 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:88 #, python-format msgid "Use Metric System" msgstr "Використовувати метричну систему" -#: selfdrive/ui/layouts/settings/toggles.py:17 -msgid "" -"Use the openpilot system for adaptive cruise control and lane keep driver " -"assistance. Your attention is required at all times to use this feature." -msgstr "" -"Використовуйте систему openpilot для адаптивного круїз-контролю та допомоги " -"в утриманні смуги руху. Ваша увага потрібна постійно при використанні цієї " -"функції. Зміна цього налаштування набуває чинності після вимкнення живлення " -"автомобіля." - -#: selfdrive/ui/layouts/sidebar.py:72 -#: selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 msgid "VEHICLE" msgstr "АВТО" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "VIEW" msgstr "ДИВИСЬ" -#: selfdrive/ui/onroad/alert_renderer.py:52 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:52 #, python-format msgid "Waiting to start" msgstr "Очікування початку" -#: selfdrive/ui/layouts/settings/developer.py:19 -msgid "" -"Warning: This grants SSH access to all public keys in your GitHub settings. " -"Never enter a GitHub username other than your own. A comma employee will " -"NEVER ask you to add their GitHub username." -msgstr "" -"Попередження: це надає доступ по SSH до всіх публічних ключів у ваших " -"налаштуваннях GitHub. Ніколи не вводьте ім'я користувача GitHub, окрім " -"вашого власного. Співробітник comma НІКОЛИ не попросить вас додати його ім'я " -"користувача GitHub." - -#: selfdrive/ui/layouts/onboarding.py:111 +#: openpilot/selfdrive/ui/layouts/onboarding.py:115 #, python-format msgid "Welcome to openpilot" msgstr "Ласкаво просимо до openpilot" -#: selfdrive/ui/layouts/settings/toggles.py:20 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:20 msgid "When enabled, pressing the accelerator pedal will disengage openpilot." msgstr "Якщо увімкнено, натискання на педаль акселератора вимкне openpilot." -#: selfdrive/ui/layouts/sidebar.py:44 +#: openpilot/selfdrive/ui/layouts/sidebar.py:44 msgid "Wi-Fi" msgstr "Wi-Fi" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Wi-Fi Network Metered" msgstr "Трафік Wi-Fi" -#: system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:320 #, python-format msgid "Wrong password" msgstr "Невірний пароль" -#: selfdrive/ui/layouts/onboarding.py:145 +#: openpilot/selfdrive/ui/layouts/onboarding.py:149 #, python-format msgid "You must accept the Terms and Conditions in order to use openpilot." msgstr "Ви повинні прийняти Умови та положення, щоб користуватися openpilot." -#: selfdrive/ui/layouts/onboarding.py:112 +#: openpilot/selfdrive/ui/layouts/onboarding.py:116 #, python-format -msgid "" -"You must accept the Terms and Conditions to use openpilot. Read the latest " -"terms at https://comma.ai/terms before continuing." -msgstr "" -"Ви повинні прийняти Умови використання, щоб користуватися openpilot. Перед " -"тим, як продовжити, ознайомтеся з останніми умовами на сайті https://" -"comma.ai/terms." +msgid "You must accept the Terms and Conditions to use openpilot. Read the latest terms at https://comma.ai/terms before continuing." +msgstr "Ви повинні прийняти Умови використання, щоб користуватися openpilot. Перед тим, як продовжити, ознайомтеся з останніми умовами на сайті https://comma.ai/terms." -#: selfdrive/ui/onroad/driver_camera_dialog.py:34 +#: openpilot/selfdrive/ui/onroad/driver_camera_dialog.py:38 #, python-format msgid "camera starting" msgstr "запуск камери" -#: selfdrive/ui/layouts/settings/software.py:105 +#: openpilot/selfdrive/ui/layouts/settings/software.py:19 #, python-format msgid "checking..." msgstr "перевіряю..." -#: selfdrive/ui/widgets/prime.py:63 +#: openpilot/selfdrive/ui/widgets/prime.py:63 #, python-format msgid "comma prime" msgstr "comma prime" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "default" msgstr "замовч." -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "down" msgstr "вниз" -#: selfdrive/ui/layouts/settings/software.py:106 +#: openpilot/selfdrive/ui/layouts/settings/software.py:20 #, python-format msgid "downloading..." msgstr "завантажую..." -#: selfdrive/ui/layouts/settings/software.py:114 +#: openpilot/selfdrive/ui/layouts/settings/software.py:116 #, python-format msgid "failed to check for update" msgstr "не вдалося перевірити оновлення" -#: selfdrive/ui/layouts/settings/software.py:107 +#: openpilot/selfdrive/ui/layouts/settings/software.py:21 #, python-format msgid "finalizing update..." msgstr "завершую..." -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:321 #, python-format msgid "for \"{}\"" msgstr "для \"{}\"" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "km/h" msgstr "км/год" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "leave blank for automatic configuration" msgstr "залиште порожнім для автоматичного налаштування" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "left" msgstr "вліво" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "metered" msgstr "обмеж." -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "mph" msgstr "миль/год" -#: selfdrive/ui/layouts/settings/software.py:20 +#: openpilot/selfdrive/ui/layouts/settings/software.py:27 #, python-format msgid "never" msgstr "ніколи" -#: selfdrive/ui/layouts/settings/software.py:31 +#: openpilot/selfdrive/ui/layouts/settings/software.py:38 #, python-format msgid "now" msgstr "зараз" -#: selfdrive/ui/layouts/settings/developer.py:71 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:71 #, python-format msgid "openpilot Longitudinal Control (Alpha)" msgstr "Поздовжнє керування openpilot (Альфа)" -#: selfdrive/ui/onroad/alert_renderer.py:51 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:51 #, python-format msgid "openpilot Unavailable" msgstr "openpilot Недоступний" -#: selfdrive/ui/layouts/settings/toggles.py:158 -#, python-format -msgid "" -"openpilot defaults to driving in chill mode. Experimental mode enables alpha-" -"level features that aren't ready for chill mode. Experimental features are " -"listed below:

End-to-End Longitudinal Control


Let the driving " -"model control the gas and brakes. openpilot will drive as it thinks a human " -"would, including stopping for red lights and stop signs. Since the driving " -"model decides the speed to drive, the set speed will only act as an upper " -"bound. This is an alpha quality feature; mistakes should be expected." -"

New Driving Visualization


The driving visualization will " -"transition to the road-facing wide-angle camera at low speeds to better show " -"some turns. The Experimental mode logo will also be shown in the top right " -"corner." -msgstr "" -"openpilot за замовчуванням працює в режимі спокій. Експериментальний режим " -"увімкне функції альфа-рівня, які ще не готові для режиму спокій. " -"Експериментальні функції перелічені нижче:

Кінцевий поздовжній " -"контроль


Дозвольте моделі водіння контролювати газ і гальма. " -"openpilot буде керувати автомобілем так, як це робив би людина, включаючи " -"зупинку на червоне світло і знаки зупинки. Оскільки модель водіння визначає " -"швидкість руху, задана швидкість буде діяти лише як верхня межа. Це функція " -"альфа-рівня; слід очікувати помилок.

Нова візуалізація водіння
Візуалізація водіння перейде на ширококутну камеру, спрямовану на " -"дорогу, при низьких швидкостях, щоб краще показувати деякі повороти. Логотип " -"експериментального режиму також буде показаний у верхньому правому куті." - -#: selfdrive/ui/layouts/settings/device.py:165 -#, python-format -msgid "" -"openpilot is continuously calibrating, resetting is rarely required. " -"Resetting calibration will restart openpilot if the car is powered on." -msgstr "" -"openpilot постійно калібрується, скидання рідко потрібне. Скидання " -"калібрування призведе до перезапуску openpilot, якщо автомобіль увімкнено." - -#: selfdrive/ui/layouts/settings/firehose.py:20 -msgid "" -"openpilot learns to drive by watching humans, like you, drive.\n" -"\n" -"Firehose Mode allows you to maximize your training data uploads to improve " -"openpilot's driving models. More data means bigger models, which means " -"better Experimental Mode." -msgstr "" -"openpilot вчиться керувати автомобілем, спостерігаючи за тим, як це роблять " -"люди, такі як ви.\n" -"\n" -"Режим зливи дозволяє максимально збільшити обсяг завантажуваних навчальних " -"даних, щоб поліпшити моделі керування автомобілем openpilot. Більше даних " -"означає більші моделі, а це означає кращий експериментальний режим." - -#: selfdrive/ui/layouts/settings/toggles.py:183 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:184 #, python-format msgid "openpilot longitudinal control may come in a future update." msgstr "Поздовжнє керування openpilot може з'явитися в майбутньому оновленні." -#: selfdrive/ui/layouts/settings/device.py:26 -msgid "" -"openpilot requires the device to be mounted within 4° left or right and " -"within 5° up or 9° down." -msgstr "" -"Для роботи openpilot потрібно, щоб пристрій був встановлений з нахилом не " -"більше 4° вліво або вправо та не більше 5° вгору або 9° вниз. openpilot " -"постійно калібрується, тому скидання калібрування потрібне рідко." +#: openpilot/selfdrive/ui/layouts/settings/device.py:25 +msgid "openpilot requires the device to be mounted within 4° left or right and within 5° up or 9° down." +msgstr "Для роботи openpilot потрібно, щоб пристрій був встановлений з нахилом не більше 4° вліво або вправо та не більше 5° вгору або 9° вниз. openpilot постійно калібрується, тому скидання калібрування потрібне рідко." -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "right" msgstr "вправо" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "unmetered" msgstr "необмеж." -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "up" msgstr "вгору" -#: selfdrive/ui/layouts/settings/software.py:125 +#: openpilot/selfdrive/ui/layouts/settings/software.py:127 #, python-format msgid "up to date, last checked never" msgstr "оновлено, ніколи не перевірялось" -#: selfdrive/ui/layouts/settings/software.py:123 +#: openpilot/selfdrive/ui/layouts/settings/software.py:125 #, python-format msgid "up to date, last checked {}" msgstr "оновлено, перевірив {}" -#: selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:119 #, python-format msgid "update available" msgstr "доступне оновлення" -#: selfdrive/ui/layouts/home.py:169 +#: openpilot/selfdrive/ui/layouts/home.py:169 #, python-format msgid "{} ALERT" msgid_plural "{} ALERTS" @@ -1209,7 +996,7 @@ msgstr[0] "{} СПОВІЩЕННЯ" msgstr[1] "{} СПОВІЩЕННЯ" msgstr[2] "{} СПОВІЩЕНЬ" -#: selfdrive/ui/layouts/settings/software.py:40 +#: openpilot/selfdrive/ui/layouts/settings/software.py:47 #, python-format msgid "{} day ago" msgid_plural "{} days ago" @@ -1217,7 +1004,7 @@ msgstr[0] "{} день тому" msgstr[1] "{} дні тому" msgstr[2] "{} днів тому" -#: selfdrive/ui/layouts/settings/software.py:37 +#: openpilot/selfdrive/ui/layouts/settings/software.py:44 #, python-format msgid "{} hour ago" msgid_plural "{} hours ago" @@ -1225,7 +1012,7 @@ msgstr[0] "{} година тому" msgstr[1] "{} години тому" msgstr[2] "{} годин тому" -#: selfdrive/ui/layouts/settings/software.py:34 +#: openpilot/selfdrive/ui/layouts/settings/software.py:41 #, python-format msgid "{} minute ago" msgid_plural "{} minutes ago" @@ -1233,26 +1020,21 @@ msgstr[0] "{} хвилина тому" msgstr[1] "{} хвилини тому" msgstr[2] "{} хвилин тому" -#: selfdrive/ui/layouts/settings/firehose.py:111 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:70 #, python-format msgid "{} segment of your driving is in the training dataset so far." msgid_plural "{} segments of your driving is in the training dataset so far." -msgstr[0] "" -"{} сегмент вашого водіння на даний момент містяться в тренувальному наборі " -"даних." -msgstr[1] "" -"{} сегменти вашого водіння на даний момент містяться в тренувальному наборі " -"даних." -msgstr[2] "" -"{} сегментів вашого водіння на даний момент містяться в тренувальному наборі " -"даних." +msgstr[0] "{} сегмент вашого водіння на даний момент містяться в тренувальному наборі даних." +msgstr[1] "{} сегменти вашого водіння на даний момент містяться в тренувальному наборі даних." +msgstr[2] "{} сегментів вашого водіння на даний момент містяться в тренувальному наборі даних." -#: selfdrive/ui/widgets/prime.py:62 +#: openpilot/selfdrive/ui/widgets/prime.py:62 #, python-format msgid "✓ SUBSCRIBED" msgstr "✓ ПІДПИСАНО" -#: selfdrive/ui/widgets/setup.py:22 +#: openpilot/selfdrive/ui/widgets/setup.py:21 #, python-format msgid "🔥 Firehose Mode 🔥" msgstr "🌧️ Режим зливи 🌧️" + diff --git a/selfdrive/ui/translations/app_zh-CHS.po b/selfdrive/ui/translations/app_zh-CHS.po index 2400b6f44a..4d9a5b78e2 100644 --- a/selfdrive/ui/translations/app_zh-CHS.po +++ b/selfdrive/ui/translations/app_zh-CHS.po @@ -17,1158 +17,1018 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=1; plural=0;\n" -#: selfdrive/ui/layouts/settings/device.py:160 +#: openpilot/selfdrive/ui/layouts/settings/device.py:152 #, python-format msgid " Steering torque response calibration is complete." msgstr " 转向扭矩响应校准完成。" -#: selfdrive/ui/layouts/settings/device.py:158 +#: openpilot/selfdrive/ui/layouts/settings/device.py:150 #, python-format msgid " Steering torque response calibration is {}% complete." msgstr " 转向扭矩响应校准已完成 {}%。" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid " Your device is pointed {:.1f}° {} and {:.1f}° {}." msgstr " 您的设备朝向 {:.1f}° {} 与 {:.1f}° {}。" -#: selfdrive/ui/layouts/sidebar.py:43 +#: openpilot/selfdrive/ui/layouts/sidebar.py:43 msgid "--" msgstr "--" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "1 year of drive storage" msgstr "1 年行驶数据存储" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "24/7 LTE connectivity" msgstr "全天候 LTE 连接" -#: selfdrive/ui/layouts/sidebar.py:46 +#: openpilot/selfdrive/ui/layouts/sidebar.py:46 msgid "2G" msgstr "2G" -#: selfdrive/ui/layouts/sidebar.py:47 +#: openpilot/selfdrive/ui/layouts/sidebar.py:47 msgid "3G" msgstr "3G" -#: selfdrive/ui/layouts/sidebar.py:49 +#: openpilot/selfdrive/ui/layouts/sidebar.py:49 msgid "5G" msgstr "5G" -#: selfdrive/ui/layouts/settings/developer.py:23 -msgid "" -"WARNING: openpilot longitudinal control is in alpha for this car and will " -"disable Automatic Emergency Braking (AEB).

On this car, openpilot " -"defaults to the car's built-in ACC instead of openpilot's longitudinal " -"control. Enable this to switch to openpilot longitudinal control. Enabling " -"Experimental mode is recommended when enabling openpilot longitudinal " -"control alpha. Changing this setting will restart openpilot if the car is " -"powered on." -msgstr "" -"警告:此车型的 openpilot 纵向控制仍为 alpha,将会停用自动紧急制动 (AEB)。" -"

在此车型上,openpilot 默认使用车载 ACC,而非 openpilot 的纵向控" -"制。启用此选项可切换为 openpilot 纵向控制。建议同时启用实验模式。若车辆通电," -"更改此设置将会重启 openpilot。" - -#: selfdrive/ui/layouts/settings/device.py:148 +#: openpilot/selfdrive/ui/layouts/settings/device.py:140 #, python-format msgid "

Steering lag calibration is complete." msgstr "

转向延迟校准完成。" -#: selfdrive/ui/layouts/settings/device.py:146 +#: openpilot/selfdrive/ui/layouts/settings/device.py:138 #, python-format msgid "

Steering lag calibration is {}% complete." msgstr "

转向延迟校准已完成 {}%。" -#: selfdrive/ui/layouts/settings/firehose.py:138 -#, python-format -msgid "ACTIVE" -msgstr "已启用" - -#: selfdrive/ui/layouts/settings/developer.py:15 -msgid "" -"ADB (Android Debug Bridge) allows connecting to your device over USB or over " -"the network. See https://docs.comma.ai/how-to/connect-to-comma for more info." -msgstr "" -"ADB(Android 调试桥)可通过 USB 或网络连接到您的设备。详见 https://docs." -"comma.ai/how-to/connect-to-comma。" - -#: selfdrive/ui/widgets/ssh_key.py:30 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:30 msgid "ADD" msgstr "添加" -#: system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:136 #, python-format msgid "APN Setting" msgstr "APN 设置" -#: selfdrive/ui/widgets/offroad_alerts.py:109 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:109 #, python-format msgid "Acknowledge Excessive Actuation" msgstr "确认过度作动" -#: system/ui/widgets/network.py:74 system/ui/widgets/network.py:95 +#: system/ui/widgets/network.py:92 +#: system/ui/widgets/network.py:74 #, python-format msgid "Advanced" msgstr "高级" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Aggressive" msgstr "激进" -#: selfdrive/ui/layouts/onboarding.py:116 +#: openpilot/selfdrive/ui/layouts/onboarding.py:120 #, python-format msgid "Agree" msgstr "同意" -#: selfdrive/ui/layouts/settings/toggles.py:70 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:70 #, python-format msgid "Always-On Driver Monitoring" msgstr "始终启用驾驶员监控" -#: selfdrive/ui/layouts/settings/toggles.py:186 -#, python-format -msgid "" -"An alpha version of openpilot longitudinal control can be tested, along with " -"Experimental mode, on non-release branches." -msgstr "openpilot 纵向控制的 alpha 版本可在非发布分支搭配实验模式进行测试。" - -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 #, python-format msgid "Are you sure you want to power off?" msgstr "确定要关机吗?" -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 #, python-format msgid "Are you sure you want to reboot?" msgstr "确定要重启吗?" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Are you sure you want to reset calibration?" msgstr "确定要重置校准吗?" -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 #, python-format msgid "Are you sure you want to uninstall?" msgstr "确定要卸载吗?" -#: system/ui/widgets/network.py:99 selfdrive/ui/layouts/onboarding.py:147 +#: system/ui/widgets/network.py:96 +#: openpilot/selfdrive/ui/layouts/onboarding.py:151 #, python-format msgid "Back" msgstr "返回" -#: selfdrive/ui/widgets/prime.py:38 +#: openpilot/selfdrive/ui/widgets/prime.py:38 #, python-format msgid "Become a comma prime member at connect.comma.ai" msgstr "前往 connect.comma.ai 成为 comma prime 会员" -#: selfdrive/ui/widgets/pairing_dialog.py:130 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:119 #, python-format msgid "Bookmark connect.comma.ai to your home screen to use it like an app" msgstr "将 connect.comma.ai 添加到主屏幕,像应用一样使用" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "CHANGE" msgstr "更改" -#: selfdrive/ui/layouts/settings/software.py:50 -#: selfdrive/ui/layouts/settings/software.py:107 -#: selfdrive/ui/layouts/settings/software.py:118 -#: selfdrive/ui/layouts/settings/software.py:147 +#: openpilot/selfdrive/ui/layouts/settings/software.py:157 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 +#: openpilot/selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:128 #, python-format msgid "CHECK" msgstr "检查" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "CHILL MODE ON" msgstr "安稳模式已开启" -#: system/ui/widgets/network.py:155 selfdrive/ui/layouts/sidebar.py:73 -#: selfdrive/ui/layouts/sidebar.py:134 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:138 +#: system/ui/widgets/network.py:152 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 #, python-format msgid "CONNECT" msgstr "CONNECT" -#: system/ui/widgets/network.py:369 +#: system/ui/widgets/network.py:376 #, python-format msgid "CONNECTING..." msgstr "连接中..." -#: system/ui/widgets/confirm_dialog.py:23 system/ui/widgets/option_dialog.py:35 -#: system/ui/widgets/keyboard.py:81 system/ui/widgets/network.py:318 +#: system/ui/widgets/network.py:326 +#: system/ui/widgets/confirm_dialog.py:24 +#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/keyboard.py:83 #, python-format msgid "Cancel" msgstr "取消" -#: system/ui/widgets/network.py:134 +#: system/ui/widgets/network.py:131 #, python-format msgid "Cellular Metered" msgstr "蜂窝计量" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "Change Language" msgstr "更改语言" -#: selfdrive/ui/layouts/settings/toggles.py:125 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:125 #, python-format msgid "Changing this setting will restart openpilot if the car is powered on." msgstr "若车辆通电,更改此设置将重启 openpilot。" -#: selfdrive/ui/widgets/pairing_dialog.py:129 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:118 #, python-format msgid "Click \"add new device\" and scan the QR code on the right" msgstr "点击“添加新设备”,扫描右侧二维码" -#: selfdrive/ui/widgets/offroad_alerts.py:104 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:104 #, python-format msgid "Close" msgstr "关闭" -#: selfdrive/ui/layouts/settings/software.py:49 +#: openpilot/selfdrive/ui/layouts/settings/software.py:56 #, python-format msgid "Current Version" msgstr "当前版本" -#: selfdrive/ui/layouts/settings/software.py:110 +#: openpilot/selfdrive/ui/layouts/settings/software.py:120 #, python-format msgid "DOWNLOAD" msgstr "下载" -#: selfdrive/ui/layouts/onboarding.py:115 +#: openpilot/selfdrive/ui/layouts/onboarding.py:119 #, python-format msgid "Decline" msgstr "拒绝" -#: selfdrive/ui/layouts/onboarding.py:148 +#: openpilot/selfdrive/ui/layouts/onboarding.py:152 #, python-format msgid "Decline, uninstall openpilot" msgstr "拒绝并卸载 openpilot" -#: selfdrive/ui/layouts/settings/settings.py:67 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:64 msgid "Developer" msgstr "开发者" -#: selfdrive/ui/layouts/settings/settings.py:62 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:59 msgid "Device" msgstr "设备" -#: selfdrive/ui/layouts/settings/toggles.py:58 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:58 #, python-format msgid "Disengage on Accelerator Pedal" msgstr "踩下加速踏板时脱离" -#: selfdrive/ui/layouts/settings/device.py:184 +#: openpilot/selfdrive/ui/layouts/settings/device.py:176 #, python-format msgid "Disengage to Power Off" msgstr "脱离以关机" -#: selfdrive/ui/layouts/settings/device.py:172 +#: openpilot/selfdrive/ui/layouts/settings/device.py:164 #, python-format msgid "Disengage to Reboot" msgstr "脱离以重启" -#: selfdrive/ui/layouts/settings/device.py:103 +#: openpilot/selfdrive/ui/layouts/settings/device.py:95 #, python-format msgid "Disengage to Reset Calibration" msgstr "脱离以重置校准" -#: selfdrive/ui/layouts/settings/toggles.py:32 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:32 msgid "Display speed in km/h instead of mph." msgstr "以 km/h 显示速度(非 mph)。" -#: selfdrive/ui/layouts/settings/device.py:59 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 #, python-format msgid "Dongle ID" msgstr "Dongle ID" -#: selfdrive/ui/layouts/settings/software.py:50 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 #, python-format msgid "Download" msgstr "下载" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "Driver Camera" msgstr "车内摄像头" -#: selfdrive/ui/layouts/settings/toggles.py:96 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:96 #, python-format msgid "Driving Personality" msgstr "驾驶风格" -#: system/ui/widgets/network.py:123 system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:136 #, python-format msgid "EDIT" msgstr "编辑" -#: selfdrive/ui/layouts/sidebar.py:138 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 msgid "ERROR" msgstr "错误" -#: selfdrive/ui/layouts/sidebar.py:45 +#: openpilot/selfdrive/ui/layouts/sidebar.py:45 msgid "ETH" msgstr "ETH" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "EXPERIMENTAL MODE ON" msgstr "实验模式已开启" -#: selfdrive/ui/layouts/settings/developer.py:166 -#: selfdrive/ui/layouts/settings/toggles.py:228 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:229 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:180 #, python-format msgid "Enable" msgstr "启用" -#: selfdrive/ui/layouts/settings/developer.py:39 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:39 #, python-format msgid "Enable ADB" msgstr "启用 ADB" -#: selfdrive/ui/layouts/settings/toggles.py:64 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:64 #, python-format msgid "Enable Lane Departure Warnings" msgstr "启用车道偏离警示" -#: system/ui/widgets/network.py:129 +#: system/ui/widgets/network.py:126 #, python-format msgid "Enable Roaming" msgstr "启用漫游" -#: selfdrive/ui/layouts/settings/developer.py:48 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:48 #, python-format msgid "Enable SSH" msgstr "启用 SSH" -#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:117 #, python-format msgid "Enable Tethering" msgstr "启用网络共享" -#: selfdrive/ui/layouts/settings/toggles.py:30 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:30 msgid "Enable driver monitoring even when openpilot is not engaged." msgstr "即使未启用 openpilot 也启用驾驶员监控。" -#: selfdrive/ui/layouts/settings/toggles.py:46 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:46 #, python-format msgid "Enable openpilot" msgstr "启用 openpilot" -#: selfdrive/ui/layouts/settings/toggles.py:189 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:190 #, python-format -msgid "" -"Enable the openpilot longitudinal control (alpha) toggle to allow " -"Experimental mode." +msgid "Enable the openpilot longitudinal control (alpha) toggle to allow Experimental mode." msgstr "启用 openpilot 纵向控制(alpha)开关,以使用实验模式。" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "Enter APN" msgstr "输入 APN" -#: system/ui/widgets/network.py:241 +#: system/ui/widgets/network.py:243 #, python-format msgid "Enter SSID" msgstr "输入 SSID" -#: system/ui/widgets/network.py:254 +#: system/ui/widgets/network.py:257 #, python-format msgid "Enter new tethering password" msgstr "输入新的网络共享密码" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:320 #, python-format msgid "Enter password" msgstr "输入密码" -#: selfdrive/ui/widgets/ssh_key.py:89 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:89 #, python-format msgid "Enter your GitHub username" msgstr "输入您的 GitHub 用户名" -#: system/ui/widgets/list_view.py:123 system/ui/widgets/list_view.py:160 +#: system/ui/widgets/list_view.py:123 +#: system/ui/widgets/list_view.py:160 #, python-format msgid "Error" msgstr "错误" -#: selfdrive/ui/layouts/settings/toggles.py:52 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:52 #, python-format msgid "Experimental Mode" msgstr "实验模式" -#: selfdrive/ui/layouts/settings/toggles.py:181 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:182 #, python-format -msgid "" -"Experimental mode is currently unavailable on this car since the car's stock " -"ACC is used for longitudinal control." +msgid "Experimental mode is currently unavailable on this car since the car's stock ACC is used for longitudinal control." msgstr "此车型当前无法使用实验模式,因为纵向控制使用的是原厂 ACC。" -#: system/ui/widgets/network.py:373 +#: system/ui/widgets/network.py:380 #, python-format msgid "FORGETTING..." msgstr "正在遗忘..." -#: selfdrive/ui/widgets/setup.py:44 +#: openpilot/selfdrive/ui/widgets/setup.py:43 #, python-format msgid "Finish Setup" msgstr "完成设置" -#: selfdrive/ui/layouts/settings/settings.py:66 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:63 msgid "Firehose" msgstr "Firehose" -#: selfdrive/ui/layouts/settings/firehose.py:18 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:10 msgid "Firehose Mode" msgstr "Firehose 模式" -#: selfdrive/ui/layouts/settings/firehose.py:25 -msgid "" -"For maximum effectiveness, bring your device inside and connect to a good " -"USB-C adapter and Wi-Fi weekly.\n" -"\n" -"Firehose Mode can also work while you're driving if connected to a hotspot " -"or unlimited SIM card.\n" -"\n" -"\n" -"Frequently Asked Questions\n" -"\n" -"Does it matter how or where I drive? Nope, just drive as you normally " -"would.\n" -"\n" -"Do all of my segments get pulled in Firehose Mode? No, we selectively pull a " -"subset of your segments.\n" -"\n" -"What's a good USB-C adapter? Any fast phone or laptop charger should be " -"fine.\n" -"\n" -"Does it matter which software I run? Yes, only upstream openpilot (and " -"particular forks) are able to be used for training." -msgstr "" -"为达到最佳效果,请将设备带到室内,并每周连接优质 USB‑C 充电器与 Wi‑Fi。\n" -"\n" -"若连接热点或不限流量卡,行车中也可使用 Firehose 模式。\n" -"\n" -"\n" -"常见问题\n" -"\n" -"我怎么开、在哪开有区别吗?没有,平常怎么开就怎么开。\n" -"\n" -"Firehose 模式会拉取我所有片段吗?不会,我们会选择性拉取部分片段。\n" -"\n" -"什么是好的 USB‑C 充电器?任何快速的手机或笔电充电器都可以。\n" -"\n" -"我跑什么软件有区别吗?有,只有上游 openpilot(及特定分支)可用于训练。" - -#: system/ui/widgets/network.py:318 system/ui/widgets/network.py:451 +#: system/ui/widgets/network.py:458 +#: system/ui/widgets/network.py:326 #, python-format msgid "Forget" msgstr "忘记" -#: system/ui/widgets/network.py:319 +#: system/ui/widgets/network.py:327 #, python-format msgid "Forget Wi-Fi Network \"{}\"?" msgstr "要忘记 Wi‑Fi 网络“{}”吗?" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 msgid "GOOD" msgstr "良好" -#: selfdrive/ui/widgets/pairing_dialog.py:128 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:117 #, python-format msgid "Go to https://connect.comma.ai on your phone" msgstr "在手机上前往 https://connect.comma.ai" -#: selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "HIGH" msgstr "高" -#: system/ui/widgets/network.py:155 +#: system/ui/widgets/network.py:152 #, python-format msgid "Hidden Network" msgstr "隐藏网络" -#: selfdrive/ui/layouts/settings/firehose.py:140 -#, python-format -msgid "INACTIVE: connect to an unmetered network" -msgstr "未启用:请连接不限流量网络" - -#: selfdrive/ui/layouts/settings/software.py:53 -#: selfdrive/ui/layouts/settings/software.py:136 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 +#: openpilot/selfdrive/ui/layouts/settings/software.py:146 #, python-format msgid "INSTALL" msgstr "安装" -#: system/ui/widgets/network.py:150 +#: system/ui/widgets/network.py:147 #, python-format msgid "IP Address" msgstr "IP 地址" -#: selfdrive/ui/layouts/settings/software.py:53 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 #, python-format msgid "Install Update" msgstr "安装更新" -#: selfdrive/ui/layouts/settings/developer.py:56 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:56 #, python-format msgid "Joystick Debug Mode" msgstr "摇杆调试模式" -#: selfdrive/ui/widgets/ssh_key.py:29 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:29 msgid "LOADING" msgstr "加载中" -#: selfdrive/ui/layouts/sidebar.py:48 +#: openpilot/selfdrive/ui/layouts/sidebar.py:48 msgid "LTE" msgstr "LTE" -#: selfdrive/ui/layouts/settings/developer.py:64 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:64 #, python-format msgid "Longitudinal Maneuver Mode" msgstr "纵向操作模式" -#: selfdrive/ui/onroad/hud_renderer.py:148 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:148 #, python-format msgid "MAX" msgstr "最大" -#: selfdrive/ui/widgets/setup.py:75 +#: openpilot/selfdrive/ui/widgets/setup.py:74 #, python-format -msgid "" -"Maximize your training data uploads to improve openpilot's driving models." +msgid "Maximize your training data uploads to improve openpilot's driving models." msgstr "最大化上传训练数据,以改进 openpilot 的驾驶模型。" -#: selfdrive/ui/layouts/settings/device.py:59 -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "N/A" msgstr "无" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "NO" msgstr "否" -#: selfdrive/ui/layouts/settings/settings.py:63 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:60 msgid "Network" msgstr "网络" -#: selfdrive/ui/widgets/ssh_key.py:114 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:115 #, python-format msgid "No SSH keys found" msgstr "未找到 SSH 密钥" -#: selfdrive/ui/widgets/ssh_key.py:126 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:127 #, python-format msgid "No SSH keys found for user '{}'" msgstr "未找到用户“{}”的 SSH 密钥" -#: selfdrive/ui/widgets/offroad_alerts.py:320 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:321 #, python-format msgid "No release notes available." msgstr "暂无发行说明。" -#: selfdrive/ui/layouts/sidebar.py:73 selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 msgid "OFFLINE" msgstr "离线" -#: system/ui/widgets/html_render.py:263 system/ui/widgets/confirm_dialog.py:93 -#: selfdrive/ui/layouts/sidebar.py:127 +#: system/ui/widgets/confirm_dialog.py:93 +#: system/ui/widgets/html_render.py:263 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 #, python-format msgid "OK" msgstr "确定" -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 msgid "ONLINE" msgstr "在线" -#: selfdrive/ui/widgets/setup.py:20 +#: openpilot/selfdrive/ui/widgets/setup.py:19 #, python-format msgid "Open" msgstr "打开" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "PAIR" msgstr "配对" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "PANDA" msgstr "PANDA" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "PREVIEW" msgstr "预览" -#: selfdrive/ui/widgets/prime.py:44 +#: openpilot/selfdrive/ui/widgets/prime.py:44 #, python-format msgid "PRIME FEATURES:" msgstr "PRIME 功能:" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "Pair Device" msgstr "配对设备" -#: selfdrive/ui/widgets/setup.py:19 +#: openpilot/selfdrive/ui/widgets/setup.py:18 #, python-format msgid "Pair device" msgstr "配对设备" -#: selfdrive/ui/widgets/pairing_dialog.py:103 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:92 #, python-format msgid "Pair your device to your comma account" msgstr "将设备配对到您的 comma 账号" -#: selfdrive/ui/widgets/setup.py:48 selfdrive/ui/layouts/settings/device.py:24 +#: openpilot/selfdrive/ui/widgets/setup.py:47 +#: openpilot/selfdrive/ui/layouts/settings/device.py:23 #, python-format -msgid "" -"Pair your device with comma connect (connect.comma.ai) and claim your comma " -"prime offer." -msgstr "" -"将设备与 comma connect(connect.comma.ai)配对,领取您的 comma prime 优惠。" +msgid "Pair your device with comma connect (connect.comma.ai) and claim your comma prime offer." +msgstr "将设备与 comma connect(connect.comma.ai)配对,领取您的 comma prime 优惠。" -#: selfdrive/ui/widgets/setup.py:91 +#: openpilot/selfdrive/ui/widgets/setup.py:91 #, python-format msgid "Please connect to Wi-Fi to complete initial pairing" msgstr "请连接 Wi‑Fi 以完成初始配对" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Power Off" msgstr "关机" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Prevent large data uploads when on a metered Wi-Fi connection" msgstr "在计量制 Wi‑Fi 连接时避免大量上传" -#: system/ui/widgets/network.py:135 +#: system/ui/widgets/network.py:132 #, python-format msgid "Prevent large data uploads when on a metered cellular connection" msgstr "在计量制蜂窝网络时避免大量上传" -#: selfdrive/ui/layouts/settings/device.py:25 -msgid "" -"Preview the driver facing camera to ensure that driver monitoring has good " -"visibility. (vehicle must be off)" +#: openpilot/selfdrive/ui/layouts/settings/device.py:24 +msgid "Preview the driver facing camera to ensure that driver monitoring has good visibility. (vehicle must be off)" msgstr "预览车内摄像头以确保驾驶员监控视野良好。(车辆必须熄火)" -#: selfdrive/ui/widgets/pairing_dialog.py:161 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:150 #, python-format msgid "QR Code Error" msgstr "二维码错误" -#: selfdrive/ui/widgets/ssh_key.py:31 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:31 msgid "REMOVE" msgstr "移除" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "RESET" msgstr "重置" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "REVIEW" msgstr "查看" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Reboot" msgstr "重启" -#: selfdrive/ui/onroad/alert_renderer.py:66 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:66 #, python-format msgid "Reboot Device" msgstr "重启设备" -#: selfdrive/ui/widgets/offroad_alerts.py:112 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:112 #, python-format msgid "Reboot and Update" msgstr "重启并更新" -#: selfdrive/ui/layouts/settings/toggles.py:27 -msgid "" -"Receive alerts to steer back into the lane when your vehicle drifts over a " -"detected lane line without a turn signal activated while driving over 31 mph " -"(50 km/h)." -msgstr "" -"当车辆以超过 31 mph(50 km/h)行驶且未打转向灯越过检测到的车道线时,接收引导" -"回车道的警报。" - -#: selfdrive/ui/layouts/settings/toggles.py:76 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:76 #, python-format msgid "Record and Upload Driver Camera" msgstr "录制并上传车内摄像头" -#: selfdrive/ui/layouts/settings/toggles.py:82 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:82 #, python-format msgid "Record and Upload Microphone Audio" msgstr "录制并上传麦克风音频" -#: selfdrive/ui/layouts/settings/toggles.py:33 -msgid "" -"Record and store microphone audio while driving. The audio will be included " -"in the dashcam video in comma connect." -msgstr "" -"行驶时录制并保存麦克风音频。音频将包含在 comma connect 的行车记录视频中。" +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:33 +msgid "Record and store microphone audio while driving. The audio will be included in the dashcam video in comma connect." +msgstr "行驶时录制并保存麦克风音频。音频将包含在 comma connect 的行车记录视频中。" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "Regulatory" msgstr "法规" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Relaxed" msgstr "从容" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote access" msgstr "远程访问" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote snapshots" msgstr "远程快照" -#: selfdrive/ui/widgets/ssh_key.py:123 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:124 #, python-format msgid "Request timed out" msgstr "请求超时" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Reset" msgstr "重置" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "Reset Calibration" msgstr "重置校准" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "Review Training Guide" msgstr "查看训练指南" -#: selfdrive/ui/layouts/settings/device.py:27 +#: openpilot/selfdrive/ui/layouts/settings/device.py:26 msgid "Review the rules, features, and limitations of openpilot" msgstr "查看 openpilot 的规则、功能与限制" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "SELECT" msgstr "选择" -#: selfdrive/ui/layouts/settings/developer.py:53 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:53 #, python-format msgid "SSH Keys" msgstr "SSH 密钥" -#: system/ui/widgets/network.py:310 +#: system/ui/widgets/network.py:316 #, python-format msgid "Scanning Wi-Fi networks..." msgstr "正在扫描 Wi‑Fi 网络…" -#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/option_dialog.py:37 #, python-format msgid "Select" msgstr "选择" -#: selfdrive/ui/layouts/settings/software.py:183 +#: openpilot/selfdrive/ui/layouts/settings/software.py:203 #, python-format msgid "Select a branch" msgstr "选择分支" -#: selfdrive/ui/layouts/settings/device.py:91 +#: openpilot/selfdrive/ui/layouts/settings/device.py:89 #, python-format msgid "Select a language" msgstr "选择语言" -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "Serial" msgstr "序列号" -#: selfdrive/ui/widgets/offroad_alerts.py:106 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:106 #, python-format msgid "Snooze Update" msgstr "延后更新" -#: selfdrive/ui/layouts/settings/settings.py:65 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:62 msgid "Software" msgstr "软件" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Standard" msgstr "标准" -#: selfdrive/ui/layouts/settings/toggles.py:22 -msgid "" -"Standard is recommended. In aggressive mode, openpilot will follow lead cars " -"closer and be more aggressive with the gas and brake. In relaxed mode " -"openpilot will stay further away from lead cars. On supported cars, you can " -"cycle through these personalities with your steering wheel distance button." -msgstr "" -"建议使用标准模式。激进模式下,openpilot 会更贴近前车,油门与刹车更为激进;从" -"容模式下,会与前车保持更远距离。在支持的车型上,可用方向盘距离按钮切换这些风" -"格。" - -#: selfdrive/ui/onroad/alert_renderer.py:59 -#: selfdrive/ui/onroad/alert_renderer.py:65 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:59 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:65 #, python-format msgid "System Unresponsive" msgstr "系统无响应" -#: selfdrive/ui/onroad/alert_renderer.py:58 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:58 #, python-format msgid "TAKE CONTROL IMMEDIATELY" msgstr "请立即接管控制" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 -#: selfdrive/ui/layouts/sidebar.py:127 selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "TEMP" msgstr "温度" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "Target Branch" msgstr "目标分支" -#: system/ui/widgets/network.py:124 +#: system/ui/widgets/network.py:121 #, python-format msgid "Tethering Password" msgstr "网络共享密码" -#: selfdrive/ui/layouts/settings/settings.py:64 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:61 msgid "Toggles" msgstr "切换" -#: selfdrive/ui/layouts/settings/software.py:72 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:79 +#, python-format +msgid "UI Debug Mode" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "UNINSTALL" msgstr "卸载" -#: selfdrive/ui/layouts/home.py:155 +#: openpilot/selfdrive/ui/layouts/home.py:155 #, python-format msgid "UPDATE" msgstr "更新" -#: selfdrive/ui/layouts/settings/software.py:72 -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "Uninstall" msgstr "卸载" -#: selfdrive/ui/layouts/sidebar.py:117 +#: openpilot/selfdrive/ui/layouts/sidebar.py:117 msgid "Unknown" msgstr "未知" -#: selfdrive/ui/layouts/settings/software.py:48 +#: openpilot/selfdrive/ui/layouts/settings/software.py:55 #, python-format msgid "Updates are only downloaded while the car is off." msgstr "仅在车辆熄火时下载更新。" -#: selfdrive/ui/widgets/prime.py:33 +#: openpilot/selfdrive/ui/widgets/prime.py:33 #, python-format msgid "Upgrade Now" msgstr "立即升级" -#: selfdrive/ui/layouts/settings/toggles.py:31 -msgid "" -"Upload data from the driver facing camera and help improve the driver " -"monitoring algorithm." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:31 +msgid "Upload data from the driver facing camera and help improve the driver monitoring algorithm." msgstr "上传车内摄像头数据,帮助改进驾驶员监控算法。" -#: selfdrive/ui/layouts/settings/toggles.py:88 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:88 #, python-format msgid "Use Metric System" msgstr "使用公制" -#: selfdrive/ui/layouts/settings/toggles.py:17 -msgid "" -"Use the openpilot system for adaptive cruise control and lane keep driver " -"assistance. Your attention is required at all times to use this feature." -msgstr "" -"使用 openpilot 进行自适应巡航与车道保持辅助。使用此功能时,您必须始终保持专" -"注。" - -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 msgid "VEHICLE" msgstr "车辆" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "VIEW" msgstr "查看" -#: selfdrive/ui/onroad/alert_renderer.py:52 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:52 #, python-format msgid "Waiting to start" msgstr "等待开始" -#: selfdrive/ui/layouts/settings/developer.py:19 -msgid "" -"Warning: This grants SSH access to all public keys in your GitHub settings. " -"Never enter a GitHub username other than your own. A comma employee will " -"NEVER ask you to add their GitHub username." -msgstr "" -"警告:这将授予对您 GitHub 设置中所有公钥的 SSH 访问权限。请勿输入非您本人的 " -"GitHub 用户名。comma 员工绝不会要求您添加他们的用户名。" - -#: selfdrive/ui/layouts/onboarding.py:111 +#: openpilot/selfdrive/ui/layouts/onboarding.py:115 #, python-format msgid "Welcome to openpilot" msgstr "欢迎使用 openpilot" -#: selfdrive/ui/layouts/settings/toggles.py:20 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:20 msgid "When enabled, pressing the accelerator pedal will disengage openpilot." msgstr "启用后,踩下加速踏板将会脱离 openpilot。" -#: selfdrive/ui/layouts/sidebar.py:44 +#: openpilot/selfdrive/ui/layouts/sidebar.py:44 msgid "Wi-Fi" msgstr "Wi‑Fi" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Wi-Fi Network Metered" msgstr "Wi‑Fi 计量网络" -#: system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:320 #, python-format msgid "Wrong password" msgstr "密码错误" -#: selfdrive/ui/layouts/onboarding.py:145 +#: openpilot/selfdrive/ui/layouts/onboarding.py:149 #, python-format msgid "You must accept the Terms and Conditions in order to use openpilot." msgstr "您必须接受条款与条件才能使用 openpilot。" -#: selfdrive/ui/layouts/onboarding.py:112 +#: openpilot/selfdrive/ui/layouts/onboarding.py:116 #, python-format -msgid "" -"You must accept the Terms and Conditions to use openpilot. Read the latest " -"terms at https://comma.ai/terms before continuing." -msgstr "" -"您必须接受条款与条件才能使用 openpilot。继续前请阅读 https://comma.ai/terms " -"上的最新条款。" +msgid "You must accept the Terms and Conditions to use openpilot. Read the latest terms at https://comma.ai/terms before continuing." +msgstr "您必须接受条款与条件才能使用 openpilot。继续前请阅读 https://comma.ai/terms 上的最新条款。" -#: selfdrive/ui/onroad/driver_camera_dialog.py:34 +#: openpilot/selfdrive/ui/onroad/driver_camera_dialog.py:38 #, python-format msgid "camera starting" msgstr "相机启动中" -#: selfdrive/ui/widgets/prime.py:63 +#: openpilot/selfdrive/ui/layouts/settings/software.py:19 +#, python-format +msgid "checking..." +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:63 #, python-format msgid "comma prime" msgstr "comma prime" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "default" msgstr "默认" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "down" msgstr "下" -#: selfdrive/ui/layouts/settings/software.py:106 +#: openpilot/selfdrive/ui/layouts/settings/software.py:20 +#, python-format +msgid "downloading..." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:116 #, python-format msgid "failed to check for update" msgstr "检查更新失败" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: openpilot/selfdrive/ui/layouts/settings/software.py:21 +#, python-format +msgid "finalizing update..." +msgstr "" + +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:321 #, python-format msgid "for \"{}\"" msgstr "用于“{}”" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "km/h" msgstr "km/h" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "leave blank for automatic configuration" msgstr "留空以自动配置" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "left" msgstr "左" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "metered" msgstr "计量" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "mph" msgstr "mph" -#: selfdrive/ui/layouts/settings/software.py:20 +#: openpilot/selfdrive/ui/layouts/settings/software.py:27 #, python-format msgid "never" msgstr "从不" -#: selfdrive/ui/layouts/settings/software.py:31 +#: openpilot/selfdrive/ui/layouts/settings/software.py:38 #, python-format msgid "now" msgstr "现在" -#: selfdrive/ui/layouts/settings/developer.py:71 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:71 #, python-format msgid "openpilot Longitudinal Control (Alpha)" msgstr "openpilot 纵向控制(Alpha)" -#: selfdrive/ui/onroad/alert_renderer.py:51 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:51 #, python-format msgid "openpilot Unavailable" msgstr "openpilot 无法使用" -#: selfdrive/ui/layouts/settings/toggles.py:158 -#, python-format -msgid "" -"openpilot defaults to driving in chill mode. Experimental mode enables alpha-" -"level features that aren't ready for chill mode. Experimental features are " -"listed below:

End-to-End Longitudinal Control


Let the driving " -"model control the gas and brakes. openpilot will drive as it thinks a human " -"would, including stopping for red lights and stop signs. Since the driving " -"model decides the speed to drive, the set speed will only act as an upper " -"bound. This is an alpha quality feature; mistakes should be expected." -"

New Driving Visualization


The driving visualization will " -"transition to the road-facing wide-angle camera at low speeds to better show " -"some turns. The Experimental mode logo will also be shown in the top right " -"corner." -msgstr "" -"openpilot 默认以安稳模式行驶。实验模式会启用尚未准备好用于安稳模式的 Alpha 级" -"功能。实验功能如下:

端到端纵向控制


让驾驶模型控制油门与刹车。" -"openpilot 会像人类一样驾驶,包括在红灯与停牌前停车。由于驾驶模型决定行驶速" -"度,设定速度仅作为上限。这是 Alpha 质量功能;预期会有错误。

全新驾驶可" -"视化


在低速时,驾驶可视化将切换至面向道路的广角摄像头以更好显示部分转" -"弯。右上角也会显示实验模式图标。" - -#: selfdrive/ui/layouts/settings/device.py:165 -#, python-format -msgid "" -"openpilot is continuously calibrating, resetting is rarely required. " -"Resetting calibration will restart openpilot if the car is powered on." -msgstr "" -"openpilot 持续进行校准,通常无需重置。若车辆通电,重置校准将会重启 " -"openpilot。" - -#: selfdrive/ui/layouts/settings/firehose.py:20 -msgid "" -"openpilot learns to drive by watching humans, like you, drive.\n" -"\n" -"Firehose Mode allows you to maximize your training data uploads to improve " -"openpilot's driving models. More data means bigger models, which means " -"better Experimental Mode." -msgstr "" -"openpilot 通过观察人类(例如您)的驾驶来学习。\n" -"\n" -"Firehose 模式可让您最大化上传训练数据,以改进 openpilot 的驾驶模型。更多数据" -"意味着更大的模型,也意味着更好的实验模式。" - -#: selfdrive/ui/layouts/settings/toggles.py:183 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:184 #, python-format msgid "openpilot longitudinal control may come in a future update." msgstr "openpilot 纵向控制可能会在未来更新中提供。" -#: selfdrive/ui/layouts/settings/device.py:26 -msgid "" -"openpilot requires the device to be mounted within 4° left or right and " -"within 5° up or 9° down." +#: openpilot/selfdrive/ui/layouts/settings/device.py:25 +msgid "openpilot requires the device to be mounted within 4° left or right and within 5° up or 9° down." msgstr "openpilot 要求设备安装在左右 4°、上 5° 或下 9° 以内。" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "right" msgstr "右" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "unmetered" msgstr "不限流量" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "up" msgstr "上" -#: selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:127 #, python-format msgid "up to date, last checked never" msgstr "已是最新,最后检查:从未" -#: selfdrive/ui/layouts/settings/software.py:115 +#: openpilot/selfdrive/ui/layouts/settings/software.py:125 #, python-format msgid "up to date, last checked {}" msgstr "已是最新,最后检查:{}" -#: selfdrive/ui/layouts/settings/software.py:109 +#: openpilot/selfdrive/ui/layouts/settings/software.py:119 #, python-format msgid "update available" msgstr "有可用更新" -#: selfdrive/ui/layouts/home.py:169 +#: openpilot/selfdrive/ui/layouts/home.py:169 #, python-format msgid "{} ALERT" msgid_plural "{} ALERTS" msgstr[0] "{} 条警报" msgstr[1] "{} 条警报" -#: selfdrive/ui/layouts/settings/software.py:40 +#: openpilot/selfdrive/ui/layouts/settings/software.py:47 #, python-format msgid "{} day ago" msgid_plural "{} days ago" msgstr[0] "{} 天前" msgstr[1] "{} 天前" -#: selfdrive/ui/layouts/settings/software.py:37 +#: openpilot/selfdrive/ui/layouts/settings/software.py:44 #, python-format msgid "{} hour ago" msgid_plural "{} hours ago" msgstr[0] "{} 小时前" msgstr[1] "{} 小时前" -#: selfdrive/ui/layouts/settings/software.py:34 +#: openpilot/selfdrive/ui/layouts/settings/software.py:41 #, python-format msgid "{} minute ago" msgid_plural "{} minutes ago" msgstr[0] "{} 分钟前" msgstr[1] "{} 分钟前" -#: selfdrive/ui/layouts/settings/firehose.py:111 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:70 #, python-format msgid "{} segment of your driving is in the training dataset so far." msgid_plural "{} segments of your driving is in the training dataset so far." msgstr[0] "目前已有 {} 个您的驾驶片段被纳入训练数据集。" msgstr[1] "目前已有 {} 个您的驾驶片段被纳入训练数据集。" -#: selfdrive/ui/widgets/prime.py:62 +#: openpilot/selfdrive/ui/widgets/prime.py:62 #, python-format msgid "✓ SUBSCRIBED" msgstr "✓ 已订阅" -#: selfdrive/ui/widgets/setup.py:22 +#: openpilot/selfdrive/ui/widgets/setup.py:21 #, python-format msgid "🔥 Firehose Mode 🔥" msgstr "🔥 Firehose 模式 🔥" + diff --git a/selfdrive/ui/translations/app_zh-CHT.po b/selfdrive/ui/translations/app_zh-CHT.po index f4d5e0a4ed..1c2fd06563 100644 --- a/selfdrive/ui/translations/app_zh-CHT.po +++ b/selfdrive/ui/translations/app_zh-CHT.po @@ -17,1157 +17,1018 @@ msgstr "" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=1; plural=0;\n" -#: selfdrive/ui/layouts/settings/device.py:160 +#: openpilot/selfdrive/ui/layouts/settings/device.py:152 #, python-format msgid " Steering torque response calibration is complete." msgstr " 轉向扭矩回應校正完成。" -#: selfdrive/ui/layouts/settings/device.py:158 +#: openpilot/selfdrive/ui/layouts/settings/device.py:150 #, python-format msgid " Steering torque response calibration is {}% complete." msgstr " 轉向扭矩回應校正已完成 {}%。" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid " Your device is pointed {:.1f}° {} and {:.1f}° {}." msgstr " 您的裝置朝向 {:.1f}° {} 與 {:.1f}° {}。" -#: selfdrive/ui/layouts/sidebar.py:43 +#: openpilot/selfdrive/ui/layouts/sidebar.py:43 msgid "--" msgstr "--" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "1 year of drive storage" msgstr "1 年行駛資料儲存" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "24/7 LTE connectivity" msgstr "全年無休 LTE 連線" -#: selfdrive/ui/layouts/sidebar.py:46 +#: openpilot/selfdrive/ui/layouts/sidebar.py:46 msgid "2G" msgstr "2G" -#: selfdrive/ui/layouts/sidebar.py:47 +#: openpilot/selfdrive/ui/layouts/sidebar.py:47 msgid "3G" msgstr "3G" -#: selfdrive/ui/layouts/sidebar.py:49 +#: openpilot/selfdrive/ui/layouts/sidebar.py:49 msgid "5G" msgstr "5G" -#: selfdrive/ui/layouts/settings/developer.py:23 -msgid "" -"WARNING: openpilot longitudinal control is in alpha for this car and will " -"disable Automatic Emergency Braking (AEB).

On this car, openpilot " -"defaults to the car's built-in ACC instead of openpilot's longitudinal " -"control. Enable this to switch to openpilot longitudinal control. Enabling " -"Experimental mode is recommended when enabling openpilot longitudinal " -"control alpha. Changing this setting will restart openpilot if the car is " -"powered on." -msgstr "" -"警告:此車款的 openpilot 縱向控制仍為 alpha,將會停用自動緊急煞車 (AEB)。" -"

在此車款上,openpilot 預設使用車載 ACC,而非 openpilot 的縱向控" -"制。啟用此選項可切換為 openpilot 縱向控制。建議同時啟用實驗模式。若車輛通電," -"變更此設定將會重新啟動 openpilot。" - -#: selfdrive/ui/layouts/settings/device.py:148 +#: openpilot/selfdrive/ui/layouts/settings/device.py:140 #, python-format msgid "

Steering lag calibration is complete." msgstr "

轉向延遲校正完成。" -#: selfdrive/ui/layouts/settings/device.py:146 +#: openpilot/selfdrive/ui/layouts/settings/device.py:138 #, python-format msgid "

Steering lag calibration is {}% complete." msgstr "

轉向延遲校正已完成 {}%。" -#: selfdrive/ui/layouts/settings/firehose.py:138 -#, python-format -msgid "ACTIVE" -msgstr "啟用" - -#: selfdrive/ui/layouts/settings/developer.py:15 -msgid "" -"ADB (Android Debug Bridge) allows connecting to your device over USB or over " -"the network. See https://docs.comma.ai/how-to/connect-to-comma for more info." -msgstr "" -"ADB (Android Debug Bridge) 可透過 USB 或網路連線至您的裝置。詳見 https://" -"docs.comma.ai/how-to/connect-to-comma。" - -#: selfdrive/ui/widgets/ssh_key.py:30 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:30 msgid "ADD" msgstr "新增" -#: system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:136 #, python-format msgid "APN Setting" msgstr "APN 設定" -#: selfdrive/ui/widgets/offroad_alerts.py:109 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:109 #, python-format msgid "Acknowledge Excessive Actuation" msgstr "確認過度作動" -#: system/ui/widgets/network.py:74 system/ui/widgets/network.py:95 +#: system/ui/widgets/network.py:92 +#: system/ui/widgets/network.py:74 #, python-format msgid "Advanced" msgstr "進階" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Aggressive" msgstr "積極" -#: selfdrive/ui/layouts/onboarding.py:116 +#: openpilot/selfdrive/ui/layouts/onboarding.py:120 #, python-format msgid "Agree" msgstr "同意" -#: selfdrive/ui/layouts/settings/toggles.py:70 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:70 #, python-format msgid "Always-On Driver Monitoring" msgstr "持續啟用駕駛監控" -#: selfdrive/ui/layouts/settings/toggles.py:186 -#, python-format -msgid "" -"An alpha version of openpilot longitudinal control can be tested, along with " -"Experimental mode, on non-release branches." -msgstr "openpilot 縱向控制的 alpha 版本可於非發行分支搭配實驗模式進行測試。" - -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 #, python-format msgid "Are you sure you want to power off?" msgstr "確定要關機嗎?" -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 #, python-format msgid "Are you sure you want to reboot?" msgstr "確定要重新啟動嗎?" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Are you sure you want to reset calibration?" msgstr "確定要重設校正嗎?" -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 #, python-format msgid "Are you sure you want to uninstall?" msgstr "確定要解除安裝嗎?" -#: system/ui/widgets/network.py:99 selfdrive/ui/layouts/onboarding.py:147 +#: system/ui/widgets/network.py:96 +#: openpilot/selfdrive/ui/layouts/onboarding.py:151 #, python-format msgid "Back" msgstr "返回" -#: selfdrive/ui/widgets/prime.py:38 +#: openpilot/selfdrive/ui/widgets/prime.py:38 #, python-format msgid "Become a comma prime member at connect.comma.ai" msgstr "前往 connect.comma.ai 成為 comma prime 會員" -#: selfdrive/ui/widgets/pairing_dialog.py:130 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:119 #, python-format msgid "Bookmark connect.comma.ai to your home screen to use it like an app" msgstr "將 connect.comma.ai 加到主畫面,像 App 一樣使用" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "CHANGE" msgstr "變更" -#: selfdrive/ui/layouts/settings/software.py:50 -#: selfdrive/ui/layouts/settings/software.py:107 -#: selfdrive/ui/layouts/settings/software.py:118 -#: selfdrive/ui/layouts/settings/software.py:147 +#: openpilot/selfdrive/ui/layouts/settings/software.py:157 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 +#: openpilot/selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:128 #, python-format msgid "CHECK" msgstr "檢查" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "CHILL MODE ON" msgstr "安穩模式已開啟" -#: system/ui/widgets/network.py:155 selfdrive/ui/layouts/sidebar.py:73 -#: selfdrive/ui/layouts/sidebar.py:134 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:138 +#: system/ui/widgets/network.py:152 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 #, python-format msgid "CONNECT" msgstr "CONNECT" -#: system/ui/widgets/network.py:369 +#: system/ui/widgets/network.py:376 #, python-format msgid "CONNECTING..." msgstr "連線中..." -#: system/ui/widgets/confirm_dialog.py:23 system/ui/widgets/option_dialog.py:35 -#: system/ui/widgets/keyboard.py:81 system/ui/widgets/network.py:318 +#: system/ui/widgets/network.py:326 +#: system/ui/widgets/confirm_dialog.py:24 +#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/keyboard.py:83 #, python-format msgid "Cancel" msgstr "取消" -#: system/ui/widgets/network.py:134 +#: system/ui/widgets/network.py:131 #, python-format msgid "Cellular Metered" msgstr "行動網路計量" -#: selfdrive/ui/layouts/settings/device.py:68 +#: openpilot/selfdrive/ui/layouts/settings/device.py:66 #, python-format msgid "Change Language" msgstr "變更語言" -#: selfdrive/ui/layouts/settings/toggles.py:125 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:125 #, python-format msgid "Changing this setting will restart openpilot if the car is powered on." msgstr "若車輛通電,變更此設定將重新啟動 openpilot。" -#: selfdrive/ui/widgets/pairing_dialog.py:129 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:118 #, python-format msgid "Click \"add new device\" and scan the QR code on the right" msgstr "點選「新增裝置」,掃描右側 QR 碼" -#: selfdrive/ui/widgets/offroad_alerts.py:104 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:104 #, python-format msgid "Close" msgstr "關閉" -#: selfdrive/ui/layouts/settings/software.py:49 +#: openpilot/selfdrive/ui/layouts/settings/software.py:56 #, python-format msgid "Current Version" msgstr "目前版本" -#: selfdrive/ui/layouts/settings/software.py:110 +#: openpilot/selfdrive/ui/layouts/settings/software.py:120 #, python-format msgid "DOWNLOAD" msgstr "下載" -#: selfdrive/ui/layouts/onboarding.py:115 +#: openpilot/selfdrive/ui/layouts/onboarding.py:119 #, python-format msgid "Decline" msgstr "拒絕" -#: selfdrive/ui/layouts/onboarding.py:148 +#: openpilot/selfdrive/ui/layouts/onboarding.py:152 #, python-format msgid "Decline, uninstall openpilot" msgstr "拒絕並解除安裝 openpilot" -#: selfdrive/ui/layouts/settings/settings.py:67 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:64 msgid "Developer" msgstr "開發人員" -#: selfdrive/ui/layouts/settings/settings.py:62 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:59 msgid "Device" msgstr "裝置" -#: selfdrive/ui/layouts/settings/toggles.py:58 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:58 #, python-format msgid "Disengage on Accelerator Pedal" msgstr "踩下加速踏板時脫離" -#: selfdrive/ui/layouts/settings/device.py:184 +#: openpilot/selfdrive/ui/layouts/settings/device.py:176 #, python-format msgid "Disengage to Power Off" msgstr "脫離以關機" -#: selfdrive/ui/layouts/settings/device.py:172 +#: openpilot/selfdrive/ui/layouts/settings/device.py:164 #, python-format msgid "Disengage to Reboot" msgstr "脫離以重新啟動" -#: selfdrive/ui/layouts/settings/device.py:103 +#: openpilot/selfdrive/ui/layouts/settings/device.py:95 #, python-format msgid "Disengage to Reset Calibration" msgstr "脫離以重設校正" -#: selfdrive/ui/layouts/settings/toggles.py:32 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:32 msgid "Display speed in km/h instead of mph." msgstr "以 km/h 顯示速度(非 mph)。" -#: selfdrive/ui/layouts/settings/device.py:59 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 #, python-format msgid "Dongle ID" msgstr "Dongle ID" -#: selfdrive/ui/layouts/settings/software.py:50 +#: openpilot/selfdrive/ui/layouts/settings/software.py:57 #, python-format msgid "Download" msgstr "下載" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "Driver Camera" msgstr "車內鏡頭" -#: selfdrive/ui/layouts/settings/toggles.py:96 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:96 #, python-format msgid "Driving Personality" msgstr "駕駛風格" -#: system/ui/widgets/network.py:123 system/ui/widgets/network.py:139 +#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:136 #, python-format msgid "EDIT" msgstr "編輯" -#: selfdrive/ui/layouts/sidebar.py:138 +#: openpilot/selfdrive/ui/layouts/sidebar.py:138 msgid "ERROR" msgstr "錯誤" -#: selfdrive/ui/layouts/sidebar.py:45 +#: openpilot/selfdrive/ui/layouts/sidebar.py:45 msgid "ETH" msgstr "ETH" -#: selfdrive/ui/widgets/exp_mode_button.py:50 +#: openpilot/selfdrive/ui/widgets/exp_mode_button.py:51 #, python-format msgid "EXPERIMENTAL MODE ON" msgstr "實驗模式已開啟" -#: selfdrive/ui/layouts/settings/developer.py:166 -#: selfdrive/ui/layouts/settings/toggles.py:228 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:229 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:180 #, python-format msgid "Enable" msgstr "啟用" -#: selfdrive/ui/layouts/settings/developer.py:39 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:39 #, python-format msgid "Enable ADB" msgstr "啟用 ADB" -#: selfdrive/ui/layouts/settings/toggles.py:64 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:64 #, python-format msgid "Enable Lane Departure Warnings" msgstr "啟用偏離車道警示" -#: system/ui/widgets/network.py:129 +#: system/ui/widgets/network.py:126 #, python-format msgid "Enable Roaming" msgstr "啟用漫遊" -#: selfdrive/ui/layouts/settings/developer.py:48 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:48 #, python-format msgid "Enable SSH" msgstr "啟用 SSH" -#: system/ui/widgets/network.py:120 +#: system/ui/widgets/network.py:117 #, python-format msgid "Enable Tethering" msgstr "啟用網路共享" -#: selfdrive/ui/layouts/settings/toggles.py:30 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:30 msgid "Enable driver monitoring even when openpilot is not engaged." msgstr "即使未啟動 openpilot 亦啟用駕駛監控。" -#: selfdrive/ui/layouts/settings/toggles.py:46 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:46 #, python-format msgid "Enable openpilot" msgstr "啟用 openpilot" -#: selfdrive/ui/layouts/settings/toggles.py:189 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:190 #, python-format -msgid "" -"Enable the openpilot longitudinal control (alpha) toggle to allow " -"Experimental mode." +msgid "Enable the openpilot longitudinal control (alpha) toggle to allow Experimental mode." msgstr "啟用 openpilot 縱向控制(alpha)切換,以使用實驗模式。" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "Enter APN" msgstr "輸入 APN" -#: system/ui/widgets/network.py:241 +#: system/ui/widgets/network.py:243 #, python-format msgid "Enter SSID" msgstr "輸入 SSID" -#: system/ui/widgets/network.py:254 +#: system/ui/widgets/network.py:257 #, python-format msgid "Enter new tethering password" msgstr "輸入新的網路共享密碼" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:320 #, python-format msgid "Enter password" msgstr "輸入密碼" -#: selfdrive/ui/widgets/ssh_key.py:89 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:89 #, python-format msgid "Enter your GitHub username" msgstr "輸入您的 GitHub 使用者名稱" -#: system/ui/widgets/list_view.py:123 system/ui/widgets/list_view.py:160 +#: system/ui/widgets/list_view.py:123 +#: system/ui/widgets/list_view.py:160 #, python-format msgid "Error" msgstr "錯誤" -#: selfdrive/ui/layouts/settings/toggles.py:52 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:52 #, python-format msgid "Experimental Mode" msgstr "實驗模式" -#: selfdrive/ui/layouts/settings/toggles.py:181 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:182 #, python-format -msgid "" -"Experimental mode is currently unavailable on this car since the car's stock " -"ACC is used for longitudinal control." +msgid "Experimental mode is currently unavailable on this car since the car's stock ACC is used for longitudinal control." msgstr "此車款目前無法使用實驗模式,因為縱向控制使用的是原廠 ACC。" -#: system/ui/widgets/network.py:373 +#: system/ui/widgets/network.py:380 #, python-format msgid "FORGETTING..." msgstr "正在遺忘..." -#: selfdrive/ui/widgets/setup.py:44 +#: openpilot/selfdrive/ui/widgets/setup.py:43 #, python-format msgid "Finish Setup" msgstr "完成設定" -#: selfdrive/ui/layouts/settings/settings.py:66 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:63 msgid "Firehose" msgstr "Firehose" -#: selfdrive/ui/layouts/settings/firehose.py:18 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:10 msgid "Firehose Mode" msgstr "Firehose 模式" -#: selfdrive/ui/layouts/settings/firehose.py:25 -msgid "" -"For maximum effectiveness, bring your device inside and connect to a good " -"USB-C adapter and Wi-Fi weekly.\n" -"\n" -"Firehose Mode can also work while you're driving if connected to a hotspot " -"or unlimited SIM card.\n" -"\n" -"\n" -"Frequently Asked Questions\n" -"\n" -"Does it matter how or where I drive? Nope, just drive as you normally " -"would.\n" -"\n" -"Do all of my segments get pulled in Firehose Mode? No, we selectively pull a " -"subset of your segments.\n" -"\n" -"What's a good USB-C adapter? Any fast phone or laptop charger should be " -"fine.\n" -"\n" -"Does it matter which software I run? Yes, only upstream openpilot (and " -"particular forks) are able to be used for training." -msgstr "" -"為達最佳效果,請將裝置帶到室內,並每週連接優質 USB‑C 充電器與 Wi‑Fi。\n" -"\n" -"若連上熱點或吃到飽門號,行車中也可使用 Firehose 模式。\n" -"\n" -"\n" -"常見問題\n" -"\n" -"我怎麼開、在哪裡開有差嗎?沒有,平常怎麼開就怎麼開。\n" -"\n" -"Firehose 模式會拉取我所有片段嗎?不會,我們會選擇性拉取部分片段。\n" -"\n" -"什麼是好的 USB‑C 充電器?任何快速的手機或筆電充電器都可以。\n" -"\n" -"我跑什麼軟體有差嗎?有,只有上游 openpilot(及特定分支)可用於訓練。" - -#: system/ui/widgets/network.py:318 system/ui/widgets/network.py:451 +#: system/ui/widgets/network.py:458 +#: system/ui/widgets/network.py:326 #, python-format msgid "Forget" msgstr "忘記" -#: system/ui/widgets/network.py:319 +#: system/ui/widgets/network.py:327 #, python-format msgid "Forget Wi-Fi Network \"{}\"?" msgstr "要忘記 Wi‑Fi 網路「{}」嗎?" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 msgid "GOOD" msgstr "良好" -#: selfdrive/ui/widgets/pairing_dialog.py:128 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:117 #, python-format msgid "Go to https://connect.comma.ai on your phone" msgstr "在手機上前往 https://connect.comma.ai" -#: selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "HIGH" msgstr "高" -#: system/ui/widgets/network.py:155 +#: system/ui/widgets/network.py:152 #, python-format msgid "Hidden Network" msgstr "隱藏網路" -#: selfdrive/ui/layouts/settings/firehose.py:140 -#, python-format -msgid "INACTIVE: connect to an unmetered network" -msgstr "未啟用:請連接不限流量網路" - -#: selfdrive/ui/layouts/settings/software.py:53 -#: selfdrive/ui/layouts/settings/software.py:136 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 +#: openpilot/selfdrive/ui/layouts/settings/software.py:146 #, python-format msgid "INSTALL" msgstr "安裝" -#: system/ui/widgets/network.py:150 +#: system/ui/widgets/network.py:147 #, python-format msgid "IP Address" msgstr "IP 位址" -#: selfdrive/ui/layouts/settings/software.py:53 +#: openpilot/selfdrive/ui/layouts/settings/software.py:60 #, python-format msgid "Install Update" msgstr "安裝更新" -#: selfdrive/ui/layouts/settings/developer.py:56 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:56 #, python-format msgid "Joystick Debug Mode" msgstr "搖桿除錯模式" -#: selfdrive/ui/widgets/ssh_key.py:29 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:29 msgid "LOADING" msgstr "載入中" -#: selfdrive/ui/layouts/sidebar.py:48 +#: openpilot/selfdrive/ui/layouts/sidebar.py:48 msgid "LTE" msgstr "LTE" -#: selfdrive/ui/layouts/settings/developer.py:64 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:64 #, python-format msgid "Longitudinal Maneuver Mode" msgstr "縱向操作模式" -#: selfdrive/ui/onroad/hud_renderer.py:148 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:148 #, python-format msgid "MAX" msgstr "最大" -#: selfdrive/ui/widgets/setup.py:75 +#: openpilot/selfdrive/ui/widgets/setup.py:74 #, python-format -msgid "" -"Maximize your training data uploads to improve openpilot's driving models." +msgid "Maximize your training data uploads to improve openpilot's driving models." msgstr "最大化上傳訓練資料,以改進 openpilot 的駕駛模型。" -#: selfdrive/ui/layouts/settings/device.py:59 -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:57 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "N/A" msgstr "無" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "NO" msgstr "否" -#: selfdrive/ui/layouts/settings/settings.py:63 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:60 msgid "Network" msgstr "網路" -#: selfdrive/ui/widgets/ssh_key.py:114 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:115 #, python-format msgid "No SSH keys found" msgstr "找不到 SSH 金鑰" -#: selfdrive/ui/widgets/ssh_key.py:126 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:127 #, python-format msgid "No SSH keys found for user '{}'" msgstr "找不到使用者 '{}' 的 SSH 金鑰" -#: selfdrive/ui/widgets/offroad_alerts.py:320 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:321 #, python-format msgid "No release notes available." msgstr "無可用發行說明。" -#: selfdrive/ui/layouts/sidebar.py:73 selfdrive/ui/layouts/sidebar.py:134 +#: openpilot/selfdrive/ui/layouts/sidebar.py:73 +#: openpilot/selfdrive/ui/layouts/sidebar.py:134 msgid "OFFLINE" msgstr "離線" -#: system/ui/widgets/html_render.py:263 system/ui/widgets/confirm_dialog.py:93 -#: selfdrive/ui/layouts/sidebar.py:127 +#: system/ui/widgets/confirm_dialog.py:93 +#: system/ui/widgets/html_render.py:263 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 #, python-format msgid "OK" msgstr "確定" -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:136 -#: selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:136 msgid "ONLINE" msgstr "線上" -#: selfdrive/ui/widgets/setup.py:20 +#: openpilot/selfdrive/ui/widgets/setup.py:19 #, python-format msgid "Open" msgstr "開啟" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "PAIR" msgstr "配對" -#: selfdrive/ui/layouts/sidebar.py:142 +#: openpilot/selfdrive/ui/layouts/sidebar.py:142 msgid "PANDA" msgstr "PANDA" -#: selfdrive/ui/layouts/settings/device.py:62 +#: openpilot/selfdrive/ui/layouts/settings/device.py:60 #, python-format msgid "PREVIEW" msgstr "預覽" -#: selfdrive/ui/widgets/prime.py:44 +#: openpilot/selfdrive/ui/widgets/prime.py:44 #, python-format msgid "PRIME FEATURES:" msgstr "PRIME 功能:" -#: selfdrive/ui/layouts/settings/device.py:48 +#: openpilot/selfdrive/ui/layouts/settings/device.py:45 #, python-format msgid "Pair Device" msgstr "配對裝置" -#: selfdrive/ui/widgets/setup.py:19 +#: openpilot/selfdrive/ui/widgets/setup.py:18 #, python-format msgid "Pair device" msgstr "配對裝置" -#: selfdrive/ui/widgets/pairing_dialog.py:103 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:92 #, python-format msgid "Pair your device to your comma account" msgstr "將裝置配對至您的 comma 帳號" -#: selfdrive/ui/widgets/setup.py:48 selfdrive/ui/layouts/settings/device.py:24 +#: openpilot/selfdrive/ui/widgets/setup.py:47 +#: openpilot/selfdrive/ui/layouts/settings/device.py:23 #, python-format -msgid "" -"Pair your device with comma connect (connect.comma.ai) and claim your comma " -"prime offer." -msgstr "" -"將裝置與 comma connect(connect.comma.ai)配對,領取您的 comma prime 優惠。" +msgid "Pair your device with comma connect (connect.comma.ai) and claim your comma prime offer." +msgstr "將裝置與 comma connect(connect.comma.ai)配對,領取您的 comma prime 優惠。" -#: selfdrive/ui/widgets/setup.py:91 +#: openpilot/selfdrive/ui/widgets/setup.py:91 #, python-format msgid "Please connect to Wi-Fi to complete initial pairing" msgstr "請連線至 Wi‑Fi 以完成初始化配對" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:187 +#: openpilot/selfdrive/ui/layouts/settings/device.py:183 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Power Off" msgstr "關機" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Prevent large data uploads when on a metered Wi-Fi connection" msgstr "在計量制 Wi‑Fi 連線時避免大量上傳" -#: system/ui/widgets/network.py:135 +#: system/ui/widgets/network.py:132 #, python-format msgid "Prevent large data uploads when on a metered cellular connection" msgstr "在計量制行動網路時避免大量上傳" -#: selfdrive/ui/layouts/settings/device.py:25 -msgid "" -"Preview the driver facing camera to ensure that driver monitoring has good " -"visibility. (vehicle must be off)" +#: openpilot/selfdrive/ui/layouts/settings/device.py:24 +msgid "Preview the driver facing camera to ensure that driver monitoring has good visibility. (vehicle must be off)" msgstr "預覽車內鏡頭以確保駕駛監控視野良好。(車輛須熄火)" -#: selfdrive/ui/widgets/pairing_dialog.py:161 +#: openpilot/selfdrive/ui/widgets/pairing_dialog.py:150 #, python-format msgid "QR Code Error" msgstr "QR 碼錯誤" -#: selfdrive/ui/widgets/ssh_key.py:31 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:31 msgid "REMOVE" msgstr "移除" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "RESET" msgstr "重設" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "REVIEW" msgstr "檢視" -#: selfdrive/ui/layouts/settings/device.py:55 -#: selfdrive/ui/layouts/settings/device.py:175 +#: openpilot/selfdrive/ui/layouts/settings/device.py:171 +#: openpilot/selfdrive/ui/layouts/settings/device.py:53 #, python-format msgid "Reboot" msgstr "重新啟動" -#: selfdrive/ui/onroad/alert_renderer.py:66 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:66 #, python-format msgid "Reboot Device" msgstr "重新啟動裝置" -#: selfdrive/ui/widgets/offroad_alerts.py:112 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:112 #, python-format msgid "Reboot and Update" msgstr "重新啟動並更新" -#: selfdrive/ui/layouts/settings/toggles.py:27 -msgid "" -"Receive alerts to steer back into the lane when your vehicle drifts over a " -"detected lane line without a turn signal activated while driving over 31 mph " -"(50 km/h)." -msgstr "" -"當車輛以超過 31 mph(50 km/h)行駛且未打方向燈越過偵測到的車道線時,接收轉向" -"回車道的警示。" - -#: selfdrive/ui/layouts/settings/toggles.py:76 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:76 #, python-format msgid "Record and Upload Driver Camera" msgstr "錄製並上傳車內鏡頭" -#: selfdrive/ui/layouts/settings/toggles.py:82 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:82 #, python-format msgid "Record and Upload Microphone Audio" msgstr "錄製並上傳麥克風音訊" -#: selfdrive/ui/layouts/settings/toggles.py:33 -msgid "" -"Record and store microphone audio while driving. The audio will be included " -"in the dashcam video in comma connect." -msgstr "" -"行車時錄製並儲存麥克風音訊。音訊將包含在 comma connect 的行車紀錄影片中。" +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:33 +msgid "Record and store microphone audio while driving. The audio will be included in the dashcam video in comma connect." +msgstr "行車時錄製並儲存麥克風音訊。音訊將包含在 comma connect 的行車紀錄影片中。" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "Regulatory" msgstr "法規" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Relaxed" msgstr "從容" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote access" msgstr "遠端存取" -#: selfdrive/ui/widgets/prime.py:47 +#: openpilot/selfdrive/ui/widgets/prime.py:47 #, python-format msgid "Remote snapshots" msgstr "遠端擷圖" -#: selfdrive/ui/widgets/ssh_key.py:123 +#: openpilot/selfdrive/ui/widgets/ssh_key.py:124 #, python-format msgid "Request timed out" msgstr "要求逾時" -#: selfdrive/ui/layouts/settings/device.py:119 +#: openpilot/selfdrive/ui/layouts/settings/device.py:111 #, python-format msgid "Reset" msgstr "重設" -#: selfdrive/ui/layouts/settings/device.py:51 +#: openpilot/selfdrive/ui/layouts/settings/device.py:49 #, python-format msgid "Reset Calibration" msgstr "重設校正" -#: selfdrive/ui/layouts/settings/device.py:65 +#: openpilot/selfdrive/ui/layouts/settings/device.py:63 #, python-format msgid "Review Training Guide" msgstr "檢視訓練指南" -#: selfdrive/ui/layouts/settings/device.py:27 +#: openpilot/selfdrive/ui/layouts/settings/device.py:26 msgid "Review the rules, features, and limitations of openpilot" msgstr "檢視 openpilot 的規則、功能與限制" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "SELECT" msgstr "選取" -#: selfdrive/ui/layouts/settings/developer.py:53 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:53 #, python-format msgid "SSH Keys" msgstr "SSH 金鑰" -#: system/ui/widgets/network.py:310 +#: system/ui/widgets/network.py:316 #, python-format msgid "Scanning Wi-Fi networks..." msgstr "正在掃描 Wi‑Fi 網路…" -#: system/ui/widgets/option_dialog.py:36 +#: system/ui/widgets/option_dialog.py:37 #, python-format msgid "Select" msgstr "選取" -#: selfdrive/ui/layouts/settings/software.py:183 +#: openpilot/selfdrive/ui/layouts/settings/software.py:203 #, python-format msgid "Select a branch" msgstr "選取分支" -#: selfdrive/ui/layouts/settings/device.py:91 +#: openpilot/selfdrive/ui/layouts/settings/device.py:89 #, python-format msgid "Select a language" msgstr "選取語言" -#: selfdrive/ui/layouts/settings/device.py:60 +#: openpilot/selfdrive/ui/layouts/settings/device.py:58 #, python-format msgid "Serial" msgstr "序號" -#: selfdrive/ui/widgets/offroad_alerts.py:106 +#: openpilot/selfdrive/ui/widgets/offroad_alerts.py:106 #, python-format msgid "Snooze Update" msgstr "延後更新" -#: selfdrive/ui/layouts/settings/settings.py:65 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:62 msgid "Software" msgstr "軟體" -#: selfdrive/ui/layouts/settings/toggles.py:98 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:98 #, python-format msgid "Standard" msgstr "標準" -#: selfdrive/ui/layouts/settings/toggles.py:22 -msgid "" -"Standard is recommended. In aggressive mode, openpilot will follow lead cars " -"closer and be more aggressive with the gas and brake. In relaxed mode " -"openpilot will stay further away from lead cars. On supported cars, you can " -"cycle through these personalities with your steering wheel distance button." -msgstr "" -"建議使用標準模式。積極模式下,openpilot 會更貼近前車,油門與煞車反應更積極;" -"從容模式下,會與前車保持更遠距離。於支援車款,可用方向盤距離按鈕切換這些風" -"格。" - -#: selfdrive/ui/onroad/alert_renderer.py:59 -#: selfdrive/ui/onroad/alert_renderer.py:65 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:59 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:65 #, python-format msgid "System Unresponsive" msgstr "系統無回應" -#: selfdrive/ui/onroad/alert_renderer.py:58 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:58 #, python-format msgid "TAKE CONTROL IMMEDIATELY" msgstr "請立刻接手控制" -#: selfdrive/ui/layouts/sidebar.py:71 selfdrive/ui/layouts/sidebar.py:125 -#: selfdrive/ui/layouts/sidebar.py:127 selfdrive/ui/layouts/sidebar.py:129 +#: openpilot/selfdrive/ui/layouts/sidebar.py:71 +#: openpilot/selfdrive/ui/layouts/sidebar.py:125 +#: openpilot/selfdrive/ui/layouts/sidebar.py:127 +#: openpilot/selfdrive/ui/layouts/sidebar.py:129 msgid "TEMP" msgstr "溫度" -#: selfdrive/ui/layouts/settings/software.py:61 +#: openpilot/selfdrive/ui/layouts/settings/software.py:68 #, python-format msgid "Target Branch" msgstr "目標分支" -#: system/ui/widgets/network.py:124 +#: system/ui/widgets/network.py:121 #, python-format msgid "Tethering Password" msgstr "網路共享密碼" -#: selfdrive/ui/layouts/settings/settings.py:64 +#: openpilot/selfdrive/ui/layouts/settings/settings.py:61 msgid "Toggles" msgstr "切換" -#: selfdrive/ui/layouts/settings/software.py:72 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:79 +#, python-format +msgid "UI Debug Mode" +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "UNINSTALL" msgstr "解除安裝" -#: selfdrive/ui/layouts/home.py:155 +#: openpilot/selfdrive/ui/layouts/home.py:155 #, python-format msgid "UPDATE" msgstr "更新" -#: selfdrive/ui/layouts/settings/software.py:72 -#: selfdrive/ui/layouts/settings/software.py:163 +#: openpilot/selfdrive/ui/layouts/settings/software.py:173 +#: openpilot/selfdrive/ui/layouts/settings/software.py:79 #, python-format msgid "Uninstall" msgstr "解除安裝" -#: selfdrive/ui/layouts/sidebar.py:117 +#: openpilot/selfdrive/ui/layouts/sidebar.py:117 msgid "Unknown" msgstr "未知" -#: selfdrive/ui/layouts/settings/software.py:48 +#: openpilot/selfdrive/ui/layouts/settings/software.py:55 #, python-format msgid "Updates are only downloaded while the car is off." msgstr "僅在車輛熄火時下載更新。" -#: selfdrive/ui/widgets/prime.py:33 +#: openpilot/selfdrive/ui/widgets/prime.py:33 #, python-format msgid "Upgrade Now" msgstr "立即升級" -#: selfdrive/ui/layouts/settings/toggles.py:31 -msgid "" -"Upload data from the driver facing camera and help improve the driver " -"monitoring algorithm." +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:31 +msgid "Upload data from the driver facing camera and help improve the driver monitoring algorithm." msgstr "上傳車內鏡頭資料,協助改善駕駛監控演算法。" -#: selfdrive/ui/layouts/settings/toggles.py:88 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:88 #, python-format msgid "Use Metric System" msgstr "使用公制" -#: selfdrive/ui/layouts/settings/toggles.py:17 -msgid "" -"Use the openpilot system for adaptive cruise control and lane keep driver " -"assistance. Your attention is required at all times to use this feature." -msgstr "" -"使用 openpilot 進行 ACC 與車道維持輔助。使用此功能時,您必須始終保持專注。" - -#: selfdrive/ui/layouts/sidebar.py:72 selfdrive/ui/layouts/sidebar.py:144 +#: openpilot/selfdrive/ui/layouts/sidebar.py:72 +#: openpilot/selfdrive/ui/layouts/sidebar.py:144 msgid "VEHICLE" msgstr "車輛" -#: selfdrive/ui/layouts/settings/device.py:67 +#: openpilot/selfdrive/ui/layouts/settings/device.py:65 #, python-format msgid "VIEW" msgstr "檢視" -#: selfdrive/ui/onroad/alert_renderer.py:52 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:52 #, python-format msgid "Waiting to start" msgstr "等待開始" -#: selfdrive/ui/layouts/settings/developer.py:19 -msgid "" -"Warning: This grants SSH access to all public keys in your GitHub settings. " -"Never enter a GitHub username other than your own. A comma employee will " -"NEVER ask you to add their GitHub username." -msgstr "" -"警告:這將授予對您 GitHub 設定中所有公開金鑰的 SSH 存取權。請勿輸入非您本人" -"的 GitHub 帳號。comma 員工絕不會要求您新增他們的帳號。" - -#: selfdrive/ui/layouts/onboarding.py:111 +#: openpilot/selfdrive/ui/layouts/onboarding.py:115 #, python-format msgid "Welcome to openpilot" msgstr "歡迎使用 openpilot" -#: selfdrive/ui/layouts/settings/toggles.py:20 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:20 msgid "When enabled, pressing the accelerator pedal will disengage openpilot." msgstr "啟用後,踩下加速踏板將會脫離 openpilot。" -#: selfdrive/ui/layouts/sidebar.py:44 +#: openpilot/selfdrive/ui/layouts/sidebar.py:44 msgid "Wi-Fi" msgstr "Wi‑Fi" -#: system/ui/widgets/network.py:144 +#: system/ui/widgets/network.py:141 #, python-format msgid "Wi-Fi Network Metered" msgstr "Wi‑Fi 計量網路" -#: system/ui/widgets/network.py:314 +#: system/ui/widgets/network.py:320 #, python-format msgid "Wrong password" msgstr "密碼錯誤" -#: selfdrive/ui/layouts/onboarding.py:145 +#: openpilot/selfdrive/ui/layouts/onboarding.py:149 #, python-format msgid "You must accept the Terms and Conditions in order to use openpilot." msgstr "您必須接受條款與細則才能使用 openpilot。" -#: selfdrive/ui/layouts/onboarding.py:112 +#: openpilot/selfdrive/ui/layouts/onboarding.py:116 #, python-format -msgid "" -"You must accept the Terms and Conditions to use openpilot. Read the latest " -"terms at https://comma.ai/terms before continuing." -msgstr "" -"您必須接受條款與細則才能使用 openpilot。繼續前請閱讀 https://comma.ai/terms " -"上的最新條款。" +msgid "You must accept the Terms and Conditions to use openpilot. Read the latest terms at https://comma.ai/terms before continuing." +msgstr "您必須接受條款與細則才能使用 openpilot。繼續前請閱讀 https://comma.ai/terms 上的最新條款。" -#: selfdrive/ui/onroad/driver_camera_dialog.py:34 +#: openpilot/selfdrive/ui/onroad/driver_camera_dialog.py:38 #, python-format msgid "camera starting" msgstr "相機啟動中" -#: selfdrive/ui/widgets/prime.py:63 +#: openpilot/selfdrive/ui/layouts/settings/software.py:19 +#, python-format +msgid "checking..." +msgstr "" + +#: openpilot/selfdrive/ui/widgets/prime.py:63 #, python-format msgid "comma prime" msgstr "comma prime" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "default" msgstr "預設" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "down" msgstr "下" -#: selfdrive/ui/layouts/settings/software.py:106 +#: openpilot/selfdrive/ui/layouts/settings/software.py:20 +#, python-format +msgid "downloading..." +msgstr "" + +#: openpilot/selfdrive/ui/layouts/settings/software.py:116 #, python-format msgid "failed to check for update" msgstr "檢查更新失敗" -#: system/ui/widgets/network.py:237 system/ui/widgets/network.py:314 +#: openpilot/selfdrive/ui/layouts/settings/software.py:21 +#, python-format +msgid "finalizing update..." +msgstr "" + +#: system/ui/widgets/network.py:238 +#: system/ui/widgets/network.py:321 #, python-format msgid "for \"{}\"" msgstr "適用於「{}」" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "km/h" msgstr "km/h" -#: system/ui/widgets/network.py:204 +#: system/ui/widgets/network.py:201 #, python-format msgid "leave blank for automatic configuration" msgstr "留空以自動設定" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "left" msgstr "左" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "metered" msgstr "計量" -#: selfdrive/ui/onroad/hud_renderer.py:177 +#: openpilot/selfdrive/ui/onroad/hud_renderer.py:177 #, python-format msgid "mph" msgstr "mph" -#: selfdrive/ui/layouts/settings/software.py:20 +#: openpilot/selfdrive/ui/layouts/settings/software.py:27 #, python-format msgid "never" msgstr "從不" -#: selfdrive/ui/layouts/settings/software.py:31 +#: openpilot/selfdrive/ui/layouts/settings/software.py:38 #, python-format msgid "now" msgstr "現在" -#: selfdrive/ui/layouts/settings/developer.py:71 +#: openpilot/selfdrive/ui/layouts/settings/developer.py:71 #, python-format msgid "openpilot Longitudinal Control (Alpha)" msgstr "openpilot 縱向控制(Alpha)" -#: selfdrive/ui/onroad/alert_renderer.py:51 +#: openpilot/selfdrive/ui/onroad/alert_renderer.py:51 #, python-format msgid "openpilot Unavailable" msgstr "openpilot 無法使用" -#: selfdrive/ui/layouts/settings/toggles.py:158 -#, python-format -msgid "" -"openpilot defaults to driving in chill mode. Experimental mode enables alpha-" -"level features that aren't ready for chill mode. Experimental features are " -"listed below:

End-to-End Longitudinal Control


Let the driving " -"model control the gas and brakes. openpilot will drive as it thinks a human " -"would, including stopping for red lights and stop signs. Since the driving " -"model decides the speed to drive, the set speed will only act as an upper " -"bound. This is an alpha quality feature; mistakes should be expected." -"

New Driving Visualization


The driving visualization will " -"transition to the road-facing wide-angle camera at low speeds to better show " -"some turns. The Experimental mode logo will also be shown in the top right " -"corner." -msgstr "" -"openpilot 預設以安穩模式行駛。實驗模式啟用尚未準備好進入安穩模式的 Alpha 等級" -"功能。實驗功能如下:

端到端縱向控制


讓駕駛模型控制油門與煞車。" -"openpilot 會如同人類駕駛般行駛,包括在紅燈與停車標誌前停車。由於駕駛模型決定" -"行駛速度,設定速度僅作為上限。此為 Alpha 品質功能;預期會有失誤。

全新" -"駕駛視覺化


在低速時,駕駛視覺化將切換至面向道路的廣角鏡頭以更好呈現部" -"分轉彎。右上角亦會顯示實驗模式圖示。" - -#: selfdrive/ui/layouts/settings/device.py:165 -#, python-format -msgid "" -"openpilot is continuously calibrating, resetting is rarely required. " -"Resetting calibration will restart openpilot if the car is powered on." -msgstr "" -"openpilot 會持續校正,通常不需重設。若車輛通電,重設校正將重新啟動 " -"openpilot。" - -#: selfdrive/ui/layouts/settings/firehose.py:20 -msgid "" -"openpilot learns to drive by watching humans, like you, drive.\n" -"\n" -"Firehose Mode allows you to maximize your training data uploads to improve " -"openpilot's driving models. More data means bigger models, which means " -"better Experimental Mode." -msgstr "" -"openpilot 透過觀察人類(也就是您)的駕駛方式來學習。\n" -"\n" -"Firehose 模式可讓您最大化上傳訓練資料,以改進 openpilot 的駕駛模型。更多資料" -"代表更大的模型,也就代表更好的實驗模式。" - -#: selfdrive/ui/layouts/settings/toggles.py:183 +#: openpilot/selfdrive/ui/layouts/settings/toggles.py:184 #, python-format msgid "openpilot longitudinal control may come in a future update." msgstr "openpilot 縱向控制可能於未來更新提供。" -#: selfdrive/ui/layouts/settings/device.py:26 -msgid "" -"openpilot requires the device to be mounted within 4° left or right and " -"within 5° up or 9° down." +#: openpilot/selfdrive/ui/layouts/settings/device.py:25 +msgid "openpilot requires the device to be mounted within 4° left or right and within 5° up or 9° down." msgstr "openpilot 要求裝置安裝在左右 4°、上 5° 或下 9° 以內。" -#: selfdrive/ui/layouts/settings/device.py:134 +#: openpilot/selfdrive/ui/layouts/settings/device.py:126 #, python-format msgid "right" msgstr "右" -#: system/ui/widgets/network.py:142 +#: system/ui/widgets/network.py:139 #, python-format msgid "unmetered" msgstr "不限流量" -#: selfdrive/ui/layouts/settings/device.py:133 +#: openpilot/selfdrive/ui/layouts/settings/device.py:125 #, python-format msgid "up" msgstr "上" -#: selfdrive/ui/layouts/settings/software.py:117 +#: openpilot/selfdrive/ui/layouts/settings/software.py:127 #, python-format msgid "up to date, last checked never" msgstr "已為最新,最後檢查:從未" -#: selfdrive/ui/layouts/settings/software.py:115 +#: openpilot/selfdrive/ui/layouts/settings/software.py:125 #, python-format msgid "up to date, last checked {}" msgstr "已為最新,最後檢查:{}" -#: selfdrive/ui/layouts/settings/software.py:109 +#: openpilot/selfdrive/ui/layouts/settings/software.py:119 #, python-format msgid "update available" msgstr "有可用更新" -#: selfdrive/ui/layouts/home.py:169 +#: openpilot/selfdrive/ui/layouts/home.py:169 #, python-format msgid "{} ALERT" msgid_plural "{} ALERTS" msgstr[0] "{} 則警示" msgstr[1] "{} 則警示" -#: selfdrive/ui/layouts/settings/software.py:40 +#: openpilot/selfdrive/ui/layouts/settings/software.py:47 #, python-format msgid "{} day ago" msgid_plural "{} days ago" msgstr[0] "{} 天前" msgstr[1] "{} 天前" -#: selfdrive/ui/layouts/settings/software.py:37 +#: openpilot/selfdrive/ui/layouts/settings/software.py:44 #, python-format msgid "{} hour ago" msgid_plural "{} hours ago" msgstr[0] "{} 小時前" msgstr[1] "{} 小時前" -#: selfdrive/ui/layouts/settings/software.py:34 +#: openpilot/selfdrive/ui/layouts/settings/software.py:41 #, python-format msgid "{} minute ago" msgid_plural "{} minutes ago" msgstr[0] "{} 分鐘前" msgstr[1] "{} 分鐘前" -#: selfdrive/ui/layouts/settings/firehose.py:111 +#: openpilot/selfdrive/ui/layouts/settings/firehose.py:70 #, python-format msgid "{} segment of your driving is in the training dataset so far." msgid_plural "{} segments of your driving is in the training dataset so far." msgstr[0] "目前已有 {} 個您的駕駛片段納入訓練資料集。" msgstr[1] "目前已有 {} 個您的駕駛片段納入訓練資料集。" -#: selfdrive/ui/widgets/prime.py:62 +#: openpilot/selfdrive/ui/widgets/prime.py:62 #, python-format msgid "✓ SUBSCRIBED" msgstr "✓ 已訂閱" -#: selfdrive/ui/widgets/setup.py:22 +#: openpilot/selfdrive/ui/widgets/setup.py:21 #, python-format msgid "🔥 Firehose Mode 🔥" msgstr "🔥 Firehose 模式 🔥" + diff --git a/selfdrive/ui/widgets/exp_mode_button.py b/selfdrive/ui/widgets/exp_mode_button.py index faa3bf877f..0b5bff7da4 100644 --- a/selfdrive/ui/widgets/exp_mode_button.py +++ b/selfdrive/ui/widgets/exp_mode_button.py @@ -20,6 +20,7 @@ class ExperimentalModeButton(Widget): self.experimental_pixmap = gui_app.texture("icons/experimental_grey.png", self.img_width, self.img_width) def show_event(self): + super().show_event() self.experimental_mode = self.params.get_bool("ExperimentalMode") def _get_gradient_colors(self): diff --git a/selfdrive/ui/widgets/offroad_alerts.py b/selfdrive/ui/widgets/offroad_alerts.py index a87727e27f..110ca714a9 100644 --- a/selfdrive/ui/widgets/offroad_alerts.py +++ b/selfdrive/ui/widgets/offroad_alerts.py @@ -118,6 +118,7 @@ class AbstractAlert(Widget, ABC): self.scroll_panel = GuiScrollPanel() def show_event(self): + super().show_event() self.scroll_panel.set_offset(0) def set_dismiss_callback(self, callback: Callable): diff --git a/selfdrive/ui/widgets/ssh_key.py b/selfdrive/ui/widgets/ssh_key.py index b31a9eb3bd..b3ff5c1711 100644 --- a/selfdrive/ui/widgets/ssh_key.py +++ b/selfdrive/ui/widgets/ssh_key.py @@ -1,7 +1,6 @@ import pyray as rl import requests import threading -import copy from collections.abc import Callable from enum import Enum @@ -25,6 +24,51 @@ from openpilot.system.ui.widgets.list_view import ( VALUE_FONT_SIZE = 48 +class SshKeyFetcher: + HTTP_TIMEOUT = 15 # seconds + + def __init__(self, params: Params): + self._params = params + self._on_response: Callable[[str | None], None] | None = None + self._done: bool = False + self._error: str | None = None + + def fetch(self, username: str, on_response: Callable[[str | None], None]): + self._error = None + self._on_response = on_response + threading.Thread(target=self._fetch_thread, args=(username,), daemon=True).start() + + def update(self): + if not self._done: + return + self._done = False + if self._error is not None: + self.clear() + if self._on_response: + self._on_response(self._error) + + def clear(self): + self._params.remove("GithubUsername") + self._params.remove("GithubSshKeys") + + def _fetch_thread(self, username: str): + try: + response = requests.get(f"https://github.com/{username}.keys", timeout=self.HTTP_TIMEOUT) + response.raise_for_status() + keys = response.text.strip() + if not keys: + raise requests.exceptions.HTTPError("No SSH keys found") + + self._params.put("GithubUsername", username) + self._params.put("GithubSshKeys", keys) + except requests.exceptions.Timeout: + self._error = tr("Request timed out") + except Exception: + self._error = tr("No SSH keys found for user '{}'").format(username) + finally: + self._done = True + + class SshKeyActionState(Enum): LOADING = tr_noop("LOADING") ADD = tr_noop("ADD") @@ -32,7 +76,6 @@ class SshKeyActionState(Enum): class SshKeyAction(ItemAction): - HTTP_TIMEOUT = 15 # seconds MAX_WIDTH = 500 def __init__(self): @@ -40,7 +83,7 @@ class SshKeyAction(ItemAction): self._keyboard = Keyboard(min_text_size=1) self._params = Params() - self._error_message: str = "" + self._fetcher = SshKeyFetcher(self._params) self._text_font = gui_app.font(FontWeight.NORMAL) self._button = Button("", click_callback=self._handle_button_click, button_style=ButtonStyle.LIST_ACTION, border_radius=BUTTON_BORDER_RADIUS, font_size=BUTTON_FONT_SIZE) @@ -55,14 +98,11 @@ class SshKeyAction(ItemAction): self._username = self._params.get("GithubUsername") self._state = SshKeyActionState.REMOVE if self._params.get("GithubSshKeys") else SshKeyActionState.ADD - def _render(self, rect: rl.Rectangle) -> bool: - # Show error dialog if there's an error - if self._error_message: - message = copy.copy(self._error_message) - gui_app.push_widget(alert_dialog(message)) - self._username = "" - self._error_message = "" + def _update_state(self): + super()._update_state() + self._fetcher.update() + def _render(self, rect: rl.Rectangle) -> bool: # Draw username if exists if self._username: text_size = measure_text_cached(self._text_font, self._username, VALUE_FONT_SIZE) @@ -90,8 +130,7 @@ class SshKeyAction(ItemAction): self._keyboard.set_callback(self._on_username_submit) gui_app.push_widget(self._keyboard) elif self._state == SshKeyActionState.REMOVE: - self._params.remove("GithubUsername") - self._params.remove("GithubSshKeys") + self._fetcher.clear() self._refresh_state() def _on_username_submit(self, result: DialogResult): @@ -103,29 +142,16 @@ class SshKeyAction(ItemAction): return self._state = SshKeyActionState.LOADING - threading.Thread(target=lambda: self._fetch_ssh_key(username), daemon=True).start() + self._fetcher.fetch(username, self._on_fetch_response) - def _fetch_ssh_key(self, username: str): - try: - url = f"https://github.com/{username}.keys" - response = requests.get(url, timeout=self.HTTP_TIMEOUT) - response.raise_for_status() - keys = response.text.strip() - if not keys: - raise requests.exceptions.HTTPError(tr("No SSH keys found")) - - # Success - save keys - self._params.put("GithubUsername", username) - self._params.put("GithubSshKeys", keys) + def _on_fetch_response(self, error: str | None): + if error is None: self._state = SshKeyActionState.REMOVE - self._username = username - - except requests.exceptions.Timeout: - self._error_message = tr("Request timed out") - self._state = SshKeyActionState.ADD - except Exception: - self._error_message = tr("No SSH keys found for user '{}'").format(username) + self._username = self._params.get("GithubUsername") + else: self._state = SshKeyActionState.ADD + self._username = "" + gui_app.push_widget(alert_dialog(error)) def ssh_key_item(title: str | Callable[[], str], description: str | Callable[[], str]) -> ListItem: diff --git a/sunnypilot/sunnylink/athena/sunnylinkd.py b/sunnypilot/sunnylink/athena/sunnylinkd.py index e8066dca49..39fe5679ce 100755 --- a/sunnypilot/sunnylink/athena/sunnylinkd.py +++ b/sunnypilot/sunnylink/athena/sunnylinkd.py @@ -229,6 +229,41 @@ def getParamsAllKeysV1() -> dict[str, str]: raise +@dispatcher.add_method +def getParamsMetadata() -> str: + """Compressed equivalent of getParamsAllKeysV1 — same struct, gzipped + base64.""" + try: + with open(METADATA_PATH) as f: + metadata = json.load(f) + except Exception: + cloudlog.exception("sunnylinkd.getParamsMetadata.exception") + metadata = {} + + try: + available_keys: list[str] = [k.decode('utf-8') for k in Params().all_keys()] + + params_list: list[dict] = [] + for key in available_keys: + value = get_param_as_byte(key, get_default=True) + + param_entry: dict = { + "key": key, + "type": int(params.get_type(key).value), + "default_value": base64.b64encode(value).decode('utf-8') if value else None, + } + + if key in metadata: + param_entry["_extra"] = metadata[key] + + params_list.append(param_entry) + + raw = json.dumps(params_list, separators=(',', ':')).encode('utf-8') + return base64.b64encode(gzip.compress(raw)).decode('utf-8') + except Exception: + cloudlog.exception("sunnylinkd.getParamsMetadata.exception") + raise + + @dispatcher.add_method def getParams(params_keys: list[str], compression: bool = False) -> str | dict[str, str]: params = Params() diff --git a/system/camerad/cameras/hw.h b/system/camerad/cameras/hw.h index f20a1b3ade..defe878e89 100644 --- a/system/camerad/cameras/hw.h +++ b/system/camerad/cameras/hw.h @@ -25,6 +25,7 @@ struct CameraConfig { uint32_t phy; bool vignetting_correction; SpectraOutputType output_type; + bool staggered_sof; // SOF is staggered (half-period offset) from other cameras }; // NOTE: to be able to disable road and wide road, we still have to configure the sensor over i2c @@ -39,6 +40,7 @@ const CameraConfig WIDE_ROAD_CAMERA_CONFIG = { .phy = CAM_ISP_IFE_IN_RES_PHY_0, .vignetting_correction = false, .output_type = ISP_IFE_PROCESSED, + .staggered_sof = false, }; const CameraConfig ROAD_CAMERA_CONFIG = { @@ -51,6 +53,7 @@ const CameraConfig ROAD_CAMERA_CONFIG = { .phy = CAM_ISP_IFE_IN_RES_PHY_1, .vignetting_correction = true, .output_type = ISP_IFE_PROCESSED, + .staggered_sof = false, }; const CameraConfig DRIVER_CAMERA_CONFIG = { @@ -63,6 +66,7 @@ const CameraConfig DRIVER_CAMERA_CONFIG = { .phy = CAM_ISP_IFE_IN_RES_PHY_2, .vignetting_correction = false, .output_type = ISP_BPS_PROCESSED, + .staggered_sof = true, }; const CameraConfig ALL_CAMERA_CONFIGS[] = {WIDE_ROAD_CAMERA_CONFIG, ROAD_CAMERA_CONFIG, DRIVER_CAMERA_CONFIG}; diff --git a/system/camerad/cameras/spectra.cc b/system/camerad/cameras/spectra.cc index 73e0a78da3..ab9d8e069a 100644 --- a/system/camerad/cameras/spectra.cc +++ b/system/camerad/cameras/spectra.cc @@ -1436,7 +1436,7 @@ bool SpectraCamera::waitForFrameReady(uint64_t request_id) { } bool SpectraCamera::processFrame(int buf_idx, uint64_t request_id, uint64_t frame_id_raw, uint64_t timestamp) { - if (!syncFirstFrame(cc.camera_num, request_id, frame_id_raw, timestamp)) { + if (!syncFirstFrame(cc.camera_num, request_id, frame_id_raw, timestamp, cc.staggered_sof)) { return false; } @@ -1455,23 +1455,31 @@ bool SpectraCamera::processFrame(int buf_idx, uint64_t request_id, uint64_t fram return true; } -bool SpectraCamera::syncFirstFrame(int camera_id, uint64_t request_id, uint64_t raw_id, uint64_t timestamp) { +bool SpectraCamera::syncFirstFrame(int camera_id, uint64_t request_id, uint64_t raw_id, uint64_t timestamp, bool staggered) { if (first_frame_synced) return true; // Store the frame data for this camera - camera_sync_data[camera_id] = SyncData{timestamp, raw_id + 1}; + camera_sync_data[camera_id] = SyncData{timestamp, raw_id + 1, staggered}; // Ensure all cameras are up int enabled_camera_count = std::count_if(std::begin(ALL_CAMERA_CONFIGS), std::end(ALL_CAMERA_CONFIGS), [](const auto &config) { return config.enabled; }); bool all_cams_up = camera_sync_data.size() == enabled_camera_count; - // Wait until the timestamps line up + // Check that camera timestamps are properly aligned: + // - non-staggered cameras should be within 0.2ms of each other + // - staggered cameras should be within 0.2ms of a 25ms offset from non-staggered cameras + const uint64_t half_period_ns = 25 * 1000000ULL; // 25ms + const uint64_t tolerance_ns = 200000ULL; // 0.2ms bool all_cams_synced = true; - for (const auto &[_, sync_data] : camera_sync_data) { + for (const auto &[cam, sync_data] : camera_sync_data) { + if (cam == camera_id) continue; uint64_t diff = std::max(timestamp, sync_data.timestamp) - std::min(timestamp, sync_data.timestamp); - if (diff > 0.2*1e6) { // milliseconds + bool pair_staggered = staggered != sync_data.staggered; + uint64_t expected_offset = pair_staggered ? half_period_ns : 0; + uint64_t error = (diff > expected_offset) ? diff - expected_offset : expected_offset - diff; + if (error > tolerance_ns) { all_cams_synced = false; } } diff --git a/system/camerad/cameras/spectra.h b/system/camerad/cameras/spectra.h index a02b8a6cac..7dd1135254 100644 --- a/system/camerad/cameras/spectra.h +++ b/system/camerad/cameras/spectra.h @@ -194,10 +194,11 @@ private: bool validateEvent(uint64_t request_id, uint64_t frame_id_raw); bool waitForFrameReady(uint64_t request_id); bool processFrame(int buf_idx, uint64_t request_id, uint64_t frame_id_raw, uint64_t timestamp); - static bool syncFirstFrame(int camera_id, uint64_t request_id, uint64_t raw_id, uint64_t timestamp); + static bool syncFirstFrame(int camera_id, uint64_t request_id, uint64_t raw_id, uint64_t timestamp, bool staggered); struct SyncData { uint64_t timestamp; uint64_t frame_id_offset = 0; + bool staggered = false; }; inline static std::map camera_sync_data; inline static bool first_frame_synced = false; diff --git a/system/camerad/test/test_camerad.py b/system/camerad/test/test_camerad.py index 5f8de86899..3abe4db654 100644 --- a/system/camerad/test/test_camerad.py +++ b/system/camerad/test/test_camerad.py @@ -105,17 +105,23 @@ class TestCamerad: assert set(np.diff(logs[c]['frameId'])) == {1, }, f"{c} has frame skips" def test_frame_sync(self, logs): + SYNCED_CAMS = ('roadCameraState', 'wideRoadCameraState') n = range(len(logs['roadCameraState']['t'][:-10])) frame_ids = {i: [logs[cam]['frameId'][i] for cam in CAMERAS] for i in n} assert all(len(set(v)) == 1 for v in frame_ids.values()), "frame IDs not aligned" - frame_times = {i: [logs[cam]['timestampSof'][i] for cam in CAMERAS] for i in n} - diffs = {i: (max(ts) - min(ts))/1e6 for i, ts in frame_times.items()} - + # road and wide cameras should be synced within 1.1ms + synced_times = {i: [logs[cam]['timestampSof'][i] for cam in SYNCED_CAMS] for i in n} + diffs = {i: (max(ts) - min(ts))/1e6 for i, ts in synced_times.items()} laggy_frames = {k: v for k, v in diffs.items() if v > 1.1} assert len(laggy_frames) == 0, f"Frames not synced properly: {laggy_frames=}" + # driver camera should be staggered ~25ms from road camera + for i in n: + offset_ms = abs(logs['driverCameraState']['timestampSof'][i] - logs['roadCameraState']['timestampSof'][i]) / 1e6 + assert 20 < offset_ms < 30, f"driver camera stagger out of range at frame {i}: {offset_ms:.1f}ms (expected ~25ms)" + def test_sanity_checks(self, logs): self._sanity_checks(logs) diff --git a/system/hardware/tici/agnos.json b/system/hardware/tici/agnos.json index e33a26bb2e..295b0279d9 100644 --- a/system/hardware/tici/agnos.json +++ b/system/hardware/tici/agnos.json @@ -56,28 +56,28 @@ }, { "name": "boot", - "url": "https://commadist.azureedge.net/agnosupdate/boot-a0185fa5ffc860de2179e4d0fec703fef6d560eacd730f79f60891ca79c72756.img.xz", - "hash": "a0185fa5ffc860de2179e4d0fec703fef6d560eacd730f79f60891ca79c72756", - "hash_raw": "a0185fa5ffc860de2179e4d0fec703fef6d560eacd730f79f60891ca79c72756", - "size": 17496064, + "url": "https://commadist.azureedge.net/agnosupdate/boot-d726315cf98a43e1090e5b49297404cf3d084cfbd42ad8bb7d8afb68136b9f51.img.xz", + "hash": "d726315cf98a43e1090e5b49297404cf3d084cfbd42ad8bb7d8afb68136b9f51", + "hash_raw": "d726315cf98a43e1090e5b49297404cf3d084cfbd42ad8bb7d8afb68136b9f51", + "size": 17500160, "sparse": false, "full_check": true, "has_ab": true, - "ondevice_hash": "0ee1ab104bb46d0f72e7d0b7d3e94629a7644a368896c6d4c558554fb955a08a" + "ondevice_hash": "2454108de1161289bc4a75449ad6421f1772b13b3e5cba68a84fca7530557699" }, { "name": "system", - "url": "https://commadist.azureedge.net/agnosupdate/system-0cf8cb01e40d05d6d325afe68b934a6c0dda3a56703b2ef3e3de637d754ae5dd.img.xz", - "hash": "7c58308be461126677ba02e9c9739556520ee02958934733867d86ecfe2e58e9", - "hash_raw": "0cf8cb01e40d05d6d325afe68b934a6c0dda3a56703b2ef3e3de637d754ae5dd", + "url": "https://commadist.azureedge.net/agnosupdate/system-dcdea6bd675d0276a63c25151727829620794baf42ada2e5e19a3f77b3f583a5.img.xz", + "hash": "5f319030ad05942267b77f1a4686c4ca24cc09b2c2a4688e57342ffc9720fd49", + "hash_raw": "dcdea6bd675d0276a63c25151727829620794baf42ada2e5e19a3f77b3f583a5", "size": 4718592000, "sparse": true, "full_check": false, "has_ab": true, - "ondevice_hash": "826790516410c325aa30265846946d06a556f0a7b23c957f65fd11c055a663da", + "ondevice_hash": "c12f1b7d790a418aea17424accf4cd59c575e5745cad82bdc9452f384483648c", "alt": { - "hash": "0cf8cb01e40d05d6d325afe68b934a6c0dda3a56703b2ef3e3de637d754ae5dd", - "url": "https://commadist.azureedge.net/agnosupdate/system-0cf8cb01e40d05d6d325afe68b934a6c0dda3a56703b2ef3e3de637d754ae5dd.img", + "hash": "dcdea6bd675d0276a63c25151727829620794baf42ada2e5e19a3f77b3f583a5", + "url": "https://commadist.azureedge.net/agnosupdate/system-dcdea6bd675d0276a63c25151727829620794baf42ada2e5e19a3f77b3f583a5.img", "size": 4718592000 } } diff --git a/system/hardware/tici/all-partitions.json b/system/hardware/tici/all-partitions.json index b6718fe97d..0801907a2d 100644 --- a/system/hardware/tici/all-partitions.json +++ b/system/hardware/tici/all-partitions.json @@ -339,62 +339,51 @@ }, { "name": "boot", - "url": "https://commadist.azureedge.net/agnosupdate/boot-a0185fa5ffc860de2179e4d0fec703fef6d560eacd730f79f60891ca79c72756.img.xz", - "hash": "a0185fa5ffc860de2179e4d0fec703fef6d560eacd730f79f60891ca79c72756", - "hash_raw": "a0185fa5ffc860de2179e4d0fec703fef6d560eacd730f79f60891ca79c72756", - "size": 17496064, + "url": "https://commadist.azureedge.net/agnosupdate/boot-d726315cf98a43e1090e5b49297404cf3d084cfbd42ad8bb7d8afb68136b9f51.img.xz", + "hash": "d726315cf98a43e1090e5b49297404cf3d084cfbd42ad8bb7d8afb68136b9f51", + "hash_raw": "d726315cf98a43e1090e5b49297404cf3d084cfbd42ad8bb7d8afb68136b9f51", + "size": 17500160, "sparse": false, "full_check": true, "has_ab": true, - "ondevice_hash": "0ee1ab104bb46d0f72e7d0b7d3e94629a7644a368896c6d4c558554fb955a08a" + "ondevice_hash": "2454108de1161289bc4a75449ad6421f1772b13b3e5cba68a84fca7530557699" }, { "name": "system", - "url": "https://commadist.azureedge.net/agnosupdate/system-0cf8cb01e40d05d6d325afe68b934a6c0dda3a56703b2ef3e3de637d754ae5dd.img.xz", - "hash": "7c58308be461126677ba02e9c9739556520ee02958934733867d86ecfe2e58e9", - "hash_raw": "0cf8cb01e40d05d6d325afe68b934a6c0dda3a56703b2ef3e3de637d754ae5dd", + "url": "https://commadist.azureedge.net/agnosupdate/system-dcdea6bd675d0276a63c25151727829620794baf42ada2e5e19a3f77b3f583a5.img.xz", + "hash": "5f319030ad05942267b77f1a4686c4ca24cc09b2c2a4688e57342ffc9720fd49", + "hash_raw": "dcdea6bd675d0276a63c25151727829620794baf42ada2e5e19a3f77b3f583a5", "size": 4718592000, "sparse": true, "full_check": false, "has_ab": true, - "ondevice_hash": "826790516410c325aa30265846946d06a556f0a7b23c957f65fd11c055a663da", + "ondevice_hash": "c12f1b7d790a418aea17424accf4cd59c575e5745cad82bdc9452f384483648c", "alt": { - "hash": "0cf8cb01e40d05d6d325afe68b934a6c0dda3a56703b2ef3e3de637d754ae5dd", - "url": "https://commadist.azureedge.net/agnosupdate/system-0cf8cb01e40d05d6d325afe68b934a6c0dda3a56703b2ef3e3de637d754ae5dd.img", + "hash": "dcdea6bd675d0276a63c25151727829620794baf42ada2e5e19a3f77b3f583a5", + "url": "https://commadist.azureedge.net/agnosupdate/system-dcdea6bd675d0276a63c25151727829620794baf42ada2e5e19a3f77b3f583a5.img", "size": 4718592000 } }, { "name": "userdata_90", - "url": "https://commadist.azureedge.net/agnosupdate/userdata_90-ec31b8116125a95755adb32853c401c462a14a74f538535532bf2c34d72c60eb.img.xz", - "hash": "aa0f0fe32187493e6135aee9e984d3f9705fc58560d537b34687bb6b51a38428", - "hash_raw": "ec31b8116125a95755adb32853c401c462a14a74f538535532bf2c34d72c60eb", + "url": "https://commadist.azureedge.net/agnosupdate/userdata_90-a7b25ea29255f4fd3a2da99e037f40b4ca10bd4afd57dd96563353b8dfb0f634.img.xz", + "hash": "7ea9d7d4685ec36bbfdf06afe0b51650d567416c3092fef96bd97158ed322742", + "hash_raw": "a7b25ea29255f4fd3a2da99e037f40b4ca10bd4afd57dd96563353b8dfb0f634", "size": 96636764160, "sparse": true, "full_check": true, "has_ab": false, - "ondevice_hash": "9c916b7d05543d4608b0401bc867639f44ce9671639a1a6da83b6d58b4eaa1b4" + "ondevice_hash": "79ed653c1679d84b13ee23083a511b0e668454e4af9b0db99a3279072ed041c1" }, { "name": "userdata_89", - "url": "https://commadist.azureedge.net/agnosupdate/userdata_89-7f092cc841124c10300e43574e90e3367e983bfbe4faa0969024e79e5ce90b11.img.xz", - "hash": "fa83d4b7096857136820b0b0a8785c90677256b054c5c14039cd7b9b1065a90b", - "hash_raw": "7f092cc841124c10300e43574e90e3367e983bfbe4faa0969024e79e5ce90b11", + "url": "https://commadist.azureedge.net/agnosupdate/userdata_89-8e428632c967aa609cac184bff938a90240e53ffd3b4fca40bc94c33c81202ba.img.xz", + "hash": "7104cdb0384e4ecb1ebfa6136a2330251bc8aa829b9ec48c4b740f656252d382", + "hash_raw": "8e428632c967aa609cac184bff938a90240e53ffd3b4fca40bc94c33c81202ba", "size": 95563022336, "sparse": true, "full_check": true, "has_ab": false, - "ondevice_hash": "1699e38de769eb32c21dfa6a5ac21eb3ad620a362c7b8abf1a2c0afe0f717530" - }, - { - "name": "userdata_30", - "url": "https://commadist.azureedge.net/agnosupdate/userdata_30-3df2dcd5e1f426c90b090fdbcd1a95b035d96a4bdaf88d5517245db5ee84f5ed.img.xz", - "hash": "890910f20b1ad88a728ee822a47b1234eb3d70cab28ca8a935679c8c2d33cbe9", - "hash_raw": "3df2dcd5e1f426c90b090fdbcd1a95b035d96a4bdaf88d5517245db5ee84f5ed", - "size": 32212254720, - "sparse": true, - "full_check": true, - "has_ab": false, - "ondevice_hash": "8e7cb392dd6e49c7d59fa850be7d1f44901314c86ba9c88be5bb27a0cd1123c9" + "ondevice_hash": "fbede3b0831dbc4a4edd336e5f547f4978902b9421fb1484e86c416192c59165" } ] \ No newline at end of file diff --git a/system/hardware/tici/updater_magic b/system/hardware/tici/updater_magic index 9674d85f00..44b82d0c54 100755 --- a/system/hardware/tici/updater_magic +++ b/system/hardware/tici/updater_magic @@ -1,3 +1,3 @@ version https://git-lfs.github.com/spec/v1 -oid sha256:d815a9140e69242d85e57f74a14c6372809eebefe8958be9152efa7874928ccc -size 71215510 +oid sha256:3a94ab8395f20d20a9d5a2a2bacca0694f072df8421cf13adca6250d28065bdc +size 24709205 diff --git a/system/qcomgpsd/qcomgpsd.py b/system/qcomgpsd/qcomgpsd.py index 59f5ac0b50..47d64ff4e9 100755 --- a/system/qcomgpsd/qcomgpsd.py +++ b/system/qcomgpsd/qcomgpsd.py @@ -7,7 +7,7 @@ import math import time import requests import shutil -import subprocess +from serial import Serial import datetime from multiprocessing import Process, Event from typing import NoReturn @@ -90,9 +90,24 @@ measurementStatusGlonassFields = { def try_setup_logs(diag, logs): return setup_logs(diag, logs) -@retry(attempts=3, delay=1.0) -def at_cmd(cmd: str) -> str | None: - return subprocess.check_output(f"mmcli -m any --timeout 30 --command='{cmd}'", shell=True, encoding='utf8') +AT_PORT = "/dev/modem_at0" + +@retry(attempts=5, delay=1.0) +def at_cmd(cmd: str) -> str: + with Serial(AT_PORT, baudrate=115200, timeout=5) as ser: + ser.reset_input_buffer() + ser.write(f"{cmd}\r".encode()) + lines = [] + while True: + line = ser.readline() + if not line: + raise RuntimeError(f"AT command timeout: {cmd}") + line = line.decode('utf-8', errors='replace').strip() + if line in ("OK", "ERROR") or line.startswith("+CME ERROR"): + break + if line and line != cmd: + lines.append(line) + return '\n'.join(lines) def gps_enabled() -> bool: return "QGPS: 1" in at_cmd("AT+QGPS?") @@ -131,6 +146,7 @@ def downloader_loop(event): @retry(attempts=5, delay=0.2, ignore_failure=True) def inject_assistance(): + import subprocess cmd = f"mmcli -m any --timeout 30 --location-inject-assistance-data={ASSIST_DATA_FILE}" subprocess.check_output(cmd, stderr=subprocess.PIPE, shell=True) cloudlog.info("successfully loaded assistance data") @@ -207,13 +223,19 @@ def teardown_quectel(diag): try_setup_logs(diag, []) -def wait_for_modem(cmd="AT+QGPS?"): +def wait_for_modem(): cloudlog.warning("waiting for modem to come up") + while not os.path.exists(AT_PORT): + time.sleep(0.5) + # wait until the modem GNSS subsystem responds while True: - ret = subprocess.call(f"mmcli -m any --timeout 10 --command=\"{cmd}\"", stdout=subprocess.DEVNULL, stderr=subprocess.DEVNULL, shell=True) - if ret == 0: - return - time.sleep(0.1) + try: + resp = at_cmd("AT+QGPS?") + if "+QGPS:" in resp: + return + except Exception: + pass + time.sleep(0.5) def main() -> NoReturn: @@ -335,6 +357,9 @@ def main() -> NoReturn: report = unpack_position(log_payload) if report["u_PosSource"] != 2: continue + # uint16_t max is an invalid sentinel value from the modem + if report['w_GpsWeekNumber'] >= 0xFFFF: + continue vNED = [report["q_FltVelEnuMps[1]"], report["q_FltVelEnuMps[0]"], -report["q_FltVelEnuMps[2]"]] vNEDsigma = [report["q_FltVelSigmaMps[1]"], report["q_FltVelSigmaMps[0]"], -report["q_FltVelSigmaMps[2]"]] diff --git a/system/qcomgpsd/tests/test_qcomgpsd.py b/system/qcomgpsd/tests/test_qcomgpsd.py index 2fc6205ea4..75e8707591 100644 --- a/system/qcomgpsd/tests/test_qcomgpsd.py +++ b/system/qcomgpsd/tests/test_qcomgpsd.py @@ -1,9 +1,7 @@ import os import pytest -import json import time import datetime -import subprocess import cereal.messaging as messaging from openpilot.system.qcomgpsd.qcomgpsd import at_cmd, wait_for_modem @@ -44,15 +42,13 @@ class TestRawgpsd: return self.sm.updated['qcomGnss'] def test_no_crash_double_command(self): + wait_for_modem() at_cmd("AT+QGPSDEL=0") at_cmd("AT+QGPSDEL=0") def test_wait_for_modem(self): os.system("sudo systemctl stop ModemManager") managed_processes['qcomgpsd'].start() - assert not self._wait_for_output(5) - - os.system("sudo systemctl restart ModemManager") assert self._wait_for_output(30) def test_startup_time(self, subtests): @@ -61,7 +57,7 @@ class TestRawgpsd: os.system("sudo systemctl stop systemd-resolved") with subtests.test(internet=internet): managed_processes['qcomgpsd'].start() - assert self._wait_for_output(7) + assert self._wait_for_output(30) managed_processes['qcomgpsd'].stop() def test_turns_off_gnss(self, subtests): @@ -71,14 +67,15 @@ class TestRawgpsd: time.sleep(s) managed_processes['qcomgpsd'].stop() - ls = subprocess.check_output("mmcli -m any --location-status --output-json", shell=True, encoding='utf-8') - loc_status = json.loads(ls) - assert set(loc_status['modem']['location']['enabled']) <= {'3gpp-lac-ci'} + wait_for_modem() + resp = at_cmd("AT+QGPS?") + assert "+QGPS: 0" in resp def check_assistance(self, should_be_loaded): # after QGPSDEL: '+QGPSXTRADATA: 0,"1980/01/05,19:00:00"' # after loading: '+QGPSXTRADATA: 10080,"2023/06/24,19:00:00"' + wait_for_modem() out = at_cmd("AT+QGPSXTRADATA?") out = out.split("+QGPSXTRADATA:")[1].split("'")[0].strip() valid_duration, injected_time_str = out.split(",", 1) @@ -92,20 +89,23 @@ class TestRawgpsd: assert injected_time_str[:] == '1980/01/05,19:00:00'[:] assert valid_duration == '0' + @pytest.mark.skip(reason="XTRA injection via QMI needs debugging on AGNOS 17") def test_assistance_loading(self): managed_processes['qcomgpsd'].start() - assert self._wait_for_output(10) + assert self._wait_for_output(30) managed_processes['qcomgpsd'].stop() self.check_assistance(True) + @pytest.mark.skip(reason="XTRA injection via QMI needs debugging on AGNOS 17") def test_no_assistance_loading(self): os.system("sudo systemctl stop systemd-resolved") managed_processes['qcomgpsd'].start() - assert self._wait_for_output(10) + assert self._wait_for_output(30) managed_processes['qcomgpsd'].stop() self.check_assistance(False) + @pytest.mark.skip(reason="XTRA injection via QMI needs debugging on AGNOS 17") def test_late_assistance_loading(self): os.system("sudo systemctl stop systemd-resolved") diff --git a/system/timed.py b/system/timed.py index b7131b04c0..c74ba51da5 100755 --- a/system/timed.py +++ b/system/timed.py @@ -5,7 +5,7 @@ import time from typing import NoReturn import cereal.messaging as messaging -from openpilot.common.time_helpers import min_date, system_time_valid +from openpilot.common.time_helpers import min_date, MAX_DATE, system_time_valid from openpilot.common.swaglog import cloudlog from openpilot.common.params import Params from openpilot.common.gps import get_gps_location_service @@ -52,7 +52,7 @@ def main() -> NoReturn: continue if not gps.hasFix: continue - if gps_time < min_date(): + if gps_time < min_date() or gps_time > MAX_DATE: continue set_time(gps_time) diff --git a/system/ui/lib/application.py b/system/ui/lib/application.py index 35aa6ff379..58edc0061a 100644 --- a/system/ui/lib/application.py +++ b/system/ui/lib/application.py @@ -1,5 +1,6 @@ import atexit import cffi +import math import os import queue import time @@ -96,7 +97,6 @@ FONT_DIR = ASSETS_DIR.joinpath("fonts") class FontWeight(StrEnum): - LIGHT = "Inter-Light.fnt" NORMAL = "Inter-Regular.fnt" if BIG_UI else "Inter-Medium.fnt" MEDIUM = "Inter-Medium.fnt" BOLD = "Inter-Bold.fnt" @@ -172,6 +172,10 @@ class MouseState: self._rk.keep_time() def _handle_mouse_event(self): + # TODO: read touch events from evdev directly to get real kernel timestamps. + # Polling at 140Hz with time.monotonic() causes timing jitter that makes scroll + # velocity oscillate (alternating high/low). Real timestamps would also let us + # detect swipe-stop-lift via event gaps instead of the fragile decel heuristic. for slot in range(MAX_TOUCH_SLOTS): mouse_pos = rl.get_touch_position(slot) x = mouse_pos.x / self._scale if self._scale != 1.0 else mouse_pos.x @@ -283,7 +287,7 @@ class GuiApplication(GuiApplicationExt): if self._scale != 1.0: rl.set_mouse_scale(1 / self._scale, 1 / self._scale) if needs_render_texture: - self._render_texture = rl.load_render_texture(self._width, self._height) + self._render_texture = rl.load_render_texture(self._scaled_width, self._scaled_height) rl.set_texture_filter(self._render_texture.texture, rl.TextureFilter.TEXTURE_FILTER_BILINEAR) if RECORD: @@ -294,13 +298,13 @@ class GuiApplication(GuiApplicationExt): '-nostats', # Suppress encoding progress '-f', 'rawvideo', # Input format '-pix_fmt', 'rgba', # Input pixel format - '-s', f'{self._width}x{self._height}', # Input resolution + '-s', f'{self._scaled_width}x{self._scaled_height}', # Input resolution '-r', str(fps), # Input frame rate '-i', 'pipe:0', # Input from stdin '-vf', 'vflip,format=yuv420p', # Flip vertically and convert to yuv420p '-r', str(output_fps), # Output frame rate (for speed multiplier) '-c:v', 'libx264', - '-preset', 'ultrafast', + '-preset', 'veryfast', '-crf', str(RECORD_QUALITY) ] if RECORD_BITRATE: @@ -324,6 +328,7 @@ class GuiApplication(GuiApplicationExt): self._set_styles() self._load_fonts() self._patch_text_functions() + self._patch_scissor_mode() if BURN_IN_MODE and self._burn_in_shader is None: self._burn_in_shader = rl.load_shader_from_memory(BURN_IN_VERTEX_SHADER, BURN_IN_FRAGMENT_SHADER) @@ -459,6 +464,12 @@ class GuiApplication(GuiApplicationExt): with as_file(ASSETS_DIR.joinpath(asset_path)) as fspath: image_obj = self._load_image_from_path(fspath.as_posix(), width, height, alpha_premultiply, keep_aspect_ratio, flip_x) texture_obj = self._load_texture_from_image(image_obj) + + # Set logical size so widget layout math stays at 1x coordinates + if self._scale != 1.0 and width is not None and height is not None: + texture_obj.width = width + texture_obj.height = height + self._textures[cache_key] = texture_obj return texture_obj @@ -470,6 +481,11 @@ class GuiApplication(GuiApplicationExt): if alpha_premultiply: rl.image_alpha_premultiply(image) + # Scale up load size for sharper rendering, capped at source resolution + if self._scale != 1.0 and width is not None and height is not None: + width = min(int(width * self._scale), image.width) + height = min(int(height * self._scale), image.height) + if width is not None and height is not None: same_dimensions = image.width == width and image.height == height @@ -593,6 +609,10 @@ class GuiApplication(GuiApplicationExt): rl.begin_drawing() rl.clear_background(rl.BLACK) + if self._scale != 1.0: + rl.rl_push_matrix() + rl.rl_scalef(self._scale, self._scale, 1.0) + # Allow a Widget to still run a function regardless of the stack depth for tick in self._nav_stack_ticks: tick() @@ -603,11 +623,14 @@ class GuiApplication(GuiApplicationExt): yield True + if self._scale != 1.0: + rl.rl_pop_matrix() + if self._render_texture: rl.end_texture_mode() rl.begin_drawing() rl.clear_background(rl.BLACK) - src_rect = rl.Rectangle(0, 0, float(self._width), -float(self._height)) + src_rect = rl.Rectangle(0, 0, float(self._scaled_width), -float(self._scaled_height)) dst_rect = rl.Rectangle(0, 0, float(self._scaled_width), float(self._scaled_height)) texture = self._render_texture.texture if texture: @@ -664,7 +687,8 @@ class GuiApplication(GuiApplicationExt): fnt_path = fspath / font_weight_file font = rl.load_font(fnt_path.as_posix()) if font_weight_file != FontWeight.UNIFONT: - rl.set_texture_filter(font.texture, rl.TextureFilter.TEXTURE_FILTER_BILINEAR) + rl.gen_texture_mipmaps(font.texture) + rl.set_texture_filter(font.texture, rl.TextureFilter.TEXTURE_FILTER_TRILINEAR) self._fonts[font_weight_file] = font rl.gui_set_font(self._fonts[FontWeight.NORMAL]) @@ -686,6 +710,20 @@ class GuiApplication(GuiApplicationExt): rl.draw_text_ex = _draw_text_ex_scaled + def _patch_scissor_mode(self): + if self._scale == 1.0: + return + + if not hasattr(rl, "_orig_begin_scissor_mode"): + rl._orig_begin_scissor_mode = rl.begin_scissor_mode + + def _begin_scissor_mode_scaled(x, y, width, height): + return rl._orig_begin_scissor_mode( + int(x * self._scale), int(y * self._scale), + int(math.ceil(width * self._scale)), int(math.ceil(height * self._scale))) + + rl.begin_scissor_mode = _begin_scissor_mode_scaled + def _set_log_callback(self): ffi_libc = cffi.FFI() ffi_libc.cdef(""" diff --git a/system/ui/lib/scroll_panel2.py b/system/ui/lib/scroll_panel2.py index e2a548ba26..18fd8a9a67 100644 --- a/system/ui/lib/scroll_panel2.py +++ b/system/ui/lib/scroll_panel2.py @@ -20,6 +20,21 @@ MAX_SPEED = 10000.0 # px/s DEBUG = os.getenv("DEBUG_SCROLL", "0") == "1" +# Weights older (steadier) velocity samples more heavily on release. +# Finger-lift samples are noisy; trusting earlier samples gives consistent fling velocity. +# Reverse-engineered from iOS UIScrollView (tuned at 120Hz touch) by Flutter team: +# https://github.com/flutter/flutter/pull/60501 +# 3 samples ≈ 25ms at 120Hz (iOS) / ~21ms at 140Hz (comma). Scale if touch rate changes. +def weighted_velocity(buffer: deque) -> float: + if len(buffer) >= 3: + return buffer[-3] * 0.6 + buffer[-2] * 0.35 + buffer[-1] * 0.05 + elif len(buffer) == 2: + return buffer[-2] * 0.7 + buffer[-1] * 0.3 + elif len(buffer) == 1: + return buffer[-1] + return 0.0 + + # from https://ariya.io/2011/10/flick-list-with-its-momentum-scrolling-and-deceleration class ScrollState(Enum): STEADY = 0 @@ -151,7 +166,13 @@ class GuiScrollPanel2: # Touch rejection: when releasing finger after swiping and stopping, panel # reports a few erroneous touch events with high velocity, try to ignore. - # If velocity decelerates very quickly, assume user doesn't intend to auto scroll + # If velocity decelerates very quickly, assume user doesn't intend to auto scroll. + # Catches two cases: 1) swipe, stop finger, then lift (stale high velocity in buffer) + # 2) dirty finger lift where finger rotates/slides producing spurious velocity spike. + # TODO: this heuristic false-positives on fast swipes because 140Hz touch polling + # jitter causes velocity to oscillate (not real deceleration). Better approaches: + # - Use evdev kernel timestamps to eliminate velocity oscillation at the source + # - Replace with a time-since-last-event check (40ms timeout) for swipe-stop-lift high_decel = False if len(self._velocity_buffer) > 2: # We limit max to first half since final few velocities can surpass first few @@ -166,6 +187,8 @@ class GuiScrollPanel2: print('deceleration too high, going to STEADY') high_decel = True + self._velocity = weighted_velocity(self._velocity_buffer) + # If final velocity is below some threshold, switch to steady state too low_speed = abs(self._velocity) <= MIN_VELOCITY_FOR_CLICKING * 1.5 # plus some margin diff --git a/system/ui/lib/wifi_manager.py b/system/ui/lib/wifi_manager.py index 1084e9e533..b83f7bacc9 100644 --- a/system/ui/lib/wifi_manager.py +++ b/system/ui/lib/wifi_manager.py @@ -854,8 +854,12 @@ class WifiManager: # NOTE: AccessPoints property may exclude hidden APs (use GetAllAccessPoints method if needed) wifi_addr = DBusAddress(self._wifi_device, NM, interface=NM_WIRELESS_IFACE) - wifi_props = self._router_main.send_and_get_reply(Properties(wifi_addr).get_all()).body[0] - ap_paths = wifi_props.get('AccessPoints', ('ao', []))[1] + wifi_props_reply = self._router_main.send_and_get_reply(Properties(wifi_addr).get_all()) + if wifi_props_reply.header.message_type == MessageType.error: + cloudlog.warning(f"Failed to get WiFi properties: {wifi_props_reply}") + return + + ap_paths = wifi_props_reply.body[0].get('AccessPoints', ('ao', []))[1] aps: dict[str, list[AccessPoint]] = {} diff --git a/system/ui/mici_reset.py b/system/ui/mici_reset.py index 5ad959badb..9cc6e7f3f8 100755 --- a/system/ui/mici_reset.py +++ b/system/ui/mici_reset.py @@ -1,18 +1,17 @@ #!/usr/bin/env python3 import os import sys -import threading import time +import threading from enum import IntEnum import pyray as rl -from openpilot.system.hardware import PC -from openpilot.system.ui.lib.application import gui_app, FontWeight -from openpilot.system.ui.widgets import Widget -from openpilot.system.ui.widgets.slider import SmallSlider -from openpilot.system.ui.widgets.button import SmallButton, FullRoundedButton -from openpilot.system.ui.widgets.label import gui_label, gui_text_box +from openpilot.system.hardware import HARDWARE, PC +from openpilot.system.ui.lib.application import gui_app +from openpilot.system.ui.widgets.scroller import Scroller +from openpilot.system.ui.mici_setup import GreyBigButton, FailedPage +from openpilot.selfdrive.ui.mici.widgets.dialog import BigDialog, BigConfirmationCircleButton USERDATA = "/dev/disk/by-partlabel/userdata" TIMEOUT = 3*60 @@ -21,35 +20,85 @@ TIMEOUT = 3*60 class ResetMode(IntEnum): USER_RESET = 0 # user initiated a factory reset from openpilot RECOVER = 1 # userdata is corrupt for some reason, give a chance to recover - FORMAT = 2 # finish up a factory reset from a tool that doesn't flash an empty partition to userdata + TAP_RESET = 2 # user initiated a factory reset by tapping the screen during boot -class ResetState(IntEnum): - NONE = 0 - RESETTING = 1 - FAILED = 2 +class ResetFailedPage(FailedPage): + def __init__(self): + super().__init__(None, "reset failed", "reboot to try again", icon="icons_mici/setup/reset_failed.png") + + def show_event(self): + super().show_event() + self._nav_bar._alpha = 0.0 # not dismissable + + def _back_enabled(self) -> bool: + return False -class Reset(Widget): +class ResettingPage(BigDialog): + DOT_STEP = 0.6 + + def __init__(self): + super().__init__("resetting device", "this may take up to\na minute...", + gui_app.texture("icons_mici/setup/factory_reset.png", 64, 64)) + self._show_time = 0.0 + + def show_event(self): + super().show_event() + self._nav_bar._alpha = 0.0 # not dismissable + self._show_time = rl.get_time() + + def _back_enabled(self) -> bool: + return False + + def _render(self, _): + t = (rl.get_time() - self._show_time) % (self.DOT_STEP * 2) + dots = "." * min(int(t / (self.DOT_STEP / 4)), 3) + self._card.set_value(f"this may take up to\na minute{dots}") + super()._render(_) + + +class Reset(Scroller): def __init__(self, mode): super().__init__() self._mode = mode - self._previous_reset_state = None - self._reset_state = ResetState.NONE + self._previous_active_widget = None + self._reset_failed = False + self._timeout_st = time.monotonic() - self._cancel_button = SmallButton("cancel") - self._cancel_button.set_click_callback(gui_app.request_close) + self._resetting_page = ResettingPage() + self._reset_failed_page = ResetFailedPage() - self._reboot_button = FullRoundedButton("reboot") - self._reboot_button.set_click_callback(self._do_reboot) + self._reset_button = BigConfirmationCircleButton("reset &\nerase", gui_app.texture("icons_mici/settings/device/uninstall.png", 70, 70), + self._start_reset, exit_on_confirm=False, red=True) + self._cancel_button = BigConfirmationCircleButton("cancel", gui_app.texture("icons_mici/setup/cancel.png", 64, 64), + gui_app.request_close, exit_on_confirm=False) + self._reboot_button = BigConfirmationCircleButton("reboot\ndevice", gui_app.texture("icons_mici/settings/device/reboot.png", 64, 70), + HARDWARE.reboot, exit_on_confirm=False) - self._confirm_slider = SmallSlider("reset", self._confirm) + # show reboot button if in recover mode + self._cancel_button.set_visible(mode != ResetMode.RECOVER) + self._reboot_button.set_visible(mode == ResetMode.RECOVER) - def _do_reboot(self): - if PC: - return + main_card = GreyBigButton("factory reset", "resetting erases\nall user content & data", + gui_app.texture("icons_mici/setup/factory_reset.png", 64, 64)) + self._scroller.add_widget(main_card) - os.system("sudo reboot") + if mode != ResetMode.USER_RESET: + self._scroller.add_widget(GreyBigButton("", "Resetting erases all user content & data.")) + if mode == ResetMode.RECOVER: + main_card.set_value("user data partition\ncould not be mounted") + elif mode == ResetMode.TAP_RESET: + main_card.set_value("reset triggered by\ntapping the screen") + + self._scroller.add_widgets([ + GreyBigButton("", "For a deeper reset, go to\nhttps://flash.comma.ai"), + self._cancel_button, + self._reboot_button, + self._reset_button, + ]) + + gui_app.add_nav_stack_tick(self._nav_stack_tick) def _do_erase(self): if PC: @@ -63,87 +112,38 @@ class Reset(Widget): if rm == 0 or fmt == 0: os.system("sudo reboot") else: - self._reset_state = ResetState.FAILED + self._reset_failed = True - def start_reset(self): - self._reset_state = ResetState.RESETTING - threading.Timer(0.1, self._do_erase).start() + def _start_reset(self): + def do_erase_thread(): + threading.Thread(target=self._do_erase, daemon=True).start() - def _update_state(self): - if self._reset_state != self._previous_reset_state: - self._previous_reset_state = self._reset_state + self._resetting_page.set_shown_callback(do_erase_thread) + gui_app.push_widget(self._resetting_page) + + def _nav_stack_tick(self): + if self._reset_failed: + self._reset_failed = False + gui_app.pop_widgets_to(self, lambda: gui_app.push_widget(self._reset_failed_page)) + + active_widget = gui_app.get_active_widget() + if active_widget != self._previous_active_widget: + self._previous_active_widget = active_widget self._timeout_st = time.monotonic() - elif self._reset_state != ResetState.RESETTING and (time.monotonic() - self._timeout_st) > TIMEOUT: + elif self._mode != ResetMode.RECOVER and active_widget != self._resetting_page and (time.monotonic() - self._timeout_st) > TIMEOUT: exit(0) - def _render(self, rect: rl.Rectangle): - label_rect = rl.Rectangle(rect.x + 8, rect.y + 8, rect.width, 50) - gui_label(label_rect, "factory reset", 48, font_weight=FontWeight.BOLD, - color=rl.Color(255, 255, 255, int(255 * 0.9))) - - text_rect = rl.Rectangle(rect.x + 8, rect.y + 56, rect.width - 8 * 2, rect.height - 80) - gui_text_box(text_rect, self._get_body_text(), 36, font_weight=FontWeight.ROMAN, line_scale=0.9) - - if self._reset_state != ResetState.RESETTING: - # fade out cancel button as slider is moved, set visible to prevent pressing invisible cancel - self._cancel_button.set_opacity(1.0 - self._confirm_slider.slider_percentage) - self._cancel_button.set_visible(self._confirm_slider.slider_percentage < 0.8) - - if self._mode == ResetMode.RECOVER: - self._cancel_button.set_text("reboot") - self._cancel_button.set_click_callback(self._do_reboot) - self._cancel_button.render(rl.Rectangle( - rect.x + 8, - rect.y + rect.height - self._cancel_button.rect.height, - self._cancel_button.rect.width, - self._cancel_button.rect.height)) - elif self._mode == ResetMode.USER_RESET and self._reset_state != ResetState.FAILED: - self._cancel_button.render(rl.Rectangle( - rect.x + 8, - rect.y + rect.height - self._cancel_button.rect.height, - self._cancel_button.rect.width, - self._cancel_button.rect.height)) - - if self._reset_state != ResetState.FAILED: - self._confirm_slider.render(rl.Rectangle( - rect.x + rect.width - self._confirm_slider.rect.width, - rect.y + rect.height - self._confirm_slider.rect.height, - self._confirm_slider.rect.width, - self._confirm_slider.rect.height)) - else: - self._reboot_button.render(rl.Rectangle( - rect.x + 8, - rect.y + rect.height - self._reboot_button.rect.height, - self._reboot_button.rect.width, - self._reboot_button.rect.height)) - - def _confirm(self): - self.start_reset() - - def _get_body_text(self): - if self._reset_state == ResetState.RESETTING: - return "Resetting device... This may take up to a minute." - if self._reset_state == ResetState.FAILED: - return "Reset failed. Reboot to try again." - if self._mode == ResetMode.RECOVER: - return "Unable to mount data partition. It may be corrupted." - return "All content and settings will be erased." - def main(): mode = ResetMode.USER_RESET if len(sys.argv) > 1: if sys.argv[1] == '--recover': mode = ResetMode.RECOVER - elif sys.argv[1] == "--format": - mode = ResetMode.FORMAT + elif sys.argv[1] == '--tap-reset': + mode = ResetMode.TAP_RESET gui_app.init_window("System Reset") reset = Reset(mode) - - if mode == ResetMode.FORMAT: - reset.start_reset() - gui_app.push_widget(reset) for _ in gui_app.render(): diff --git a/system/ui/mici_setup.py b/system/ui/mici_setup.py index fd873109f1..d04f08ca37 100755 --- a/system/ui/mici_setup.py +++ b/system/ui/mici_setup.py @@ -1,61 +1,52 @@ #!/usr/bin/env python3 import os import re +import ssl import threading import time import urllib.request import urllib.error from urllib.parse import urlparse -import shutil from collections.abc import Callable import pyray as rl from cereal import log -from openpilot.common.filter_simple import FirstOrderFilter +from openpilot.common.filter_simple import BounceFilter from openpilot.system.hardware import HARDWARE, TICI from openpilot.common.realtime import config_realtime_process, set_core_affinity from openpilot.common.swaglog import cloudlog +from openpilot.common.time_helpers import system_time_valid from openpilot.common.utils import run_cmd from openpilot.system.ui.lib.application import gui_app, FontWeight -from openpilot.system.ui.lib.wifi_manager import WifiManager +from openpilot.system.ui.lib.wifi_manager import WifiManager, ConnectStatus from openpilot.system.ui.widgets import Widget from openpilot.system.ui.widgets.nav_widget import NavWidget -from openpilot.system.ui.widgets.button import SmallButton from openpilot.system.ui.widgets.label import UnifiedLabel from openpilot.system.ui.widgets.scroller import Scroller, NavScroller, ITEM_SPACING -from openpilot.system.ui.widgets.slider import LargerSlider, SmallSlider +from openpilot.system.ui.widgets.slider import LargerSlider from openpilot.selfdrive.ui.mici.layouts.settings.network import WifiNetworkButton from openpilot.selfdrive.ui.mici.layouts.settings.network.wifi_ui import WifiUIMici -from openpilot.selfdrive.ui.mici.widgets.dialog import BigInputDialog -from openpilot.selfdrive.ui.mici.widgets.button import BigButton +from openpilot.selfdrive.ui.mici.widgets.dialog import BigInputDialog, BigConfirmationCircleButton +from openpilot.selfdrive.ui.mici.widgets.button import BigButton, GreyBigButton NetworkType = log.DeviceState.NetworkType OPENPILOT_URL = "https://openpilot.comma.ai" USER_AGENT = f"AGNOSSetup-{HARDWARE.get_os_version()}" -CONTINUE_PATH = "/data/continue.sh" -TMP_CONTINUE_PATH = "/data/continue.sh.new" -INSTALL_PATH = "/data/openpilot" -VALID_CACHE_PATH = "/data/.openpilot_cache" -INSTALLER_SOURCE_PATH = "/usr/comma/installer" INSTALLER_DESTINATION_PATH = "/tmp/installer" INSTALLER_URL_PATH = "/tmp/installer_url" -CONTINUE = """#!/usr/bin/env bash - -cd /data/openpilot -exec ./launch_openpilot.sh -""" - class NetworkConnectivityMonitor: def __init__(self, should_check: Callable[[], bool] | None = None): self.network_connected = threading.Event() self.wifi_connected = threading.Event() + self.recheck_event = threading.Event() self._should_check = should_check or (lambda: True) self._stop_event = threading.Event() + self._last_timesyncd_restart = 0.0 self._thread: threading.Thread | None = None def start(self): @@ -74,15 +65,32 @@ class NetworkConnectivityMonitor: self.network_connected.clear() self.wifi_connected.clear() + def invalidate(self): + self.recheck_event.set() + self.reset() + def _run(self): while not self._stop_event.is_set(): if self._should_check(): try: request = urllib.request.Request(OPENPILOT_URL, method="HEAD") urllib.request.urlopen(request, timeout=2.0) + + # Discard stale result if invalidated during request + if self.recheck_event.is_set(): + self.recheck_event.clear() + continue + self.network_connected.set() if HARDWARE.get_network_type() == NetworkType.wifi: self.wifi_connected.set() + except urllib.error.URLError as e: + if (isinstance(e.reason, ssl.SSLCertVerificationError) and + not system_time_valid() and + time.monotonic() - self._last_timesyncd_restart > 5): + self._last_timesyncd_restart = time.monotonic() + run_cmd(["sudo", "systemctl", "restart", "systemd-timesyncd"]) + self.reset() except Exception: self.reset() else: @@ -102,7 +110,7 @@ class StartPage(Widget): self._start_bg_txt = gui_app.texture("icons_mici/setup/start_button.png", 500, 224, keep_aspect_ratio=False) self._start_bg_pressed_txt = gui_app.texture("icons_mici/setup/start_button_pressed.png", 500, 224, keep_aspect_ratio=False) - self._scale_filter = FirstOrderFilter(1.0, 0.1, 1 / gui_app.target_fps) + self._scale_filter = BounceFilter(1.0, 0.1, 1 / gui_app.target_fps) self._click_delay = 0.075 def _render(self, rect: rl.Rectangle): @@ -122,9 +130,9 @@ class SoftwareSelectionPage(NavWidget): use_custom_software_callback: Callable): super().__init__() - self._openpilot_slider = LargerSlider("slide to install\nopenpilot", use_openpilot_callback) + self._openpilot_slider = self._child(LargerSlider("slide to install\nopenpilot", use_openpilot_callback)) self._openpilot_slider.set_enabled(lambda: self.enabled and not self.is_dismissing) - self._custom_software_slider = LargerSlider("slide to install\nother software", use_custom_software_callback, green=False) + self._custom_software_slider = self._child(LargerSlider("slide to install\ncustom software", use_custom_software_callback, green=False, shimmer_offset=0.4)) self._custom_software_slider.set_enabled(lambda: self.enabled and not self.is_dismissing) def show_event(self): @@ -170,18 +178,19 @@ class CustomSoftwareWarningPage(NavScroller): self._continue_button.set_click_callback(continue_callback) self._scroller.add_widgets([ - GreyBigButton("use caution", "when installing\n3rd party software", + GreyBigButton("caution: installing\n3rd party software", "swipe down to go back", gui_app.texture("icons_mici/setup/warning.png", 64, 58)), - GreyBigButton("", "• It has not been tested by comma"), - GreyBigButton("", "• It may not comply with relevant safety standards."), - GreyBigButton("", "• It may cause damage to your device and/or vehicle."), + GreyBigButton("", "• It has not been tested by comma."), + GreyBigButton("", "• It may not comply with safety standards."), + GreyBigButton("", "• It may damage your device and/or vehicle."), GreyBigButton("how to restore to a\nfactory state later", "https://flash.comma.ai", gui_app.texture("icons_mici/setup/restore.png", 64, 64)), self._continue_button, ]) -class DownloadingPage(Widget): +# TODO: unifi with updater's progress page +class DownloadingPage(NavWidget): def __init__(self): super().__init__() @@ -191,8 +200,12 @@ class DownloadingPage(Widget): font_weight=FontWeight.ROMAN, alignment_vertical=rl.GuiTextAlignmentVertical.TEXT_ALIGN_BOTTOM) self._progress = 0 + def _back_enabled(self) -> bool: + return False + def show_event(self): super().show_event() + self._nav_bar._alpha = 0.0 # not dismissable self.set_progress(0) def set_progress(self, progress: int): @@ -216,97 +229,29 @@ class DownloadingPage(Widget): )) -class FailedPageBase(Widget): - def __init__(self, reboot_callback: Callable, retry_callback: Callable, title: str = "download failed"): +class FailedPage(NavScroller): + def __init__(self, retry_callback: Callable | None, title: str = "download failed", + description: str | None = None, icon: str = "icons_mici/setup/warning.png"): super().__init__() - self._title_label = UnifiedLabel(title, 64, text_color=rl.Color(255, 255, 255, int(255 * 0.9)), - font_weight=FontWeight.DISPLAY) - self._reason_label = UnifiedLabel("", 36, text_color=rl.Color(255, 255, 255, int(255 * 0.9 * 0.65)), - font_weight=FontWeight.ROMAN) - - self._reboot_slider = SmallSlider("reboot", reboot_callback) - self._reboot_slider.set_enabled(lambda: self.enabled) # for nav stack - - self._retry_button = SmallButton("retry") - self._retry_button.set_click_callback(retry_callback) - self._retry_button.set_enabled(lambda: self.enabled) # for nav stack - - def set_reason(self, reason: str): - self._reason_label.set_text(reason) - - def show_event(self): - super().show_event() - self._reboot_slider.reset() - - def _render(self, rect: rl.Rectangle): - self._title_label.render(rl.Rectangle( - rect.x + 8, - rect.y + 10, - rect.width, - 64, - )) - - self._reason_label.render(rl.Rectangle( - rect.x + 8, - rect.y + 10 + 64, - rect.width, - 36, - )) - - self._retry_button.set_opacity(1 - self._reboot_slider.slider_percentage) - self._retry_button.render(rl.Rectangle( - self._rect.x + 8, - self._rect.y + self._rect.height - self._retry_button.rect.height, - self._retry_button.rect.width, - self._retry_button.rect.height, - )) - - self._reboot_slider.render(rl.Rectangle( - self._rect.x + self._rect.width - self._reboot_slider.rect.width, - self._rect.y + self._rect.height - self._reboot_slider.rect.height, - self._reboot_slider.rect.width, - self._reboot_slider.rect.height, - )) - - -class FailedPage(FailedPageBase, NavWidget): - def __init__(self, reboot_callback: Callable, retry_callback: Callable, title: str = "download failed"): - super().__init__(reboot_callback, retry_callback, title) self.set_back_callback(retry_callback) + self._reason_card = GreyBigButton("", "") + self._reason_card.set_visible(False) -class GreyBigButton(BigButton): - """Users should manage newlines with this class themselves""" + self._scroller.add_widgets([ + GreyBigButton(title, description or "swipe down to go\nback and try again", + gui_app.texture(icon, 64, 58)), + self._reason_card, + BigConfirmationCircleButton("reboot\ndevice", gui_app.texture("icons_mici/settings/device/reboot.png", 64, 70), + HARDWARE.reboot, exit_on_confirm=False), + ]) - LABEL_HORIZONTAL_PADDING = 30 - - def __init__(self, *args, **kwargs): - super().__init__(*args, **kwargs) - self.set_touch_valid_callback(lambda: False) - - self._rect.width = 476 - - self._label.set_font_size(36) - self._label.set_font_weight(FontWeight.BOLD) - self._label.set_line_height(1.0) - - self._sub_label.set_font_size(36) - self._sub_label.set_text_color(rl.Color(255, 255, 255, int(255 * 0.9))) - self._sub_label.set_font_weight(FontWeight.DISPLAY_REGULAR) - self._sub_label.set_alignment_vertical(rl.GuiTextAlignmentVertical.TEXT_ALIGN_MIDDLE if not self._label.text else - rl.GuiTextAlignmentVertical.TEXT_ALIGN_BOTTOM) - self._sub_label.set_line_height(0.95) - - @property - def LABEL_VERTICAL_PADDING(self): - return BigButton.LABEL_VERTICAL_PADDING if self._label.text else 18 - - def _width_hint(self) -> int: - return int(self._rect.width - self.LABEL_HORIZONTAL_PADDING * 2) - - def _render(self, _): - rl.draw_rectangle_rounded(self._rect, 0.4, 10, rl.Color(255, 255, 255, int(255 * 0.15))) - self._draw_content(self._rect.y) + def set_reason(self, reason: str): + if reason: + self._reason_card.set_value(reason) + self._reason_card.set_visible(True) + else: + self._reason_card.set_visible(False) class BigPillButton(BigButton): @@ -354,7 +299,6 @@ class NetworkSetupPageBase(Scroller): self._wifi_manager.set_active(True) self._network_monitor = network_monitor self._custom_software = False - self._prev_has_internet = False self._wifi_ui = WifiUIMici(self._wifi_manager) self._connect_button = GreyBigButton("connect to\ninternet", "swipe down to go back", @@ -364,8 +308,9 @@ class NetworkSetupPageBase(Scroller): self._wifi_button = WifiNetworkButton(self._wifi_manager) self._wifi_button.set_click_callback(lambda: gui_app.push_widget(self._wifi_ui)) - self._show_time = 0.0 - self._pending_has_internet_scroll = False + self._prev_has_internet = False + self._prev_wifi_connected = False + self._pending_has_internet_scroll: float | None = None # stores time to use as delay self._pending_continue_grow_animation = False self._pending_wifi_grow_animation = False @@ -375,7 +320,7 @@ class NetworkSetupPageBase(Scroller): # trigger grow when wifi button in view self._pending_wifi_grow_animation = True - self._waiting_button = BigPillButton("waiting for\ninternet...", disabled_background=True) + self._waiting_button = BigPillButton("connect to\ncontinue", disabled_background=True) self._waiting_button.set_click_callback(on_waiting_click) self._continue_button = BigPillButton("install openpilot", green=True) self._continue_button.set_click_callback(lambda: continue_callback(self._custom_software)) @@ -391,45 +336,77 @@ class NetworkSetupPageBase(Scroller): def show_event(self): super().show_event() - self._show_time = rl.get_time() - self._prev_has_internet = False - self._pending_has_internet_scroll = False + # make sure we populate strength and ip immediately if already have wifi + self._wifi_manager.set_active(True) + self._prev_has_internet = self._has_internet + self._prev_wifi_connected = self._wifi_manager.wifi_state.status == ConnectStatus.CONNECTED + self._pending_has_internet_scroll = None self._pending_continue_grow_animation = False self._pending_wifi_grow_animation = False + if self._prev_has_internet or self._prev_wifi_connected: + self.set_shown_callback(lambda: self._scroll_to_end_and_grow()) + + @property + def _has_internet(self) -> bool: + network_changing = self._wifi_ui.any_network_forgetting or self._wifi_manager.wifi_state.status == ConnectStatus.CONNECTING + if network_changing: + self._network_monitor.invalidate() + + has_internet = (self._network_monitor.network_connected.is_set() and + not network_changing and + not self._network_monitor.recheck_event.is_set()) + return has_internet + def _nav_stack_tick(self): + # Only run tick when this page or its WiFi UI is on the stack + if gui_app.get_active_widget() is not self and not gui_app.widget_in_stack(self._wifi_ui): + self._wifi_manager.process_callbacks() + return + + # Check network state before processing callbacks so forgetting flag + # is still set on the frame the forgotten callback fires + has_internet = self._has_internet + wifi_connected = self._wifi_manager.wifi_state.status == ConnectStatus.CONNECTED + + self._continue_button.set_visible(has_internet) + self._waiting_button.set_visible(not has_internet) + + # TODO: fire show/hide events on visibility changes + if not has_internet: + self._pending_continue_grow_animation = False + self._waiting_button.set_text("waiting for\ninternet..." if wifi_connected else "connect to\ncontinue") + self._wifi_manager.process_callbacks() - has_internet = self._network_monitor.network_connected.is_set() - if has_internet and not self._prev_has_internet: - self._pending_has_internet_scroll = True + # Dismiss WiFi UI and scroll on WiFi connect or internet gain + if (has_internet and not self._prev_has_internet) or (wifi_connected and not self._prev_wifi_connected): + # TODO: cancel if connect is transient + self._pending_has_internet_scroll = rl.get_time() + self._prev_has_internet = has_internet + self._prev_wifi_connected = wifi_connected - if self._pending_has_internet_scroll: + if self._pending_has_internet_scroll is not None: # Scrolls over to continue button, then grows once in view - elapsed = rl.get_time() - self._show_time - if elapsed > 0.5: - self._pending_has_internet_scroll = False - - def scroll_to_download(): - self._scroller._layout() - end_offset = -(self._scroller.content_size - self._rect.width) - remaining = self._scroller.scroll_panel.get_offset() - end_offset - self._scroller.scroll_to(remaining, smooth=True, block_interaction=True) - self._pending_continue_grow_animation = True - + elapsed = rl.get_time() - self._pending_has_internet_scroll + if elapsed > 0.7 or gui_app.get_active_widget() is self: # instant scroll + grow if not popping # Animate WifiUi down first before scroll - gui_app.pop_widgets_to(self, scroll_to_download) + self._pending_has_internet_scroll = None + gui_app.pop_widgets_to(self, self._scroll_to_end_and_grow) + + def _scroll_to_end_and_grow(self): + self._scroller._layout() + end_offset = -(self._scroller.content_size - self._rect.width) + remaining = self._scroller.scroll_panel.get_offset() - end_offset + self._scroller.scroll_to(remaining, smooth=True, block_interaction=True) + self._pending_continue_grow_animation = True def set_custom_software(self, custom_software: bool): self._custom_software = custom_software self._continue_button.set_text("install openpilot" if not custom_software else "choose software") self._continue_button.set_green(not custom_software) - def set_is_updater(self): - self._continue_button.set_text("download\n& install") - self._continue_button.set_green(False) - def _update_state(self): super()._update_state() @@ -444,13 +421,6 @@ class NetworkSetupPageBase(Scroller): self._pending_wifi_grow_animation = False self._wifi_button.trigger_grow_animation() - if self._network_monitor.network_connected.is_set(): - self._continue_button.set_visible(True) - self._waiting_button.set_visible(False) - else: - self._continue_button.set_visible(False) - self._waiting_button.set_visible(True) - class NetworkSetupPage(NetworkSetupPageBase, NavScroller): def __init__(self, network_monitor: NetworkConnectivityMonitor, continue_callback: Callable[[bool], None], @@ -471,7 +441,6 @@ class Setup(Widget): self._network_monitor.start() def getting_started_button_callback(): - self._software_selection_page.reset() gui_app.push_widget(self._software_selection_page) self._start_page = StartPage() @@ -480,9 +449,9 @@ class Setup(Widget): self._network_setup_page = NetworkSetupPage(self._network_monitor, self._network_setup_continue_callback, self._pop_to_software_selection) - self._software_selection_page = SoftwareSelectionPage(self._use_openpilot, lambda: gui_app.push_widget(self._custom_software_warning_page)) + self._software_selection_page = SoftwareSelectionPage(self._push_network_setup, lambda: gui_app.push_widget(self._custom_software_warning_page)) - self._download_failed_page = FailedPage(HARDWARE.reboot, self._pop_to_software_selection) + self._download_failed_page = FailedPage(self._pop_to_software_selection, icon="icons_mici/setup/red_warning.png") self._custom_software_warning_page = CustomSoftwareWarningPage(lambda: self._push_network_setup(True), self._pop_to_software_selection) @@ -497,8 +466,7 @@ class Setup(Widget): reason = self._download_failed_reason self._download_failed_reason = None self._download_failed_page.set_reason(reason) - gui_app.pop_widgets_to(self._software_selection_page, instant=True) # don't reset sliders - gui_app.push_widget(self._download_failed_page) + gui_app.pop_widgets_to(self._software_selection_page, lambda: gui_app.push_widget(self._download_failed_page)) def _render(self, rect: rl.Rectangle): self._start_page.render(rect) @@ -510,35 +478,18 @@ class Setup(Widget): # reset sliders after dismiss completes gui_app.pop_widgets_to(self._software_selection_page, self._software_selection_page.reset) - def _use_openpilot(self): - if os.path.isdir(INSTALL_PATH) and os.path.isfile(VALID_CACHE_PATH): - os.remove(VALID_CACHE_PATH) - with open(TMP_CONTINUE_PATH, "w") as f: - f.write(CONTINUE) - run_cmd(["chmod", "+x", TMP_CONTINUE_PATH]) - shutil.move(TMP_CONTINUE_PATH, CONTINUE_PATH) - shutil.copyfile(INSTALLER_SOURCE_PATH, INSTALLER_DESTINATION_PATH) - - # give time for installer UI to take over - time.sleep(0.1) - gui_app.request_close() - else: - self._push_network_setup() - def _push_network_setup(self, custom_software: bool = False): # to fire the correct continue callback later self._network_setup_page.set_custom_software(custom_software) - gui_app.pop_widgets_to(self._software_selection_page, lambda: gui_app.push_widget(self._network_setup_page)) + gui_app.push_widget(self._network_setup_page) def _network_setup_continue_callback(self, custom_software: bool): if not custom_software: - gui_app.pop_widgets_to(self._software_selection_page, instant=True) # don't reset sliders self._download(OPENPILOT_URL) else: def handle_keyboard_result(text): url = text.strip() if url: - gui_app.pop_widgets_to(self._software_selection_page, instant=True) # don't reset sliders self._download(url) keyboard = BigInputDialog("custom software URL...", confirm_callback=handle_keyboard_result, auto_return_to_letters="./") @@ -553,10 +504,12 @@ class Setup(Widget): self.download_url = (urlparse(f"https://{url}") if not parsed.netloc else parsed).geturl() self.download_progress = 0 - gui_app.push_widget(self._downloading_page) + def start_download(): + self.download_thread = threading.Thread(target=self._download_thread, daemon=True) + self.download_thread.start() - self.download_thread = threading.Thread(target=self._download_thread, daemon=True) - self.download_thread.start() + self._downloading_page.set_shown_callback(start_download) + gui_app.push_widget(self._downloading_page) def _download_thread(self): try: @@ -591,26 +544,27 @@ class Setup(Widget): is_elf = header == b'\x7fELF' if not is_elf: - self._download_failed_reason = "No custom software found at this URL." + self._download_failed_reason = "No custom software found at this URL: " + self.download_url.replace("https://", "", 1) return + # NOTE: currently unused, for future logging + with open(INSTALLER_URL_PATH, "w") as f: + f.write(self.download_url) + # AGNOS might try to execute the installer before this process exits. # Therefore, important to close the fd before renaming the installer. os.close(fd) os.rename(tmpfile, INSTALLER_DESTINATION_PATH) - with open(INSTALLER_URL_PATH, "w") as f: - f.write(self.download_url) - # give time for installer UI to take over time.sleep(0.1) gui_app.request_close() except urllib.error.HTTPError as e: if e.code == 409: - self._download_failed_reason = "Incompatible sunnypilot version" + self._download_failed_reason = "Incompatible sunnypilot version." except Exception: - self._download_failed_reason = "Invalid URL" + self._download_failed_reason = "Invalid URL: " + self.download_url.replace("https://", "", 1) def main(): diff --git a/system/ui/mici_updater.py b/system/ui/mici_updater.py index cd1f99062c..8437e6fa60 100755 --- a/system/ui/mici_updater.py +++ b/system/ui/mici_updater.py @@ -3,57 +3,28 @@ import sys import subprocess import threading import pyray as rl -from enum import IntEnum from openpilot.common.realtime import config_realtime_process, set_core_affinity from openpilot.system.hardware import HARDWARE, TICI from openpilot.common.swaglog import cloudlog from openpilot.system.ui.lib.application import gui_app, FontWeight -from openpilot.system.ui.widgets import Widget +from openpilot.system.ui.widgets.nav_widget import NavWidget +from openpilot.system.ui.widgets.scroller import Scroller from openpilot.system.ui.widgets.label import UnifiedLabel -from openpilot.system.ui.widgets.button import FullRoundedButton -from openpilot.system.ui.mici_setup import NetworkSetupPageBase, FailedPageBase, NetworkConnectivityMonitor +from openpilot.system.ui.mici_setup import (NetworkSetupPage, FailedPage, NetworkConnectivityMonitor, + GreyBigButton, BigPillButton) -class Screen(IntEnum): - PROMPT = 0 - WIFI = 1 - PROGRESS = 2 - FAILED = 3 +class UpdaterNetworkSetupPage(NetworkSetupPage): + def __init__(self, network_monitor, continue_callback): + super().__init__(network_monitor, continue_callback, back_callback=None) + self._continue_button.set_text("download\n& install") + self._continue_button.set_green(False) -class Updater(Widget): - def __init__(self, updater_path, manifest_path): +class ProgressPage(NavWidget): + def __init__(self): super().__init__() - self.updater = updater_path - self.manifest = manifest_path - self.current_screen = Screen.PROMPT - - self.progress_value = 0 - self.progress_text = "loading" - self.process = None - self.update_thread = None - self._network_monitor = NetworkConnectivityMonitor() - self._network_monitor.start() - - # TODO: network page is rendered inline, not pushed on nav stack, so auto-dismiss on internet connect doesn't work - self._network_setup_page = NetworkSetupPageBase(self._network_monitor, self._network_setup_continue_callback, - disable_connect_hint=True) - self._network_setup_page.set_is_updater() - self._network_setup_page.set_enabled(lambda: self.enabled) # for nav stack - - # Buttons - self._continue_button = FullRoundedButton("continue") - self._continue_button.set_click_callback(lambda: self.set_current_screen(Screen.WIFI)) - - self._title_label = UnifiedLabel("update required", 48, text_color=rl.Color(255, 255, 255, int(255 * 0.9)), - font_weight=FontWeight.DISPLAY) - self._subtitle_label = UnifiedLabel("The download size is approximately 1GB.", 36, - text_color=rl.Color(255, 255, 255, int(255 * 0.9)), - font_weight=FontWeight.ROMAN) - - self._update_failed_page = FailedPageBase(HARDWARE.reboot, self._update_failed_retry_callback, - title="update failed") self._progress_title_label = UnifiedLabel("", 64, text_color=rl.Color(255, 255, 255, int(255 * 0.9)), font_weight=FontWeight.DISPLAY, line_height=0.8) @@ -61,38 +32,92 @@ class Updater(Widget): font_weight=FontWeight.ROMAN, alignment_vertical=rl.GuiTextAlignmentVertical.TEXT_ALIGN_BOTTOM) + def _back_enabled(self) -> bool: + return False + + def set_progress(self, text: str, value: int): + self._progress_title_label.set_text(text.replace("_", "_\n") + "...") + self._progress_percent_label.set_text(f"{value}%") + + def show_event(self): + super().show_event() + self._nav_bar._alpha = 0.0 # not dismissable + self.set_progress("downloading", 0) + + def _render(self, rect: rl.Rectangle): + rl.draw_rectangle_rec(rect, rl.BLACK) + self._progress_title_label.render(rl.Rectangle( + rect.x + 12, + rect.y + 2, + rect.width, + self._progress_title_label.get_content_height(int(rect.width - 20)), + )) + + self._progress_percent_label.render(rl.Rectangle( + rect.x + 12, + rect.y + 18, + rect.width, + rect.height, + )) + + +class Updater(Scroller): + def __init__(self, updater_path, manifest_path): + super().__init__() + self.updater = updater_path + self.manifest = manifest_path + + self.progress_value = 0 + self.progress_text = "loading" + self.process = None + self.update_thread = None + self._update_failed = False + + self._network_monitor = NetworkConnectivityMonitor() + self._network_monitor.start() + + self._network_setup_page = UpdaterNetworkSetupPage(self._network_monitor, self._network_setup_continue_callback) + + self._progress_page = ProgressPage() + + self._failed_page = FailedPage(self._retry, title="update failed") + + self._continue_button = BigPillButton("next") + self._continue_button.set_click_callback(lambda: gui_app.push_widget(self._network_setup_page)) + + self._scroller.add_widgets([ + GreyBigButton("update required", "the download size\nis approximately 1 GB", + gui_app.texture("icons_mici/offroad_alerts/green_wheel.png", 64, 64)), + self._continue_button, + ]) + + gui_app.add_nav_stack_tick(self._nav_stack_tick) + def _network_setup_continue_callback(self, _): self.install_update() - def _update_failed_retry_callback(self): - self.set_current_screen(Screen.PROMPT) + def _retry(self): + gui_app.pop_widgets_to(self) - def set_current_screen(self, screen: Screen): - if self.current_screen != screen: - if screen == Screen.PROGRESS: - if self._network_setup_page: - self._network_setup_page.hide_event() - elif screen == Screen.WIFI: - if self._network_setup_page: - self._network_setup_page.show_event() - elif screen == Screen.PROMPT: - if self._network_setup_page: - self._network_setup_page.hide_event() - elif screen == Screen.FAILED: - if self._network_setup_page: - self._network_setup_page.hide_event() + def _nav_stack_tick(self): + self._progress_page.set_progress(self.progress_text, self.progress_value) - self.current_screen = screen + if self._update_failed: + self._update_failed = False + self.show_event() + gui_app.pop_widgets_to(self, lambda: gui_app.push_widget(self._failed_page)) def install_update(self): - self.set_current_screen(Screen.PROGRESS) self.progress_value = 0 self.progress_text = "downloading" - # Start the update process in a separate thread - self.update_thread = threading.Thread(target=self._run_update_process) - self.update_thread.daemon = True - self.update_thread.start() + def start_update(): + self.update_thread = threading.Thread(target=self._run_update_process, daemon=True) + self.update_thread.start() + + # Start the update process in a separate thread *after* show animation completes + self._progress_page.set_shown_callback(start_update) + gui_app.push_widget(self._progress_page) def _run_update_process(self): # TODO: just import it and run in a thread without a subprocess @@ -101,7 +126,7 @@ class Updater(Widget): self.process = subprocess.Popen(cmd, stdout=subprocess.PIPE, text=True, bufsize=1, universal_newlines=True) except Exception: - self.set_current_screen(Screen.FAILED) + self._update_failed = True return if self.process.stdout is not None: @@ -118,58 +143,7 @@ class Updater(Widget): if exit_code == 0: HARDWARE.reboot() else: - self.set_current_screen(Screen.FAILED) - - def render_prompt_screen(self, rect: rl.Rectangle): - self._title_label.render(rl.Rectangle( - rect.x + 8, - rect.y - 5, - rect.width, - 48, - )) - - subtitle_width = rect.width - 16 - subtitle_height = self._subtitle_label.get_content_height(int(subtitle_width)) - self._subtitle_label.render(rl.Rectangle( - rect.x + 8, - rect.y + 48, - subtitle_width, - subtitle_height, - )) - - self._continue_button.render(rl.Rectangle( - rect.x + 8, - rect.y + rect.height - self._continue_button.rect.height, - self._continue_button.rect.width, - self._continue_button.rect.height, - )) - - def render_progress_screen(self, rect: rl.Rectangle): - self._progress_title_label.set_text(self.progress_text.replace("_", "_\n") + "...") - self._progress_title_label.render(rl.Rectangle( - rect.x + 12, - rect.y + 2, - rect.width, - self._progress_title_label.get_content_height(int(rect.width - 20)), - )) - - self._progress_percent_label.set_text(f"{self.progress_value}%") - self._progress_percent_label.render(rl.Rectangle( - rect.x + 12, - rect.y + 18, - rect.width, - rect.height, - )) - - def _render(self, rect: rl.Rectangle): - if self.current_screen == Screen.PROMPT: - self.render_prompt_screen(rect) - elif self.current_screen == Screen.WIFI: - self._network_setup_page.render(rect) - elif self.current_screen == Screen.PROGRESS: - self.render_progress_screen(rect) - elif self.current_screen == Screen.FAILED: - self._update_failed_page.render(rect) + self._update_failed = True def close(self): self._network_monitor.stop() diff --git a/system/ui/tici_reset.py b/system/ui/tici_reset.py index 23f6b344ec..a6603d547e 100755 --- a/system/ui/tici_reset.py +++ b/system/ui/tici_reset.py @@ -20,7 +20,6 @@ TIMEOUT = 3*60 class ResetMode(IntEnum): USER_RESET = 0 # user initiated a factory reset from openpilot RECOVER = 1 # userdata is corrupt for some reason, give a chance to recover - FORMAT = 2 # finish up a factory reset from a tool that doesn't flash an empty partition to userdata class ResetState(IntEnum): @@ -54,7 +53,7 @@ class Reset(Widget): else: self._reset_state = ResetState.FAILED - def start_reset(self): + def _start_reset(self): self._reset_state = ResetState.RESETTING threading.Timer(0.1, self._do_erase).start() @@ -92,7 +91,7 @@ class Reset(Widget): def _confirm(self): if self._reset_state == ResetState.CONFIRM: - self.start_reset() + self._start_reset() else: self._reset_state = ResetState.CONFIRM @@ -113,15 +112,10 @@ def main(): if len(sys.argv) > 1: if sys.argv[1] == '--recover': mode = ResetMode.RECOVER - elif sys.argv[1] == "--format": - mode = ResetMode.FORMAT gui_app.init_window("System Reset", 20) reset = Reset(mode) - if mode == ResetMode.FORMAT: - reset.start_reset() - gui_app.push_widget(reset) for _ in gui_app.render(): diff --git a/system/ui/tici_setup.py b/system/ui/tici_setup.py index 8098e9ea27..9eefb6af53 100755 --- a/system/ui/tici_setup.py +++ b/system/ui/tici_setup.py @@ -7,12 +7,10 @@ import urllib.request import urllib.error from urllib.parse import urlparse from enum import IntEnum -import shutil import pyray as rl from cereal import log -from openpilot.common.utils import run_cmd from openpilot.system.hardware import HARDWARE from openpilot.system.ui.lib.scroll_panel import GuiScrollPanel from openpilot.system.ui.lib.application import gui_app, FontWeight, FONT_SCALE @@ -35,20 +33,9 @@ BUTTON_SPACING = 50 OPENPILOT_URL = "https://openpilot.comma.ai" USER_AGENT = f"AGNOSSetup-{HARDWARE.get_os_version()}" -CONTINUE_PATH = "/data/continue.sh" -TMP_CONTINUE_PATH = "/data/continue.sh.new" -INSTALL_PATH = "/data/openpilot" -VALID_CACHE_PATH = "/data/.openpilot_cache" -INSTALLER_SOURCE_PATH = "/usr/comma/installer" INSTALLER_DESTINATION_PATH = "/tmp/installer" INSTALLER_URL_PATH = "/tmp/installer_url" -CONTINUE = """#!/usr/bin/env bash - -cd /data/openpilot -exec ./launch_openpilot.sh -""" - class SetupState(IntEnum): LOW_VOLTAGE = 0 @@ -176,7 +163,9 @@ class Setup(Widget): def _software_selection_continue_button_callback(self): if self._software_selection_openpilot_button.selected: - self.use_openpilot() + self.state = SetupState.NETWORK_SETUP + self.stop_network_check_thread.clear() + self.start_network_check() else: self.state = SetupState.CUSTOM_SOFTWARE_WARNING @@ -194,7 +183,7 @@ class Setup(Widget): self.state = SetupState.CUSTOM_SOFTWARE def render_low_voltage(self, rect: rl.Rectangle): - rl.draw_texture(self.warning, int(rect.x + 150), int(rect.y + 110), rl.WHITE) + rl.draw_texture_ex(self.warning, rl.Vector2(rect.x + 150, rect.y + 110), 0.0, 1.0, rl.WHITE) self._low_voltage_title_label.render(rl.Rectangle(rect.x + 150, rect.y + 110 + 150 + 100, rect.width - 500 - 150, TITLE_FONT_SIZE * FONT_SCALE)) self._low_voltage_body_label.render(rl.Rectangle(rect.x + 150, rect.y + 110 + 150 + 150, rect.width - 500, BODY_FONT_SIZE * FONT_SCALE * 3)) @@ -342,23 +331,6 @@ class Setup(Widget): self.keyboard.set_callback(handle_keyboard_result) gui_app.push_widget(self.keyboard) - def use_openpilot(self): - if os.path.isdir(INSTALL_PATH) and os.path.isfile(VALID_CACHE_PATH): - os.remove(VALID_CACHE_PATH) - with open(TMP_CONTINUE_PATH, "w") as f: - f.write(CONTINUE) - run_cmd(["chmod", "+x", TMP_CONTINUE_PATH]) - shutil.move(TMP_CONTINUE_PATH, CONTINUE_PATH) - shutil.copyfile(INSTALLER_SOURCE_PATH, INSTALLER_DESTINATION_PATH) - - # give time for installer UI to take over - time.sleep(0.1) - gui_app.request_close() - else: - self.state = SetupState.NETWORK_SETUP - self.stop_network_check_thread.clear() - self.start_network_check() - def download(self, url: str): # autocomplete incomplete URLs if re.match("^([^/.]+)/([^/]+)$", url): diff --git a/system/ui/widgets/__init__.py b/system/ui/widgets/__init__.py index 568f58b985..4ce1c1b694 100644 --- a/system/ui/widgets/__init__.py +++ b/system/ui/widgets/__init__.py @@ -3,6 +3,7 @@ from __future__ import annotations import abc import pyray as rl from enum import IntEnum +from typing import TypeVar from collections.abc import Callable from openpilot.system.ui.lib.application import gui_app, MousePos, MAX_TOUCH_SLOTS, MouseEvent @@ -13,6 +14,10 @@ except ImportError: awake = True device = Device() +W = TypeVar('W', bound='Widget') + +DEBUG = False + class DialogResult(IntEnum): CANCEL = 0 @@ -24,11 +29,14 @@ class Widget(abc.ABC): def __init__(self): self._rect: rl.Rectangle = rl.Rectangle(0, 0, 0, 0) self._parent_rect: rl.Rectangle | None = None + self._children: list[Widget] = [] + + self._enabled: bool | Callable[[], bool] = True + self._is_visible: bool | Callable[[], bool] = True + self.__is_pressed = [False] * MAX_TOUCH_SLOTS # if current mouse/touch down started within the widget's rectangle self.__tracking_is_pressed = [False] * MAX_TOUCH_SLOTS - self._enabled: bool | Callable[[], bool] = True - self._is_visible: bool | Callable[[], bool] = True self._touch_valid_callback: Callable[[], bool] | None = None self._click_delay: float | None = None # seconds to hold is_pressed after release self._click_release_time: float | None = None @@ -197,12 +205,37 @@ class Widget(abc.ABC): """Optionally handle mouse events. This is called before rendering.""" # Default implementation does nothing, can be overridden by subclasses + def _child(self, widget: W) -> W: + """ + Register a widget as a child. Lifecycle events (show/hide) propagate to registered children. + - If the widget is pushed onto the nav stack, do NOT register it (gui_app manages its lifecycle). + - If the widget is rendered inline in _render(), register it. + """ + assert widget not in self._children, f"{type(widget).__name__} already a child of {type(self).__name__}" + self._children.append(widget) + return widget + + _show_hide_depth = 0 + def show_event(self): - """Optionally handle show event. Parent must manually call this""" - # TODO: iterate through all child objects, check for subclassing from Widget/Layout (Scroller) + """Called when widget becomes visible. Propagates to registered children.""" + if DEBUG: + print(f"{' ' * Widget._show_hide_depth}show_event: {type(self).__name__}") + Widget._show_hide_depth += 1 + for child in self._children: + child.show_event() + if DEBUG: + Widget._show_hide_depth -= 1 def hide_event(self): - """Optionally handle hide event. Parent must manually call this""" + """Called when widget is hidden. Propagates to registered children.""" + if DEBUG: + print(f"{' ' * Widget._show_hide_depth}hide_event: {type(self).__name__}") + Widget._show_hide_depth += 1 + for child in self._children: + child.hide_event() + if DEBUG: + Widget._show_hide_depth -= 1 def dismiss(self, callback: Callable[[], None] | None = None): """Immediately dismiss the widget, firing the callback after.""" diff --git a/system/ui/widgets/button.py b/system/ui/widgets/button.py index a608344710..36ef3bedab 100644 --- a/system/ui/widgets/button.py +++ b/system/ui/widgets/button.py @@ -5,7 +5,7 @@ import pyray as rl from openpilot.system.ui.lib.application import gui_app, FontWeight, MousePos from openpilot.system.ui.widgets import Widget -from openpilot.system.ui.widgets.label import Label, UnifiedLabel +from openpilot.system.ui.widgets.label import Label from openpilot.common.filter_simple import FirstOrderFilter @@ -191,7 +191,7 @@ class IconButton(Widget): color = rl.Color(255, 255, 255, int(255 * 0.9 * 0.35 * self._opacity_filter.x)) draw_x = rect.x + (rect.width - self._texture.width) / 2 draw_y = rect.y + (rect.height - self._texture.height) / 2 - rl.draw_texture(self._texture, int(draw_x), int(draw_y), color) + rl.draw_texture_ex(self._texture, rl.Vector2(draw_x, draw_y), 0.0, 1.0, color) class SmallCircleIconButton(Widget): @@ -219,86 +219,7 @@ class SmallCircleIconButton(Widget): bg_txt = self._icon_bg_pressed_txt if self.is_pressed else self._icon_bg_txt icon_white = white - rl.draw_texture(bg_txt, int(self.rect.x), int(self.rect.y), white) + rl.draw_texture_ex(bg_txt, rl.Vector2(self.rect.x, self.rect.y), 0.0, 1.0, white) icon_x = self.rect.x + (self.rect.width - self._icon_txt.width) / 2 icon_y = self.rect.y + (self.rect.height - self._icon_txt.height) / 2 - rl.draw_texture(self._icon_txt, int(icon_x), int(icon_y), icon_white) - - -class SmallButton(Widget): - def __init__(self, text: str): - super().__init__() - self._click_delay = 0.075 - self._opacity_filter = FirstOrderFilter(1.0, 0.1, 1 / gui_app.target_fps) - - self._load_assets() - - self._label = UnifiedLabel(text, 36, font_weight=FontWeight.SEMI_BOLD, - text_color=rl.Color(255, 255, 255, int(255 * 0.9)), - alignment=rl.GuiTextAlignment.TEXT_ALIGN_CENTER, - alignment_vertical=rl.GuiTextAlignmentVertical.TEXT_ALIGN_MIDDLE) - - self._bg_disabled_txt = None - - def _load_assets(self): - self.set_rect(rl.Rectangle(0, 0, 194, 100)) - self._bg_txt = gui_app.texture("icons_mici/setup/reset/small_button.png", 194, 100) - self._bg_pressed_txt = gui_app.texture("icons_mici/setup/reset/small_button_pressed.png", 194, 100) - - def set_text(self, text: str): - self._label.set_text(text) - - def set_opacity(self, opacity: float, smooth: bool = False): - if smooth: - self._opacity_filter.update(opacity) - else: - self._opacity_filter.x = opacity - - def _render(self, _): - if not self.enabled and self._bg_disabled_txt is not None: - rl.draw_texture(self._bg_disabled_txt, int(self.rect.x), int(self.rect.y), rl.Color(255, 255, 255, int(255 * self._opacity_filter.x))) - elif self.is_pressed: - rl.draw_texture(self._bg_pressed_txt, int(self.rect.x), int(self.rect.y), rl.Color(255, 255, 255, int(255 * self._opacity_filter.x))) - else: - rl.draw_texture(self._bg_txt, int(self.rect.x), int(self.rect.y), rl.Color(255, 255, 255, int(255 * self._opacity_filter.x))) - - opacity = 0.9 if self.enabled else 0.35 - self._label.set_color(rl.Color(255, 255, 255, int(255 * opacity * self._opacity_filter.x))) - self._label.render(self._rect) - - -class SmallRedPillButton(SmallButton): - def _load_assets(self): - self.set_rect(rl.Rectangle(0, 0, 194, 100)) - self._bg_txt = gui_app.texture("icons_mici/setup/small_red_pill.png", 194, 100) - self._bg_pressed_txt = gui_app.texture("icons_mici/setup/small_red_pill_pressed.png", 194, 100) - - -class SmallerRoundedButton(SmallButton): - def _load_assets(self): - self.set_rect(rl.Rectangle(0, 0, 150, 100)) - self._bg_txt = gui_app.texture("icons_mici/setup/smaller_button.png", 150, 100) - self._bg_disabled_txt = gui_app.texture("icons_mici/setup/smaller_button_disabled.png", 150, 100) - self._bg_pressed_txt = gui_app.texture("icons_mici/setup/smaller_button_pressed.png", 150, 100) - - -class WideRoundedButton(SmallButton): - def _load_assets(self): - self.set_rect(rl.Rectangle(0, 0, 316, 100)) - self._bg_txt = gui_app.texture("icons_mici/setup/medium_button_bg.png", 316, 100) - self._bg_pressed_txt = gui_app.texture("icons_mici/setup/medium_button_pressed_bg.png", 316, 100) - - -class WidishRoundedButton(SmallButton): - def _load_assets(self): - self.set_rect(rl.Rectangle(0, 0, 250, 100)) - self._bg_txt = gui_app.texture("icons_mici/setup/widish_button.png", 250, 100) - self._bg_pressed_txt = gui_app.texture("icons_mici/setup/widish_button_pressed.png", 250, 100) - self._bg_disabled_txt = gui_app.texture("icons_mici/setup/widish_button_disabled.png", 250, 100) - - -class FullRoundedButton(SmallButton): - def _load_assets(self): - self.set_rect(rl.Rectangle(0, 0, 520, 100)) - self._bg_txt = gui_app.texture("icons_mici/setup/reset/wide_button.png", 520, 100) - self._bg_pressed_txt = gui_app.texture("icons_mici/setup/reset/wide_button_pressed.png", 520, 100) + rl.draw_texture_ex(self._icon_txt, rl.Vector2(icon_x, icon_y), 0.0, 1.0, icon_white) diff --git a/system/ui/widgets/label.py b/system/ui/widgets/label.py index 8ed9ec62f5..7fe25ab51d 100644 --- a/system/ui/widgets/label.py +++ b/system/ui/widgets/label.py @@ -1,3 +1,4 @@ +import math from enum import IntEnum from collections.abc import Callable from itertools import zip_longest @@ -26,166 +27,6 @@ class ScrollState(IntEnum): SCROLLING = 1 -# TODO: merge anything new here to master -class MiciLabel(Widget): - def __init__(self, - text: str, - font_size: int = DEFAULT_TEXT_SIZE, - width: int | None = None, - color: rl.Color = DEFAULT_TEXT_COLOR, - font_weight: FontWeight = FontWeight.NORMAL, - alignment: int = rl.GuiTextAlignment.TEXT_ALIGN_LEFT, - alignment_vertical: int = rl.GuiTextAlignmentVertical.TEXT_ALIGN_TOP, - spacing: int = 0, - line_height: int | None = None, - elide_right: bool = True, - wrap_text: bool = False, - scroll: bool = False): - super().__init__() - self.text = text - self.wrapped_text: list[str] = [] - self.font_size = font_size - self.width = width - self.color = color - self.font_weight = font_weight - self.alignment = alignment - self.alignment_vertical = alignment_vertical - self.spacing = spacing - self.line_height = line_height if line_height is not None else font_size - self.elide_right = elide_right - self.wrap_text = wrap_text - self._height = 0 - - # Scroll state - self.scroll = scroll - self._needs_scroll = False - self._scroll_offset = 0 - self._scroll_pause_t: float | None = None - self._scroll_state: ScrollState = ScrollState.STARTING - - assert not (self.scroll and self.wrap_text), "Cannot enable both scroll and wrap_text" - assert not (self.scroll and self.elide_right), "Cannot enable both scroll and elide_right" - - self.set_text(text) - - @property - def text_height(self): - return self._height - - def set_font_size(self, font_size: int): - self.font_size = font_size - self.set_text(self.text) - - def set_width(self, width: int): - self.width = width - self._rect.width = width - self.set_text(self.text) - - def set_text(self, txt: str): - self.text = txt - text_size = measure_text_cached(gui_app.font(self.font_weight), self.text, self.font_size, self.spacing) - if self.width is not None: - self._rect.width = self.width - else: - self._rect.width = text_size.x - - if self.wrap_text: - self.wrapped_text = wrap_text(gui_app.font(self.font_weight), self.text, self.font_size, int(self._rect.width)) - self._height = len(self.wrapped_text) * self.line_height - elif self.scroll: - self._needs_scroll = self.scroll and text_size.x > self._rect.width - self._rect.height = text_size.y - - def set_color(self, color: rl.Color): - self.color = color - - def set_font_weight(self, font_weight: FontWeight): - self.font_weight = font_weight - self.set_text(self.text) - - def _render(self, rect: rl.Rectangle): - # Only scissor when we know there is a single scrolling line - if self._needs_scroll: - rl.begin_scissor_mode(int(rect.x), int(rect.y), int(rect.width), int(rect.height)) - - font = gui_app.font(self.font_weight) - - text_y_offset = 0 - # Draw the text in the specified rectangle - lines = self.wrapped_text or [self.text] - if self.alignment_vertical == rl.GuiTextAlignmentVertical.TEXT_ALIGN_BOTTOM: - lines = lines[::-1] - - for display_text in lines: - text_size = measure_text_cached(font, display_text, self.font_size, self.spacing) - - # Elide text to fit within the rectangle - if self.elide_right and text_size.x > rect.width: - ellipsis = "..." - left, right = 0, len(display_text) - while left < right: - mid = (left + right) // 2 - candidate = display_text[:mid] + ellipsis - candidate_size = measure_text_cached(font, candidate, self.font_size, self.spacing) - if candidate_size.x <= rect.width: - left = mid + 1 - else: - right = mid - display_text = display_text[: left - 1] + ellipsis if left > 0 else ellipsis - text_size = measure_text_cached(font, display_text, self.font_size, self.spacing) - - # Handle scroll state - elif self.scroll and self._needs_scroll: - if self._scroll_state == ScrollState.STARTING: - if self._scroll_pause_t is None: - self._scroll_pause_t = rl.get_time() + 2.0 - if rl.get_time() >= self._scroll_pause_t: - self._scroll_state = ScrollState.SCROLLING - self._scroll_pause_t = None - - elif self._scroll_state == ScrollState.SCROLLING: - self._scroll_offset -= 0.8 / 60. * gui_app.target_fps - # don't fully hide - if self._scroll_offset <= -text_size.x - self._rect.width / 3: - self._scroll_offset = 0 - self._scroll_state = ScrollState.STARTING - self._scroll_pause_t = None - - # Calculate horizontal position based on alignment - text_x = rect.x + { - rl.GuiTextAlignment.TEXT_ALIGN_LEFT: 0, - rl.GuiTextAlignment.TEXT_ALIGN_CENTER: (rect.width - text_size.x) / 2, - rl.GuiTextAlignment.TEXT_ALIGN_RIGHT: rect.width - text_size.x, - }.get(self.alignment, 0) + self._scroll_offset - - # Calculate vertical position based on alignment - text_y = rect.y + { - rl.GuiTextAlignmentVertical.TEXT_ALIGN_TOP: 0, - rl.GuiTextAlignmentVertical.TEXT_ALIGN_MIDDLE: (rect.height - text_size.y) / 2, - rl.GuiTextAlignmentVertical.TEXT_ALIGN_BOTTOM: rect.height - text_size.y, - }.get(self.alignment_vertical, 0) - text_y += text_y_offset - - rl.draw_text_ex(font, display_text, rl.Vector2(round(text_x), text_y), self.font_size, self.spacing, self.color) - # Draw 2nd instance for scrolling - if self._needs_scroll and self._scroll_state != ScrollState.STARTING: - text2_scroll_offset = text_size.x + self._rect.width / 3 - rl.draw_text_ex(font, display_text, rl.Vector2(round(text_x + text2_scroll_offset), text_y), self.font_size, self.spacing, self.color) - if self.alignment_vertical == rl.GuiTextAlignmentVertical.TEXT_ALIGN_BOTTOM: - text_y_offset -= self.line_height - else: - text_y_offset += self.line_height - - if self._needs_scroll: - # draw black fade on left and right - fade_width = 20 - rl.draw_rectangle_gradient_h(int(rect.x + rect.width - fade_width), int(rect.y), fade_width, int(rect.height), rl.BLANK, rl.BLACK) - if self._scroll_state != ScrollState.STARTING: - rl.draw_rectangle_gradient_h(int(rect.x), int(rect.y), fade_width, int(rect.height), rl.BLACK, rl.BLANK) - - rl.end_scissor_mode() - - # TODO: This should be a Widget class def gui_label( rect: rl.Rectangle, @@ -392,7 +233,7 @@ class Label(Widget): class UnifiedLabel(Widget): """ - Unified label widget that combines functionality from gui_label, gui_text_box, Label, and MiciLabel. + Unified label widget that combines functionality from gui_label, gui_text_box, and Label. Supports: - Emoji rendering @@ -401,6 +242,13 @@ class UnifiedLabel(Widget): - Proper multiline vertical alignment - Height calculation for layout purposes """ + # Shimmer constants + SHIMMER_BAND_WIDTH = 0.3 # shimmer width as fraction of text width + SHIMMER_BLUR_RADIUS = 0.12 # gaussian blur as fraction of text width + SHIMMER_CYCLE_PERIOD = 2.5 # seconds per full shimmer cycle + SHIMMER_SWEEP_FRACTION = 0.9 # fraction of cycle spent sweeping (rest is pause) + SHIMMER_LOW_OPACITY = 0.65 # text opacity at rest, shimmer brings to 1.0 + def __init__(self, text: str | Callable[[], str], font_size: int = DEFAULT_TEXT_SIZE, @@ -414,7 +262,8 @@ class UnifiedLabel(Widget): wrap_text: bool = True, scroll: bool = False, line_height: float = 1.0, - letter_spacing: float = 0.0): + letter_spacing: float = 0.0, + shimmer: bool = False): super().__init__() self._text = text self._font_size = font_size @@ -432,6 +281,10 @@ class UnifiedLabel(Widget): self._letter_spacing = letter_spacing # 0.1 = 10% self._spacing_pixels = font_size * letter_spacing + # Shimmer state + self._shimmer = shimmer + self._shimmer_start_time = 0.0 + # Scroll state self._scroll = scroll self._needs_scroll = False @@ -467,6 +320,14 @@ class UnifiedLabel(Widget): """Get the current text content.""" return str(_resolve_value(self._text)) + @property + def font_size(self) -> int: + return self._font_size + + @property + def text_width(self) -> float: + return max((s.x for s in self._cached_line_sizes), default=0.0) + def set_text_color(self, color: rl.Color): """Update the text color.""" self._text_color = color @@ -517,6 +378,15 @@ class UnifiedLabel(Widget): self._scroll_pause_t = None self._scroll_state = ScrollState.STARTING + def show_event(self): + super().show_event() + if self._shimmer: + self.reset_shimmer() + + def reset_shimmer(self, offset: float = 0.0): + """Reset shimmer animation timing.""" + self._shimmer_start_time = rl.get_time() + offset + def set_max_width(self, max_width: int | None): """Set the maximum width constraint for wrapping/eliding.""" if self._max_width != max_width: @@ -770,6 +640,24 @@ class UnifiedLabel(Widget): rl.end_scissor_mode() + def _shimmer_alpha(self, char_x: float, shimmer_left: float, shimmer_width: float) -> float: + """Compute shimmer opacity multiplier for a character at the given x position.""" + sigma = shimmer_width * self.SHIMMER_BLUR_RADIUS + if sigma <= 0: + return self.SHIMMER_LOW_OPACITY + + elapsed = rl.get_time() - self._shimmer_start_time + t_raw = (elapsed % self.SHIMMER_CYCLE_PERIOD) / self.SHIMMER_CYCLE_PERIOD + t_clamped = max(0.0, min(t_raw / self.SHIMMER_SWEEP_FRACTION, 1.0)) + t = t_clamped * t_clamped * (3.0 - 2.0 * t_clamped) # smoothstep + + margin = shimmer_width * self.SHIMMER_BAND_WIDTH + center = shimmer_left + shimmer_width + margin - t * (shimmer_width + 2.0 * margin) + + d = char_x - center + shimmer = math.exp(-0.5 * d * d / (sigma * sigma)) + return self.SHIMMER_LOW_OPACITY + (1.0 - self.SHIMMER_LOW_OPACITY) * shimmer + def _render_line(self, line, size, emojis, current_y, x_offset=0.0): # Calculate horizontal position if self._alignment == rl.GuiTextAlignment.TEXT_ALIGN_LEFT: @@ -782,7 +670,13 @@ class UnifiedLabel(Widget): line_x = self._rect.x + self._text_padding line_x += self._scroll_offset + x_offset - # Render line with emojis + if self._shimmer: + self._render_line_shimmer(line, line_x, current_y) + else: + # Render line with emojis + self._render_line_normal(line, emojis, line_x, current_y) + + def _render_line_normal(self, line, emojis, line_x, current_y): line_pos = rl.Vector2(line_x, current_y) prev_index = 0 @@ -806,3 +700,23 @@ class UnifiedLabel(Widget): text_after = line[prev_index:] if text_after: rl.draw_text_ex(self._font, text_after, line_pos, self._font_size, self._spacing_pixels, self._text_color) + + def _render_line_shimmer(self, line, line_x, current_y): + # Shimmer range based on widest line so sweep is even across all lines + max_width = self.text_width + if self._alignment == rl.GuiTextAlignment.TEXT_ALIGN_RIGHT: + shimmer_left = self._rect.x + self._rect.width - self._text_padding - max_width + elif self._alignment == rl.GuiTextAlignment.TEXT_ALIGN_CENTER: + shimmer_left = self._rect.x + (self._rect.width - max_width) / 2 + else: + shimmer_left = self._rect.x + self._text_padding + + base_a = self._text_color.a / 255.0 + cursor_x = line_x + for ch in line: + char_width = measure_text_cached(self._font, ch, self._font_size, self._spacing_pixels).x + char_center_x = cursor_x + char_width / 2.0 + alpha = int(255 * self._shimmer_alpha(char_center_x, shimmer_left, max_width) * base_a) + color = rl.Color(self._text_color.r, self._text_color.g, self._text_color.b, alpha) + rl.draw_text_ex(self._font, ch, rl.Vector2(cursor_x, current_y), self._font_size, 0, color) + cursor_x += char_width + self._spacing_pixels diff --git a/system/ui/widgets/layouts.py b/system/ui/widgets/layouts.py index 6f97fe5ed8..6bbc49e927 100644 --- a/system/ui/widgets/layouts.py +++ b/system/ui/widgets/layouts.py @@ -21,7 +21,6 @@ class HBoxLayout(Widget): def __init__(self, widgets: list[Widget] | None = None, spacing: int = 0, alignment: Alignment = Alignment.LEFT | Alignment.V_CENTER): super().__init__() - self._widgets: list[Widget] = [] self._spacing = spacing self._alignment = alignment @@ -31,13 +30,13 @@ class HBoxLayout(Widget): @property def widgets(self) -> list[Widget]: - return self._widgets + return self._children def add_widget(self, widget: Widget) -> None: - self._widgets.append(widget) + self._child(widget) def _render(self, _): - visible_widgets = [w for w in self._widgets if w.is_visible] + visible_widgets = [w for w in self._children if w.is_visible] cur_offset_x = 0 @@ -55,6 +54,6 @@ class HBoxLayout(Widget): y = self._rect.y + (self._rect.height - widget.rect.height) / 2 # Update widget position and render - widget.set_position(round(x), round(y)) + widget.set_position(x, y) widget.set_parent_rect(self._rect) widget.render() diff --git a/system/ui/widgets/list_view.py b/system/ui/widgets/list_view.py index 32bf01cfc8..82613c37c8 100644 --- a/system/ui/widgets/list_view.py +++ b/system/ui/widgets/list_view.py @@ -293,6 +293,7 @@ class ListItem(Widget): self._prev_description: str | None = self.description def show_event(self): + super().show_event() self._set_description_visible(False) def set_description_opened_callback(self, callback: Callable) -> None: @@ -354,7 +355,7 @@ class ListItem(Widget): if self.title: # Draw icon if present if self.icon: - rl.draw_texture(self._icon_texture, int(content_x), int(self._rect.y + (ITEM_BASE_HEIGHT - self._icon_texture.height) // 2), rl.WHITE) + rl.draw_texture_ex(self._icon_texture, rl.Vector2(content_x, self._rect.y + (ITEM_BASE_HEIGHT - self._icon_texture.height) / 2), 0.0, 1.0, rl.WHITE) text_x += ICON_SIZE + ITEM_PADDING # Draw main text diff --git a/system/ui/widgets/mici_keyboard.py b/system/ui/widgets/mici_keyboard.py index 74f1f56346..75a3c29e6b 100644 --- a/system/ui/widgets/mici_keyboard.py +++ b/system/ui/widgets/mici_keyboard.py @@ -95,7 +95,7 @@ class Key(Widget): self._size_filter.update(size) def _get_font_size(self) -> int: - return int(round(self._size_filter.x)) + return round(self._size_filter.x) class SmallKey(Key): diff --git a/system/ui/widgets/nav_widget.py b/system/ui/widgets/nav_widget.py index 3292c53ce8..11770bbe5d 100644 --- a/system/ui/widgets/nav_widget.py +++ b/system/ui/widgets/nav_widget.py @@ -65,9 +65,11 @@ class NavWidget(Widget, abc.ABC): self._back_callback: Callable[[], None] | None = None # persistent callback for user-initiated back navigation self._dismiss_callback: Callable[[], None] | None = None # transient callback for programmatic dismiss + # TODO: add this functionality to push_widget + self._shown_callback: Callable[[], None] | None = None # transient callback fired after show animation completes # TODO: move this state into NavBar - self._nav_bar = NavBar() + self._nav_bar = self._child(NavBar()) self._nav_bar_show_time = 0.0 self._nav_bar_y_filter = FirstOrderFilter(0.0, 0.1, 1 / gui_app.target_fps) @@ -79,6 +81,9 @@ class NavWidget(Widget, abc.ABC): def set_back_callback(self, callback: Callable[[], None]) -> None: self._back_callback = callback + def set_shown_callback(self, callback: Callable[[], None] | None) -> None: + self._shown_callback = callback + def _handle_mouse_event(self, mouse_event: MouseEvent) -> None: super()._handle_mouse_event(mouse_event) @@ -143,9 +148,14 @@ class NavWidget(Widget, abc.ABC): if self._playing_dismiss_animation: new_y = self._rect.height + DISMISS_PUSH_OFFSET - new_y = round(self._y_pos_filter.update(new_y)) - if abs(new_y) < 1 and self._y_pos_filter.velocity.x == 0.0: + new_y = self._y_pos_filter.update(new_y) + if abs(new_y) < 1 and abs(self._y_pos_filter.velocity.x) < 0.5: new_y = self._y_pos_filter.x = 0.0 + self._y_pos_filter.velocity.x = 0.0 + + if self._shown_callback is not None: + self._shown_callback() + self._shown_callback = None if new_y > self._rect.height + DISMISS_PUSH_OFFSET - 10: gui_app.pop_widget() @@ -166,10 +176,10 @@ class NavWidget(Widget, abc.ABC): def _layout(self): # Dim whatever is behind this widget, fading with position (runs after _update_state so position is correct) overlay_alpha = int(200 * max(0.0, min(1.0, 1.0 - self._rect.y / self._rect.height))) if self._rect.height > 0 else 0 - rl.draw_rectangle(0, 0, int(self._rect.width), int(self._rect.height), rl.Color(0, 0, 0, overlay_alpha)) + rl.draw_rectangle_rec(rl.Rectangle(0, 0, self._rect.width, self._rect.height), rl.Color(0, 0, 0, overlay_alpha)) bounce_height = 20 - rl.draw_rectangle(int(self._rect.x), int(self._rect.y), int(self._rect.width), int(self._rect.height + bounce_height), rl.BLACK) + rl.draw_rectangle_rec(rl.Rectangle(self._rect.x, self._rect.y, self._rect.width, self._rect.height + bounce_height), rl.BLACK) def render(self, rect: rl.Rectangle | None = None) -> bool | int | None: ret = super().render(rect) @@ -186,7 +196,7 @@ class NavWidget(Widget, abc.ABC): else: self._nav_bar_y_filter.update(NAV_BAR_MARGIN) - self._nav_bar.set_position(bar_x, round(self._nav_bar_y_filter.x)) + self._nav_bar.set_position(bar_x, self._nav_bar_y_filter.x) self._nav_bar.render() return ret @@ -204,7 +214,6 @@ class NavWidget(Widget, abc.ABC): def show_event(self): super().show_event() - self._nav_bar.show_event() # Reset state self._drag_start_pos = None @@ -214,6 +223,7 @@ class NavWidget(Widget, abc.ABC): # Start NavWidget off-screen, no matter how tall it is self._y_pos_filter.update_alpha(0.1) self._y_pos_filter.x = gui_app.height + self._y_pos_filter.velocity.x = 0.0 self._nav_bar_y_filter.x = -NAV_BAR_MARGIN - NAV_BAR_HEIGHT self._nav_bar_show_time = rl.get_time() diff --git a/system/ui/widgets/network.py b/system/ui/widgets/network.py index 6427a2f203..69be42f502 100644 --- a/system/ui/widgets/network.py +++ b/system/ui/widgets/network.py @@ -75,17 +75,14 @@ class NetworkUI(Widget): super().__init__() self._wifi_manager = wifi_manager self._current_panel: PanelType = PanelType.WIFI - self._wifi_panel = WifiManagerUI(wifi_manager) - self._advanced_panel = AdvancedNetworkSettings(wifi_manager) - self._nav_button = NavButton(tr("Advanced")) + self._wifi_panel = self._child(WifiManagerUI(wifi_manager)) + self._advanced_panel = self._child(AdvancedNetworkSettings(wifi_manager)) + self._nav_button = self._child(NavButton(tr("Advanced"))) self._nav_button.set_click_callback(self._cycle_panel) def show_event(self): + super().show_event() self._set_current_panel(PanelType.WIFI) - self._wifi_panel.show_event() - - def hide_event(self): - self._wifi_panel.hide_event() def _cycle_panel(self): if self._current_panel == PanelType.WIFI: @@ -305,10 +302,12 @@ class WifiManagerUI(Widget): disconnected=self._on_disconnected) def show_event(self): + super().show_event() # start/stop scanning when widget is visible self._wifi_manager.set_active(True) def hide_event(self): + super().hide_event() self._wifi_manager.set_active(False) def _load_icons(self): diff --git a/system/ui/widgets/scroller.py b/system/ui/widgets/scroller.py index c48be6b80b..a3a0d2b38f 100644 --- a/system/ui/widgets/scroller.py +++ b/system/ui/widgets/scroller.py @@ -47,7 +47,7 @@ class ScrollIndicator(Widget): # position based on scroll ratio slide_range = self._viewport.width - indicator_w max_scroll = self._content_size - self._viewport.width - scroll_ratio = -self._scroll_offset / max_scroll + scroll_ratio = (-self._scroll_offset / abs(max_scroll)) if abs(max_scroll) > 1e-3 else 0.0 x = self._viewport.x + scroll_ratio * slide_range # don't bounce up when NavWidget shows y = max(self._viewport.y, 0) + self._viewport.height - self._txt_scroll_indicator.height / 2 @@ -190,7 +190,7 @@ class _Scroller(Widget): self.scroll_panel.set_enabled(scroll_enabled and self.enabled and not self._scrolling_to[1]) self.scroll_panel.update(self._rect, content_size) if not self._snap_items: - return round(self.scroll_panel.get_offset()) + return self.scroll_panel.get_offset() # Snap closest item to center center_pos = self._rect.x + self._rect.width / 2 if self._horizontal else self._rect.y + self._rect.height / 2 @@ -341,7 +341,7 @@ class _Scroller(Widget): x, y = self._do_move_animation(item, x, y) # Update item state - item.set_position(round(x), round(y)) # round to prevent jumping when settling + item.set_position(x, y) item.set_parent_rect(self._rect) def _render_item(self, item: Widget): @@ -422,18 +422,10 @@ class Scroller(Widget): """Wrapper for _Scroller so that children do not need to call events or pass down enabled for nav stack.""" def __init__(self, **kwargs): super().__init__() - self._scroller = _Scroller([], **kwargs) + self._scroller = self._child(_Scroller([], **kwargs)) # pass down enabled to child widget for nav stack self._scroller.set_enabled(lambda: self.enabled) - def show_event(self): - super().show_event() - self._scroller.show_event() - - def hide_event(self): - super().hide_event() - self._scroller.hide_event() - def _render(self, _): self._scroller.render(self._rect) diff --git a/system/ui/widgets/slider.py b/system/ui/widgets/slider.py index 8f4bbfc011..bf965954f2 100644 --- a/system/ui/widgets/slider.py +++ b/system/ui/widgets/slider.py @@ -1,3 +1,4 @@ +import abc from collections.abc import Callable import pyray as rl @@ -5,19 +6,23 @@ import pyray as rl from openpilot.system.ui.lib.application import gui_app, FontWeight from openpilot.system.ui.widgets import Widget from openpilot.system.ui.widgets.label import UnifiedLabel -from openpilot.common.filter_simple import FirstOrderFilter +from openpilot.common.filter_simple import FirstOrderFilter, BounceFilter -class SmallSlider(Widget): +class SliderBase(Widget, abc.ABC): HORIZONTAL_PADDING = 8 CONFIRM_DELAY = 0.2 + PRESSED_SCALE = 1.07 - def __init__(self, title: str, confirm_callback: Callable | None = None): - # TODO: unify this with BigConfirmationDialogV2 + _bg_txt: rl.Texture + _circle_bg_txt: rl.Texture + _circle_bg_pressed_txt: rl.Texture + _circle_arrow_txt: rl.Texture + + def __init__(self, title: str, confirm_callback: Callable | None = None, shimmer_offset: float = 0.0): super().__init__() self._confirm_callback = confirm_callback - - self._font = gui_app.font(FontWeight.DISPLAY) + self._shimmer_offset = shimmer_offset self._load_assets() @@ -30,30 +35,34 @@ class SmallSlider(Widget): self._start_x_circle = 0.0 self._scroll_x_circle = 0.0 self._scroll_x_circle_filter = FirstOrderFilter(0, 0.05, 1 / gui_app.target_fps) + self._circle_scale_filter = BounceFilter(1.0, 0.1, 1 / gui_app.target_fps) + self._circle_press_time: float | None = None self._is_dragging_circle = False - self._label = UnifiedLabel(title, font_size=36, font_weight=FontWeight.SEMI_BOLD, text_color=rl.Color(255, 255, 255, int(255 * 0.65)), - alignment=rl.GuiTextAlignment.TEXT_ALIGN_RIGHT, - alignment_vertical=rl.GuiTextAlignmentVertical.TEXT_ALIGN_MIDDLE, line_height=0.9) + self._label = self._child(UnifiedLabel(title, font_size=36, font_weight=FontWeight.SEMI_BOLD, text_color=rl.WHITE, + alignment=rl.GuiTextAlignment.TEXT_ALIGN_RIGHT, + alignment_vertical=rl.GuiTextAlignmentVertical.TEXT_ALIGN_MIDDLE, line_height=0.9, shimmer=True)) + @abc.abstractmethod def _load_assets(self): - self.set_rect(rl.Rectangle(0, 0, 316 + self.HORIZONTAL_PADDING * 2, 100)) - - self._bg_txt = gui_app.texture("icons_mici/setup/small_slider/slider_bg.png", 316, 100) - self._circle_bg_txt = gui_app.texture("icons_mici/setup/small_slider/slider_red_circle.png", 100, 100) - self._circle_bg_pressed_txt = gui_app.texture("icons_mici/setup/small_slider/slider_red_circle_pressed.png", 100, 100) - self._circle_arrow_txt = gui_app.texture("icons_mici/setup/small_slider/slider_arrow.png", 37, 32) + ... @property def confirmed(self) -> bool: return self._confirmed_time > 0.0 + def show_event(self): + super().show_event() + self.reset() + def reset(self): # reset all slider state self._is_dragging_circle = False + self._circle_press_time = None self._confirmed_time = 0.0 self._confirm_callback_called = False + self._label.reset_shimmer(self._shimmer_offset) def set_opacity(self, opacity: float, smooth: bool = False): if smooth: @@ -84,6 +93,7 @@ class SmallSlider(Widget): if rl.check_collision_point_rec(mouse_event.pos, circle_button_rect): self._start_x_circle = mouse_event.pos.x self._is_dragging_circle = True + self._circle_press_time = rl.get_time() elif mouse_event.left_released: # swiped to left @@ -101,7 +111,7 @@ class SmallSlider(Widget): activated_pos = int(-self._bg_txt.width + self._circle_bg_txt.width) self._scroll_x_circle = max(min(self._scroll_x_circle, 0), activated_pos) - if self._confirmed_time > 0: + if self.confirmed: # swiped left to confirm self._scroll_x_circle_filter.update(activated_pos) @@ -119,8 +129,6 @@ class SmallSlider(Widget): self._scroll_x_circle_filter.x = self._scroll_x_circle def _render(self, _): - # TODO: iOS text shimmering animation - white = rl.Color(255, 255, 255, int(255 * self._opacity_filter.x)) bg_txt_x = self._rect.x + (self._rect.width - self._bg_txt.width) / 2 @@ -130,8 +138,9 @@ class SmallSlider(Widget): btn_x = bg_txt_x + self._bg_txt.width - self._circle_bg_txt.width + self._scroll_x_circle_filter.x btn_y = self._rect.y + (self._rect.height - self._circle_bg_txt.height) / 2 - if self._confirmed_time == 0.0 or self._scroll_x_circle > 0: - self._label.set_text_color(rl.Color(255, 255, 255, int(255 * 0.65 * (1.0 - self.slider_percentage) * self._opacity_filter.x))) + label_alpha = int(255 * (1.0 - self.slider_percentage) * self._opacity_filter.x) + if label_alpha > 0: + self._label.set_text_color(rl.Color(255, 255, 255, label_alpha)) label_rect = rl.Rectangle( self._rect.x + 20, self._rect.y, @@ -140,19 +149,23 @@ class SmallSlider(Widget): ) self._label.render(label_rect) - # circle and arrow - circle_bg_txt = self._circle_bg_pressed_txt if self._is_dragging_circle or self._confirmed_time > 0 else self._circle_bg_txt - rl.draw_texture_ex(circle_bg_txt, rl.Vector2(btn_x, btn_y), 0.0, 1.0, white) + # circle and arrow with grow animation + circle_pressed = self._is_dragging_circle or self.confirmed or (self._circle_press_time is not None and rl.get_time() - self._circle_press_time < 0.075) + circle_bg_txt = self._circle_bg_pressed_txt if circle_pressed else self._circle_bg_txt + scale = self._circle_scale_filter.update(self.PRESSED_SCALE if circle_pressed else 1.0) + scaled_btn_x = btn_x + (self._circle_bg_txt.width * (1 - scale)) / 2 + scaled_btn_y = btn_y + (self._circle_bg_txt.height * (1 - scale)) / 2 + rl.draw_texture_ex(circle_bg_txt, rl.Vector2(scaled_btn_x, scaled_btn_y), 0.0, scale, white) arrow_x = btn_x + (self._circle_bg_txt.width - self._circle_arrow_txt.width) / 2 - arrow_y = btn_y + (self._circle_bg_txt.height - self._circle_arrow_txt.height) / 2 + arrow_y = scaled_btn_y + (self._circle_bg_txt.height - self._circle_arrow_txt.height) / 2 rl.draw_texture_ex(self._circle_arrow_txt, rl.Vector2(arrow_x, arrow_y), 0.0, 1.0, white) -class LargerSlider(SmallSlider): - def __init__(self, title: str, confirm_callback: Callable | None = None, green: bool = True): +class LargerSlider(SliderBase): + def __init__(self, title: str, confirm_callback: Callable | None = None, green: bool = True, shimmer_offset: float = 0.0): self._green = green - super().__init__(title, confirm_callback=confirm_callback) + super().__init__(title, confirm_callback=confirm_callback, shimmer_offset=shimmer_offset) def _load_assets(self): self.set_rect(rl.Rectangle(0, 0, 520 + self.HORIZONTAL_PADDING * 2, 115)) @@ -164,13 +177,13 @@ class LargerSlider(SmallSlider): self._circle_arrow_txt = gui_app.texture("icons_mici/setup/small_slider/slider_arrow.png", 64, 55) -class BigSlider(SmallSlider): +class BigSlider(SliderBase): def __init__(self, title: str, icon: rl.Texture, confirm_callback: Callable | None = None): self._icon = icon super().__init__(title, confirm_callback=confirm_callback) - self._label = UnifiedLabel(title, font_size=48, font_weight=FontWeight.DISPLAY, text_color=rl.Color(255, 255, 255, int(255 * 0.65)), - alignment=rl.GuiTextAlignment.TEXT_ALIGN_RIGHT, alignment_vertical=rl.GuiTextAlignmentVertical.TEXT_ALIGN_MIDDLE, - line_height=0.875) + self._label.set_font_size(48) + self._label.set_font_weight(FontWeight.DISPLAY) + self._label.set_line_height(0.875) def _load_assets(self): self.set_rect(rl.Rectangle(0, 0, 520 + self.HORIZONTAL_PADDING * 2, 180)) diff --git a/third_party/.gitignore b/third_party/.gitignore deleted file mode 100644 index 0d20b6487c..0000000000 --- a/third_party/.gitignore +++ /dev/null @@ -1 +0,0 @@ -*.pyc diff --git a/third_party/json11/json11.cpp b/third_party/json11/json11.cpp index bc4045f07d..3bd4fde2f2 100644 --- a/third_party/json11/json11.cpp +++ b/third_party/json11/json11.cpp @@ -25,6 +25,7 @@ #include #include #include +#include namespace json11 { diff --git a/tools/README.md b/tools/README.md index d52c8f4522..90696ab4e6 100644 --- a/tools/README.md +++ b/tools/README.md @@ -38,7 +38,7 @@ scons -u -j$(nproc) Follow [these instructions](https://docs.microsoft.com/en-us/windows/wsl/install) to setup the WSL and install the `Ubuntu-24.04` distribution. Once your Ubuntu WSL environment is setup, follow the Linux setup instructions to finish setting up your environment. See [these instructions](https://learn.microsoft.com/en-us/windows/wsl/tutorials/gui-apps) for running GUI apps. -**NOTE**: If you are running WSL and any GUIs are failing (segfaulting or other strange issues) even after following the steps above, you may need to enable software rendering with `LIBGL_ALWAYS_SOFTWARE=1`, e.g. `LIBGL_ALWAYS_SOFTWARE=1 selfdrive/ui/ui`. +**NOTE**: If you are running WSL 2 and experiencing performance issues with the UI or simulator, you may need to explicitly enable hardware acceleration by setting `GALLIUM_DRIVER=d3d12` before commands. Add `export GALLIUM_DRIVER=d3d12` to your `~/.bashrc` file to make it automatic for future sessions. ## CTF Learn about the openpilot ecosystem and tools by playing our [CTF](/tools/CTF.md). diff --git a/tools/bodyteleop/.gitignore b/tools/bodyteleop/.gitignore deleted file mode 100644 index adeab99a95..0000000000 --- a/tools/bodyteleop/.gitignore +++ /dev/null @@ -1,4 +0,0 @@ -av -av-10.0.0/* -key.pem -cert.pem \ No newline at end of file diff --git a/tools/cabana/.gitignore b/tools/cabana/.gitignore index 3d64f83204..1ee6c92236 100644 --- a/tools/cabana/.gitignore +++ b/tools/cabana/.gitignore @@ -1,6 +1,8 @@ moc_* *.moc +assets.cc + _cabana dbc/car_fingerprint_to_dbc.json tests/test_cabana diff --git a/tools/cabana/SConscript b/tools/cabana/SConscript index 098a6351b7..dbe4dbc659 100644 --- a/tools/cabana/SConscript +++ b/tools/cabana/SConscript @@ -2,6 +2,8 @@ import subprocess import os import shutil +import libusb + Import('env', 'arch', 'common', 'messaging', 'visionipc', 'cereal') # Detect Qt - skip build if not available @@ -64,21 +66,18 @@ qt_env['LIBPATH'] += ['#selfdrive/ui', ] qt_env['LIBS'] = qt_libs base_frameworks = qt_env['FRAMEWORKS'] -base_libs = [common, messaging, cereal, visionipc, 'm', 'ssl', 'crypto', 'pthread'] + qt_env["LIBS"] +base_libs = [common, messaging, cereal, visionipc, 'm', 'pthread'] + qt_env["LIBS"] if arch == "Darwin": base_frameworks.append('QtCharts') else: base_libs.append('Qt5Charts') -qt_libs = base_libs - cabana_env = qt_env.Clone() -if arch == "Darwin": - cabana_env['CPPPATH'] += [f"{brew_prefix}/include"] - cabana_env['LIBPATH'] += [f"{brew_prefix}/lib"] +cabana_env['CPPPATH'] += [libusb.INCLUDE_DIR] +cabana_env['LIBPATH'] += [libusb.LIB_DIR] -cabana_libs = [cereal, messaging, visionipc, replay_lib, 'avformat', 'avcodec', 'swresample', 'avutil', 'x264', 'z', 'bz2', 'zstd', 'yuv', 'usb-1.0'] + qt_libs +cabana_libs = [cereal, messaging, visionipc, replay_lib, 'avformat', 'avcodec', 'swresample', 'avutil', 'x264', 'z', 'bz2', 'zstd', 'yuv', 'usb-1.0'] + base_libs opendbc_path = '-DOPENDBC_FILE_PATH=\'"%s"\'' % (cabana_env.Dir("../../opendbc/dbc").abspath) cabana_env['CXXFLAGS'] += [opendbc_path] @@ -88,12 +87,15 @@ assets_src = "assets/assets.qrc" cabana_env.Command(assets, assets_src, f"rcc $SOURCES -o $TARGET") cabana_env.Depends(assets, Glob('/assets/*', exclude=[assets, assets_src, "assets/assets.o"])) -cabana_lib = cabana_env.Library("cabana_lib", ['mainwin.cc', 'streams/socketcanstream.cc', 'streams/pandastream.cc', 'streams/devicestream.cc', 'streams/livestream.cc', 'streams/abstractstream.cc', 'streams/replaystream.cc', 'binaryview.cc', 'historylog.cc', 'videowidget.cc', 'signalview.cc', - 'streams/routes.cc', 'dbc/dbc.cc', 'dbc/dbcfile.cc', 'dbc/dbcmanager.cc', - 'utils/export.cc', 'utils/util.cc', 'utils/elidedlabel.cc', - 'chart/chartswidget.cc', 'chart/chart.cc', 'chart/signalselector.cc', 'chart/tiplabel.cc', 'chart/sparkline.cc', - 'commands.cc', 'messageswidget.cc', 'streamselector.cc', 'settings.cc', 'panda.cc', - 'cameraview.cc', 'detailwidget.cc', 'tools/findsimilarbits.cc', 'tools/findsignal.cc', 'tools/routeinfo.cc'], LIBS=cabana_libs, FRAMEWORKS=base_frameworks) +cabana_srcs = ['mainwin.cc', 'streams/pandastream.cc', 'streams/devicestream.cc', 'streams/livestream.cc', 'streams/abstractstream.cc', 'streams/replaystream.cc', 'binaryview.cc', 'historylog.cc', 'videowidget.cc', 'signalview.cc', + 'streams/routes.cc', 'dbc/dbc.cc', 'dbc/dbcfile.cc', 'dbc/dbcmanager.cc', + 'utils/export.cc', 'utils/util.cc', 'utils/elidedlabel.cc', + 'chart/chartswidget.cc', 'chart/chart.cc', 'chart/signalselector.cc', 'chart/tiplabel.cc', 'chart/sparkline.cc', + 'commands.cc', 'messageswidget.cc', 'streamselector.cc', 'settings.cc', 'panda.cc', + 'cameraview.cc', 'detailwidget.cc', 'tools/findsimilarbits.cc', 'tools/findsignal.cc', 'tools/routeinfo.cc'] +if arch != "Darwin": + cabana_srcs += ['streams/socketcanstream.cc'] +cabana_lib = cabana_env.Library("cabana_lib", cabana_srcs, LIBS=cabana_libs, FRAMEWORKS=base_frameworks) cabana_env.Program('_cabana', ['cabana.cc', cabana_lib, assets], LIBS=cabana_libs, FRAMEWORKS=base_frameworks) if GetOption('extras'): diff --git a/tools/cabana/assets/.gitignore b/tools/cabana/assets/.gitignore deleted file mode 100644 index 283034ca8b..0000000000 --- a/tools/cabana/assets/.gitignore +++ /dev/null @@ -1 +0,0 @@ -*.cc diff --git a/tools/cabana/cabana.cc b/tools/cabana/cabana.cc index 9e4cfc4a51..db26b4067a 100644 --- a/tools/cabana/cabana.cc +++ b/tools/cabana/cabana.cc @@ -5,7 +5,9 @@ #include "tools/cabana/streams/devicestream.h" #include "tools/cabana/streams/pandastream.h" #include "tools/cabana/streams/replaystream.h" +#ifdef __linux__ #include "tools/cabana/streams/socketcanstream.h" +#endif int main(int argc, char *argv[]) { QCoreApplication::setApplicationName("Cabana"); @@ -29,9 +31,11 @@ int main(int argc, char *argv[]) { cmd_parser.addOption({"msgq", "read can messages from the msgq"}); cmd_parser.addOption({"panda", "read can messages from panda"}); cmd_parser.addOption({"panda-serial", "read can messages from panda with given serial", "panda-serial"}); +#ifdef __linux__ if (SocketCanStream::available()) { cmd_parser.addOption({"socketcan", "read can messages from given SocketCAN device", "socketcan"}); } +#endif cmd_parser.addOption({"zmq", "read can messages from zmq at the specified ip-address", "ip-address"}); cmd_parser.addOption({"data_dir", "local directory with routes", "data_dir"}); cmd_parser.addOption({"no-vipc", "do not output video"}); @@ -51,8 +55,10 @@ int main(int argc, char *argv[]) { qWarning() << e.what(); return 0; } +#ifdef __linux__ } else if (SocketCanStream::available() && cmd_parser.isSet("socketcan")) { stream = new SocketCanStream(&app, {.device = cmd_parser.value("socketcan").toStdString()}); +#endif } else { uint32_t replay_flags = REPLAY_FLAG_NONE; if (cmd_parser.isSet("ecam")) replay_flags |= REPLAY_FLAG_ECAM; diff --git a/tools/cabana/streamselector.cc b/tools/cabana/streamselector.cc index efd00d3985..4ad552d4b4 100644 --- a/tools/cabana/streamselector.cc +++ b/tools/cabana/streamselector.cc @@ -4,11 +4,12 @@ #include #include -#include "streams/socketcanstream.h" #include "tools/cabana/streams/devicestream.h" #include "tools/cabana/streams/pandastream.h" #include "tools/cabana/streams/replaystream.h" +#ifdef __linux__ #include "tools/cabana/streams/socketcanstream.h" +#endif StreamSelector::StreamSelector(QWidget *parent) : QDialog(parent) { setWindowTitle(tr("Open stream")); @@ -35,9 +36,11 @@ StreamSelector::StreamSelector(QWidget *parent) : QDialog(parent) { addStreamWidget(new OpenReplayWidget, tr("&Replay")); addStreamWidget(new OpenPandaWidget, tr("&Panda")); +#ifdef __linux__ if (SocketCanStream::available()) { addStreamWidget(new OpenSocketCanWidget, tr("&SocketCAN")); } +#endif addStreamWidget(new OpenDeviceWidget, tr("&Device")); QObject::connect(btn_box, &QDialogButtonBox::rejected, this, &QDialog::reject); diff --git a/tools/clip/run.py b/tools/clip/run.py index a5587f239b..ed2a5075b4 100755 --- a/tools/clip/run.py +++ b/tools/clip/run.py @@ -63,8 +63,10 @@ def parse_args(): return args -def setup_env(output_path: str, big: bool = False, speed: int = 1, target_mb: float = 0, duration: int = 0): - os.environ.update({"RECORD": "1", "OFFSCREEN": "1", "RECORD_OUTPUT": str(Path(output_path).with_suffix(".mp4"))}) +def setup_env(output_path: str, big: bool = False, speed: int = 1, target_mb: float = 0, duration: int = 0, headless: bool = True): + os.environ.update({"RECORD": "1", "RECORD_OUTPUT": str(Path(output_path).with_suffix(".mp4"))}) + if headless: + os.environ["OFFSCREEN"] = "1" if speed > 1: os.environ["RECORD_SPEED"] = str(speed) if target_mb > 0 and duration > 0: @@ -302,11 +304,11 @@ def clip(route: Route, output: str, start: int, end: int, headless: bool = True, logger.error("No messages to render") sys.exit(1) - metadata = load_route_metadata(route) if show_metadata else None if headless: rl.set_config_flags(rl.ConfigFlags.FLAG_WINDOW_HIDDEN) with OpenpilotPrefix(shared_download_cache=True): + metadata = load_route_metadata(route) if show_metadata else None camera_paths = route.qcamera_paths() if use_qcam else route.camera_paths() frame_queue = FrameQueue(camera_paths, start, end, fps=FRAMERATE, use_qcam=use_qcam) @@ -349,8 +351,9 @@ def main(): logging.basicConfig(level=logging.INFO, format="%(asctime)s %(levelname)s\t%(message)s") args = parse_args() - setup_env(args.output, big=args.big, speed=args.speed, target_mb=args.file_size, duration=args.end - args.start) - clip(Route(args.route, data_dir=args.data_dir), args.output, args.start, args.end, not args.windowed, + headless = not args.windowed + setup_env(args.output, big=args.big, speed=args.speed, target_mb=args.file_size, duration=args.end - args.start, headless=headless) + clip(Route(args.route, data_dir=args.data_dir), args.output, args.start, args.end, headless, args.big, args.title, not args.no_metadata, not args.no_time_overlay, args.qcam) diff --git a/tools/op.sh b/tools/op.sh index 7c20403a27..f21a285d17 100755 --- a/tools/op.sh +++ b/tools/op.sh @@ -167,29 +167,6 @@ function op_check_os() { fi } -function op_check_python() { - echo "Checking for compatible python version..." - REQUIRED_PYTHON_VERSION=$(grep "requires-python" $OPENPILOT_ROOT/pyproject.toml) - INSTALLED_PYTHON_VERSION=$(python3 --version 2> /dev/null || true) - - if [[ -z $INSTALLED_PYTHON_VERSION ]]; then - echo -e " ↳ [${RED}✗${NC}] python3 not found on your system. You need python version satisfying $(echo $REQUIRED_PYTHON_VERSION | cut -d '=' -f2-) to continue!" - loge "ERROR_PYTHON_NOT_FOUND" - return 1 - else - LB=$(echo $REQUIRED_PYTHON_VERSION | tr -d '",' | awk '{ split($4, v, "."); printf "%d%02d%02d", v[1], v[2], v[3] }') - UB=$(echo $REQUIRED_PYTHON_VERSION | tr -d '",' | awk '{ split($6, v, "."); printf "%d%02d%02d", v[1], v[2], v[3] }') - VERSION=$(echo $INSTALLED_PYTHON_VERSION | awk '{ split($2, v, "."); printf "%d%02d%02d", v[1], v[2], v[3] }') - if [[ $VERSION -ge LB && $VERSION -lt UB ]]; then - echo -e " ↳ [${GREEN}✔${NC}] $INSTALLED_PYTHON_VERSION detected." - else - echo -e " ↳ [${RED}✗${NC}] You need a python version satisfying $(echo $REQUIRED_PYTHON_VERSION | cut -d '=' -f2-) to continue!" - loge "ERROR_PYTHON_VERSION" "$INSTALLED_PYTHON_VERSION" - return 1 - fi - fi -} - function op_check_venv() { echo "Checking for venv..." if [[ -f $OPENPILOT_ROOT/.venv/bin/activate ]]; then @@ -214,8 +191,6 @@ function op_before_cmd() { op_activate_venv - result="${result}\n$(( op_check_python ) 2>&1)" || (echo -e "$result" && return 1) - if [[ -z $VERBOSE ]]; then echo -e "${BOLD}Checking system →${NC} [${GREEN}✔${NC}]" else @@ -436,7 +411,7 @@ function op_default() { echo "" echo -e "${BOLD}${UNDERLINE}Commands [System]:${NC}" echo -e " ${BOLD}auth${NC} Authenticate yourself for API use" - echo -e " ${BOLD}check${NC} Check the development environment (git, os, python) to start using openpilot" + echo -e " ${BOLD}check${NC} Check the development environment (git, os) to start using openpilot" echo -e " ${BOLD}esim${NC} Manage eSIM profiles on your comma device" echo -e " ${BOLD}venv${NC} Activate the python virtual environment" echo -e " ${BOLD}setup${NC} Install openpilot dependencies" diff --git a/tools/plotjuggler/.gitignore b/tools/plotjuggler/.gitignore deleted file mode 100644 index 45559d0b09..0000000000 --- a/tools/plotjuggler/.gitignore +++ /dev/null @@ -1,3 +0,0 @@ -bin/ -bin -*.rlog diff --git a/tools/replay/.gitignore b/tools/replay/.gitignore index 83f0e99a8b..aa615770a2 100644 --- a/tools/replay/.gitignore +++ b/tools/replay/.gitignore @@ -1,5 +1,2 @@ -moc_* -*.moc - replay tests/test_replay diff --git a/tools/replay/SConscript b/tools/replay/SConscript index 3efa970b37..757f3fec4e 100644 --- a/tools/replay/SConscript +++ b/tools/replay/SConscript @@ -4,7 +4,7 @@ replay_env = env.Clone() replay_env['CCFLAGS'] += ['-Wno-deprecated-declarations'] base_frameworks = [] -base_libs = [common, messaging, cereal, visionipc, 'm', 'ssl', 'crypto', 'pthread'] +base_libs = [common, messaging, cereal, visionipc, 'm', 'pthread'] replay_lib_src = ["replay.cc", "consoleui.cc", "camera.cc", "filereader.cc", "logreader.cc", "framereader.cc", "route.cc", "util.cc", "seg_mgr.cc", "timeline.cc", "py_downloader.cc"] diff --git a/tools/replay/ui.py b/tools/replay/ui.py index 8707f2be99..7fe2f405a1 100755 --- a/tools/replay/ui.py +++ b/tools/replay/ui.py @@ -218,7 +218,7 @@ def ui_thread(addr): # Update camera texture from numpy array img_rgba = cv2.cvtColor(img, cv2.COLOR_RGB2RGBA) rl.update_texture(camera_texture, rl.ffi.cast("void *", img_rgba.ctypes.data)) - rl.draw_texture(camera_texture, 0, 0, rl.WHITE) + rl.draw_texture(camera_texture, 0, 0, rl.WHITE) # noqa: TID251 # display alerts rl.draw_text_ex(font, sm['selfdriveState'].alertText1, rl.Vector2(180, 150), 30, 0, rl.RED) @@ -227,15 +227,15 @@ def ui_thread(addr): # draw plots (texture is reused internally) plot_texture = draw_plots(plot_arr) if hor_mode: - rl.draw_texture(plot_texture, 640 + 384, 0, rl.WHITE) + rl.draw_texture(plot_texture, 640 + 384, 0, rl.WHITE) # noqa: TID251 else: - rl.draw_texture(plot_texture, 0, 600, rl.WHITE) + rl.draw_texture(plot_texture, 0, 600, rl.WHITE) # noqa: TID251 # Convert lid_overlay to RGBA and update top_down texture # lid_overlay is (384, 960), need to transpose to (960, 384) for row-major RGBA buffer lid_rgba = palette[lid_overlay.T] rl.update_texture(top_down_texture, rl.ffi.cast("void *", np.ascontiguousarray(lid_rgba).ctypes.data)) - rl.draw_texture(top_down_texture, 640, 0, rl.WHITE) + rl.draw_texture(top_down_texture, 640, 0, rl.WHITE) # noqa: TID251 SPACING = 25 lines = [ diff --git a/tools/replay/util.cc b/tools/replay/util.cc index 7294de8282..7b308b5c3d 100644 --- a/tools/replay/util.cc +++ b/tools/replay/util.cc @@ -1,7 +1,6 @@ #include "tools/replay/util.h" #include -#include #include #include @@ -162,15 +161,6 @@ void precise_nano_sleep(int64_t nanoseconds, std::atomic &interrupt_reques } } -std::string sha256(const std::string &str) { - unsigned char hash[SHA256_DIGEST_LENGTH]; - SHA256_CTX sha256; - SHA256_Init(&sha256); - SHA256_Update(&sha256, str.c_str(), str.size()); - SHA256_Final(hash, &sha256); - return util::hexdump(hash, SHA256_DIGEST_LENGTH); -} - std::vector split(std::string_view source, char delimiter) { std::vector fields; size_t last = 0; diff --git a/tools/replay/util.h b/tools/replay/util.h index ee92190337..a2d0f6203a 100644 --- a/tools/replay/util.h +++ b/tools/replay/util.h @@ -46,7 +46,6 @@ private: static constexpr float growth_factor = 1.5; }; -std::string sha256(const std::string &str); void precise_nano_sleep(int64_t nanoseconds, std::atomic &interrupt_requested); std::string decompressBZ2(const std::string &in, std::atomic *abort = nullptr); std::string decompressBZ2(const std::byte *in, size_t in_size, std::atomic *abort = nullptr); diff --git a/tools/scripts/adb_ssh.sh b/tools/scripts/adb_ssh.sh index 4527a0296d..b9668e7e0b 100755 --- a/tools/scripts/adb_ssh.sh +++ b/tools/scripts/adb_ssh.sh @@ -31,8 +31,12 @@ for name, port in sorted(ports): PY ) -# Forward SSH port first for interactive shell access. -adb forward tcp:2222 tcp:22 +# Forward SSH port, finding a free local port if 2222 is taken. +SSH_PORT=2222 +while ss -tln | grep -q ":${SSH_PORT} "; do + SSH_PORT=$((SSH_PORT + 1)) +done +adb forward tcp:${SSH_PORT} tcp:22 # SSH! -ssh comma@localhost -p 2222 "$@" +ssh comma@localhost -p ${SSH_PORT} "$@" diff --git a/tools/setup_dependencies.sh b/tools/setup_dependencies.sh index 0b785bf4a2..8132cd16dc 100755 --- a/tools/setup_dependencies.sh +++ b/tools/setup_dependencies.sh @@ -113,24 +113,12 @@ function install_python_deps() { source .venv/bin/activate } -function install_macos_deps() { - if ! command -v brew > /dev/null 2>&1; then - echo "homebrew not found, skipping macOS system dependency install" - return 0 - fi - - if ! command -v cmake > /dev/null 2>&1; then - brew install cmake - fi -} - # --- Main --- if [[ "$OSTYPE" == "linux-gnu"* ]]; then install_ubuntu_deps echo "[ ] installed system dependencies t=$SECONDS" elif [[ "$OSTYPE" == "darwin"* ]]; then - install_macos_deps if [[ $SHELL == "/bin/zsh" ]]; then RC_FILE="$HOME/.zshrc" elif [[ $SHELL == "/bin/bash" ]]; then diff --git a/tools/sim/bridge/metadrive/metadrive_common.py b/tools/sim/bridge/metadrive/metadrive_common.py index 42a7eb60dd..0106579b20 100644 --- a/tools/sim/bridge/metadrive/metadrive_common.py +++ b/tools/sim/bridge/metadrive/metadrive_common.py @@ -13,11 +13,9 @@ class CopyRamRGBCamera(RGBCamera): def get_rgb_array_cpu(self): origin_img = self.cpu_texture - img = np.frombuffer(origin_img.getRamImage().getData(), dtype=np.uint8) - img = img.reshape((origin_img.getYSize(), origin_img.getXSize(), -1)) - img = img[:,:,:3] # RGBA to RGB - # img = np.swapaxes(img, 1, 0) - img = img[::-1] # Flip on vertical axis + img = np.frombuffer(origin_img.getRamImageAs("RGB").getData(), dtype=np.uint8) + img = img.reshape((origin_img.getYSize(), origin_img.getXSize(), 3)) + img = img[::-1] # Flip on vertical axis return img diff --git a/uv.lock b/uv.lock index 743521fb2f..8e597db6ef 100644 --- a/uv.lock +++ b/uv.lock @@ -116,12 +116,12 @@ wheels = [ [[package]] name = "bzip2" version = "1.0.8" -source = { git = "https://github.com/commaai/dependencies.git?subdirectory=bzip2&rev=releases#9777ee38aa5ca9439843125392af38ed1262e500" } +source = { git = "https://github.com/commaai/dependencies.git?subdirectory=bzip2&rev=release-bzip2#4808f76c45cb797e697ab21e5e37d68a0ab3b2d4" } [[package]] name = "capnproto" version = "1.0.1" -source = { git = "https://github.com/commaai/dependencies.git?subdirectory=capnproto&rev=releases#9777ee38aa5ca9439843125392af38ed1262e500" } +source = { git = "https://github.com/commaai/dependencies.git?subdirectory=capnproto&rev=release-capnproto#f735fd22c66029b92019019d0596da6a4445b931" } [[package]] name = "casadi" @@ -371,7 +371,7 @@ wheels = [ [[package]] name = "eigen" version = "3.4.0" -source = { git = "https://github.com/commaai/dependencies.git?subdirectory=eigen&rev=releases#9777ee38aa5ca9439843125392af38ed1262e500" } +source = { git = "https://github.com/commaai/dependencies.git?subdirectory=eigen&rev=release-eigen#fc9915c3a81d6488eafcdbbdc428f15d8123e540" } [[package]] name = "execnet" @@ -385,7 +385,7 @@ wheels = [ [[package]] name = "ffmpeg" version = "7.1.0" -source = { git = "https://github.com/commaai/dependencies.git?subdirectory=ffmpeg&rev=releases#9777ee38aa5ca9439843125392af38ed1262e500" } +source = { git = "https://github.com/commaai/dependencies.git?subdirectory=ffmpeg&rev=release-ffmpeg#8d693da088e5905d4479550e07484961765df45b" } [[package]] name = "fonttools" @@ -432,7 +432,7 @@ wheels = [ [[package]] name = "gcc-arm-none-eabi" version = "13.2.1" -source = { git = "https://github.com/commaai/dependencies.git?subdirectory=gcc-arm-none-eabi&rev=releases#9777ee38aa5ca9439843125392af38ed1262e500" } +source = { git = "https://github.com/commaai/dependencies.git?subdirectory=gcc-arm-none-eabi&rev=release-gcc-arm-none-eabi#e101138b29023effc932df7a58fb76a26c4e443a" } [[package]] name = "ghp-import" @@ -449,7 +449,7 @@ wheels = [ [[package]] name = "git-lfs" version = "3.6.1" -source = { git = "https://github.com/commaai/dependencies.git?subdirectory=git-lfs&rev=releases#9777ee38aa5ca9439843125392af38ed1262e500" } +source = { git = "https://github.com/commaai/dependencies.git?subdirectory=git-lfs&rev=release-git-lfs#5407b1d37b7a8a9ae3747cc20cb6e7a7b01f5059" } [[package]] name = "google-crc32c" @@ -567,7 +567,12 @@ wheels = [ [[package]] name = "libjpeg" version = "3.1.0" -source = { git = "https://github.com/commaai/dependencies.git?subdirectory=libjpeg&rev=releases#9777ee38aa5ca9439843125392af38ed1262e500" } +source = { git = "https://github.com/commaai/dependencies.git?subdirectory=libjpeg&rev=release-libjpeg#83fa530843e5109c51aef14327b6fde5dcb4507b" } + +[[package]] +name = "libusb" +version = "1.0.29" +source = { git = "https://github.com/commaai/dependencies.git?subdirectory=libusb&rev=release-libusb#5f188080524c3c6d098ab6cb8d206ceef0394e8e" } [[package]] name = "libusb1" @@ -583,7 +588,7 @@ wheels = [ [[package]] name = "libyuv" version = "1922.0" -source = { git = "https://github.com/commaai/dependencies.git?subdirectory=libyuv&rev=releases#9777ee38aa5ca9439843125392af38ed1262e500" } +source = { git = "https://github.com/commaai/dependencies.git?subdirectory=libyuv&rev=release-libyuv#600cdd08cb77cbcc001daeb031abcb5c6008c7c2" } [[package]] name = "markdown" @@ -735,7 +740,7 @@ wheels = [ [[package]] name = "ncurses" version = "6.5" -source = { git = "https://github.com/commaai/dependencies.git?subdirectory=ncurses&rev=releases#9777ee38aa5ca9439843125392af38ed1262e500" } +source = { git = "https://github.com/commaai/dependencies.git?subdirectory=ncurses&rev=release-ncurses#0503ac0d54799b58c84f900dba75abcad17e780f" } [[package]] name = "numpy" @@ -796,6 +801,7 @@ dependencies = [ { name = "jeepney" }, { name = "json-rpc" }, { name = "libjpeg" }, + { name = "libusb" }, { name = "libusb1" }, { name = "libyuv" }, { name = "ncurses" }, @@ -806,7 +812,6 @@ dependencies = [ { name = "pycryptodome" }, { name = "pyjwt" }, { name = "pyserial" }, - { name = "python3-dev" }, { name = "pyzmq" }, { name = "qrcode" }, { name = "raylib" }, @@ -858,30 +863,31 @@ requires-dist = [ { name = "aiohttp" }, { name = "aiortc" }, { name = "av" }, - { name = "bzip2", git = "https://github.com/commaai/dependencies.git?subdirectory=bzip2&rev=releases" }, - { name = "capnproto", git = "https://github.com/commaai/dependencies.git?subdirectory=capnproto&rev=releases" }, + { name = "bzip2", git = "https://github.com/commaai/dependencies.git?subdirectory=bzip2&rev=release-bzip2" }, + { name = "capnproto", git = "https://github.com/commaai/dependencies.git?subdirectory=capnproto&rev=release-capnproto" }, { name = "casadi", specifier = ">=3.6.6" }, { name = "cffi" }, { name = "codespell", marker = "extra == 'testing'" }, { name = "coverage", marker = "extra == 'testing'" }, { name = "crcmod-plus" }, { name = "cython" }, - { name = "eigen", git = "https://github.com/commaai/dependencies.git?subdirectory=eigen&rev=releases" }, - { name = "ffmpeg", git = "https://github.com/commaai/dependencies.git?subdirectory=ffmpeg&rev=releases" }, - { name = "gcc-arm-none-eabi", git = "https://github.com/commaai/dependencies.git?subdirectory=gcc-arm-none-eabi&rev=releases" }, - { name = "git-lfs", git = "https://github.com/commaai/dependencies.git?subdirectory=git-lfs&rev=releases" }, + { name = "eigen", git = "https://github.com/commaai/dependencies.git?subdirectory=eigen&rev=release-eigen" }, + { name = "ffmpeg", git = "https://github.com/commaai/dependencies.git?subdirectory=ffmpeg&rev=release-ffmpeg" }, + { name = "gcc-arm-none-eabi", git = "https://github.com/commaai/dependencies.git?subdirectory=gcc-arm-none-eabi&rev=release-gcc-arm-none-eabi" }, + { name = "git-lfs", git = "https://github.com/commaai/dependencies.git?subdirectory=git-lfs&rev=release-git-lfs" }, { name = "hypothesis", marker = "extra == 'testing'", specifier = "==6.47.*" }, { name = "inputs" }, { name = "jeepney" }, { name = "jinja2", marker = "extra == 'docs'" }, { name = "json-rpc" }, - { name = "libjpeg", git = "https://github.com/commaai/dependencies.git?subdirectory=libjpeg&rev=releases" }, + { name = "libjpeg", git = "https://github.com/commaai/dependencies.git?subdirectory=libjpeg&rev=release-libjpeg" }, + { name = "libusb", git = "https://github.com/commaai/dependencies.git?subdirectory=libusb&rev=release-libusb" }, { name = "libusb1" }, - { name = "libyuv", git = "https://github.com/commaai/dependencies.git?subdirectory=libyuv&rev=releases" }, + { name = "libyuv", git = "https://github.com/commaai/dependencies.git?subdirectory=libyuv&rev=release-libyuv" }, { name = "matplotlib", marker = "extra == 'dev'" }, { name = "metadrive-simulator", marker = "platform_machine != 'aarch64' and extra == 'tools'", git = "https://github.com/commaai/metadrive.git?rev=minimal" }, { name = "mkdocs", marker = "extra == 'docs'" }, - { name = "ncurses", git = "https://github.com/commaai/dependencies.git?subdirectory=ncurses&rev=releases" }, + { name = "ncurses", git = "https://github.com/commaai/dependencies.git?subdirectory=ncurses&rev=release-ncurses" }, { name = "numpy", specifier = ">=2.0" }, { name = "opencv-python-headless", marker = "extra == 'dev'" }, { name = "pillow" }, @@ -897,7 +903,6 @@ requires-dist = [ { name = "pytest-mock", marker = "extra == 'testing'" }, { name = "pytest-subtests", marker = "extra == 'testing'" }, { name = "pytest-xdist", marker = "extra == 'testing'", git = "https://github.com/sshane/pytest-xdist?rev=2b4372bd62699fb412c4fe2f95bf9f01bd2018da" }, - { name = "python3-dev", git = "https://github.com/commaai/dependencies.git?subdirectory=python3-dev&rev=releases" }, { name = "pyzmq" }, { name = "qrcode" }, { name = "raylib", specifier = ">5.5.0.3" }, @@ -914,9 +919,9 @@ requires-dist = [ { name = "ty", marker = "extra == 'testing'" }, { name = "websocket-client" }, { name = "xattr" }, - { name = "zeromq", git = "https://github.com/commaai/dependencies.git?subdirectory=zeromq&rev=releases" }, + { name = "zeromq", git = "https://github.com/commaai/dependencies.git?subdirectory=zeromq&rev=release-zeromq" }, { name = "zstandard" }, - { name = "zstd", git = "https://github.com/commaai/dependencies.git?subdirectory=zstd&rev=releases" }, + { name = "zstd", git = "https://github.com/commaai/dependencies.git?subdirectory=zstd&rev=release-zstd" }, ] provides-extras = ["docs", "testing", "dev", "tools"] @@ -1286,11 +1291,6 @@ wheels = [ { url = "https://files.pythonhosted.org/packages/ec/57/56b9bcc3c9c6a792fcbaf139543cee77261f3651ca9da0c93f5c1221264b/python_dateutil-2.9.0.post0-py2.py3-none-any.whl", hash = "sha256:a8b2bc7bffae282281c8140a97d3aa9c14da0b136dfe83f850eea9a5f7470427", size = 229892, upload-time = "2024-03-01T18:36:18.57Z" }, ] -[[package]] -name = "python3-dev" -version = "3.12.8" -source = { git = "https://github.com/commaai/dependencies.git?subdirectory=python3-dev&rev=releases#9777ee38aa5ca9439843125392af38ed1262e500" } - [[package]] name = "pyyaml" version = "6.0.3" @@ -1659,7 +1659,7 @@ wheels = [ [[package]] name = "zeromq" version = "4.3.5" -source = { git = "https://github.com/commaai/dependencies.git?subdirectory=zeromq&rev=releases#9777ee38aa5ca9439843125392af38ed1262e500" } +source = { git = "https://github.com/commaai/dependencies.git?subdirectory=zeromq&rev=release-zeromq#768bd6d6d67acc7b4e919993967187532af0d410" } [[package]] name = "zstandard" @@ -1689,4 +1689,4 @@ wheels = [ [[package]] name = "zstd" version = "1.5.6" -source = { git = "https://github.com/commaai/dependencies.git?subdirectory=zstd&rev=releases#9777ee38aa5ca9439843125392af38ed1262e500" } +source = { git = "https://github.com/commaai/dependencies.git?subdirectory=zstd&rev=release-zstd#4d4dd0b74dfc52bdeec36706fd1a3a27754679ec" }