From: Soeren Apel Date: Thu, 14 Mar 2024 20:58:47 +0000 (+0100) Subject: Session: Fix issue #67 by improving error handling X-Git-Url: https://sigrok.org/gitweb/?p=pulseview.git;a=commitdiff_plain;h=HEAD;hp=2802b9ec97992323dc797c1b2cd5f9213e3d6932 Session: Fix issue #67 by improving error handling --- diff --git a/CMakeLists.txt b/CMakeLists.txt index 7791b1b1..ec86073d 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -48,6 +48,7 @@ option(ENABLE_DECODE "Build with libsigrokdecode" TRUE) option(ENABLE_FLOW "Build with libsigrokflow" FALSE) option(ENABLE_TESTS "Enable unit tests" FALSE) option(STATIC_PKGDEPS_LIBS "Statically link to (pkg-config) libraries" FALSE) +option(ENABLE_TS_UPDATE "Update .ts source files (Qt l10n)" FALSE) if(WIN32) # On Windows/MinGW we need to statically link to libraries. @@ -74,8 +75,59 @@ add_subdirectory(manual) #= Dependencies #------------------------------------------------------------------------------- +include(CheckCSourceCompiles) +include(CheckCXXCompilerFlag) +include(CheckCXXSourceCompiles) +include(CMakePushCheckState) +include(memaccess) + +find_package(PkgConfig) + +if(CMAKE_VERSION VERSION_EQUAL "3.8.0" OR CMAKE_VERSION VERSION_GREATER "3.8.0") + check_cxx_compiler_flag("-std=c++17" HAVE_STD_CXX_17) + check_cxx_compiler_flag("-std=c++14" HAVE_STD_CXX_14) + check_cxx_compiler_flag("-std=c++11" HAVE_STD_CXX_11) + if(HAVE_STD_CXX_17) + message(STATUS "Using C++17 for the application build") + set(CMAKE_CXX_STANDARD 17) + set(REQUIRED_STD_CXX_FLAGS "-std=c++17") + elseif(HAVE_STD_CXX_14) + message(STATUS "Using C++14 for the application build") + set(CMAKE_CXX_STANDARD 14) + set(REQUIRED_STD_CXX_FLAGS "-std=c++14") + elseif(HAVE_STD_CXX_11) + message(STATUS "Using C++11 for the application build") + set(CMAKE_CXX_STANDARD 11) + set(REQUIRED_STD_CXX_FLAGS "-std=c++11") + else() + message(FATAL_ERROR "Need modern C++, at least language standard 11") + endif() +else() + check_cxx_compiler_flag("-std=c++14" HAVE_STD_CXX_14) + check_cxx_compiler_flag("-std=c++11" HAVE_STD_CXX_11) + if(HAVE_STD_CXX_14) + message(STATUS "Using C++14 for the application build") + set(CMAKE_CXX_STANDARD 14) + set(REQUIRED_STD_CXX_FLAGS "-std=c++14") + elseif(HAVE_STD_CXX_11) + message(STATUS "Using C++11 for the application build") + set(CMAKE_CXX_STANDARD 11) + set(REQUIRED_STD_CXX_FLAGS "-std=c++11") + else() + message(FATAL_ERROR "Need modern C++, at least language standard 11") + endif() +endif() + list(APPEND PKGDEPS glib-2.0>=2.28.0) -list(APPEND PKGDEPS glibmm-2.4>=2.28.0) + +# Try to find the prefered glibmm-2.4. If not found then add glibmm-2.68 +# to the dependency list. +pkg_check_modules(GLIBMM_2_4 glibmm-2.4>=2.28.0) +if(GLIBMM_2_4_FOUND) + list(APPEND PKGDEPS glibmm-2.4>=2.28.0) +else() + list(APPEND PKGDEPS glibmm-2.68>=2.68.0) +endif() if(ENABLE_FLOW) list(APPEND PKGDEPS gstreamermm-1.0>=1.8.0) @@ -93,7 +145,6 @@ if(ANDROID) list(APPEND PKGDEPS libsigrokandroidutils>=0.1.0) endif() -find_package(PkgConfig) pkg_check_modules(LIBSRCXX ${LIBSR_CXX_BINDING}) if(NOT LIBSRCXX_FOUND OR NOT LIBSRCXX_VERSION) message(FATAL_ERROR "libsigrok C++ bindings missing, check libsigrok's 'configure' output (missing dependencies?)") @@ -102,20 +153,35 @@ pkg_check_modules(PKGDEPS REQUIRED ${PKGDEPS}) set(CMAKE_AUTOMOC TRUE) -find_package(Qt5 5.3 COMPONENTS Core Gui LinguistTools Widgets Svg REQUIRED) - -message(STATUS "Qt version: ${Qt5_VERSION}") +# Check for Qt5, and check for Qt6 if Qt5 is not found. +set(QT_COMPONENTS Core Gui LinguistTools Widgets Svg) +find_package(Qt5 5.3 QUIET COMPONENTS Core) +if(Qt5_FOUND) + find_package(Qt5 5.3 COMPONENTS ${QT_COMPONENTS} REQUIRED) + message(STATUS "Qt version: ${Qt5_VERSION}") +else() + find_package(Qt6 6.2 COMPONENTS ${QT_COMPONENTS} REQUIRED) + message(STATUS "Qt version: ${Qt6_VERSION}") +endif() if(WIN32) - # MXE workaround: Use pkg-config to find Qt5 libs. + # MXE workaround: Use pkg-config to find Qt5 and Qt6 libs. # https://github.com/mxe/mxe/issues/1642 # Not required (and doesn't work) on MSYS2. if(NOT DEFINED ENV{MSYSTEM}) - pkg_check_modules(QT5ALL REQUIRED Qt5Widgets>=5.3 Qt5Gui>=5.3 Qt5Svg>=5.3) + if(Qt5_FOUND) + pkg_check_modules(QT5ALL REQUIRED Qt5Widgets>=5.3 Qt5Gui>=5.3 Qt5Svg>=5.3) + else() + pkg_check_modules(QT6ALL REQUIRED Qt6Widgets>=6.2 Qt6Gui>=6.2 Qt6Svg>=6.2) + endif() endif() endif() -set(QT_LIBRARIES Qt5::Gui Qt5::Widgets Qt5::Svg) +if(Qt5_FOUND) + set(QT_LIBRARIES Qt5::Gui Qt5::Widgets Qt5::Svg) +else() + set(QT_LIBRARIES Qt6::Gui Qt6::Widgets Qt6::Svg) +endif() set(BOOSTCOMPS filesystem serialization system) if(ENABLE_TESTS) @@ -151,48 +217,44 @@ find_package(Threads REQUIRED) # Helper for checking for atomics function(check_working_cxx_atomics varname additional_lib) - include(CheckCXXSourceCompiles) - include(CMakePushCheckState) - cmake_push_check_state() - set(CMAKE_REQUIRED_FLAGS "-std=c++11") - set(CMAKE_REQUIRED_LIBRARIES "${additional_lib}") - set(CMAKE_REQUIRED_QUIET 1) - CHECK_CXX_SOURCE_COMPILES(" + cmake_push_check_state() + set(CMAKE_REQUIRED_FLAGS "${REQUIRED_STD_CXX_FLAGS}") + set(CMAKE_REQUIRED_LIBRARIES "${additional_lib}") + set(CMAKE_REQUIRED_QUIET 1) + CHECK_CXX_SOURCE_COMPILES(" #include std::atomic x; int main() { - return std::atomic_fetch_add_explicit(&x, 1, std::memory_order_seq_cst); + return std::atomic_fetch_add_explicit(&x, 1, std::memory_order_seq_cst); } " ${varname}) - cmake_pop_check_state() + cmake_pop_check_state() endfunction(check_working_cxx_atomics) # First check if atomics work without the library. # If not, check if the library exists, and atomics work with it. check_working_cxx_atomics(HAVE_CXX_ATOMICS_WITHOUT_LIB "") if(HAVE_CXX_ATOMICS_WITHOUT_LIB) - message(STATUS "Atomics provided by the C-library - yes") + message(STATUS "Atomics provided by the C-library - yes") else() - message(STATUS "Atomics provided by the C-library - no") - find_library(LIBATOMIC_LIBRARY NAMES atomic PATH_SUFFIXES lib) - if(LIBATOMIC_LIBRARY) - check_working_cxx_atomics(HAVE_CXX_ATOMICS_WITH_LIB "${LIBATOMIC_LIBRARY}") - if (HAVE_CXX_ATOMICS_WITH_LIB) - message(STATUS "Atomics provided by libatomic - yes") - else() - message(STATUS "Atomics provided by libatomic - no") - message(FATAL_ERROR "Compiler must support std::atomic!") - endif() - else() - message(FATAL_ERROR "Compiler appears to require libatomic, but cannot find it.") - endif() + message(STATUS "Atomics provided by the C-library - no") + find_library(LIBATOMIC_LIBRARY NAMES atomic PATH_SUFFIXES lib) + if(LIBATOMIC_LIBRARY) + check_working_cxx_atomics(HAVE_CXX_ATOMICS_WITH_LIB "${LIBATOMIC_LIBRARY}") + if (HAVE_CXX_ATOMICS_WITH_LIB) + message(STATUS "Atomics provided by libatomic - yes") + else() + message(STATUS "Atomics provided by libatomic - no") + message(FATAL_ERROR "Compiler must support std::atomic!") + endif() + else() + message(FATAL_ERROR "Compiler appears to require libatomic, but cannot find it.") + endif() endif() # Check availability of features which depend on library versions. # TODO Ideally use check_symbol_exists() instead, reduce boilerplate. if(ENABLE_DECODE) - include(CheckCSourceCompiles) - include(CMakePushCheckState) cmake_push_check_state() set(CMAKE_REQUIRED_INCLUDES "${PKGDEPS_INCLUDE_DIRS}") set(CMAKE_REQUIRED_LIBRARIES "sigrokdecode") @@ -215,7 +277,6 @@ endif() #= System Introspection #------------------------------------------------------------------------------- -include(memaccess) memaccess_check_unaligned_le(HAVE_UNALIGNED_LITTLE_ENDIAN_ACCESS) #=============================================================================== @@ -225,7 +286,11 @@ memaccess_check_unaligned_le(HAVE_UNALIGNED_LITTLE_ENDIAN_ACCESS) set(PV_TITLE PulseView) set(PV_VERSION_STRING "0.5.0") -set(PV_GLIBMM_VERSION ${PKGDEPS_glibmm-2.4_VERSION}) +if(GLIBMM_2_4_FOUND) + set(PV_GLIBMM_VERSION ${PKGDEPS_glibmm-2.4_VERSION}) +else() + set(PV_GLIBMM_VERSION ${PKGDEPS_glibmm-2.68_VERSION}) +endif() include(GetGitRevisionDescription) @@ -462,7 +527,11 @@ if(ANDROID) ) endif() -qt5_add_resources(pulseview_RESOURCES_RCC ${pulseview_RESOURCES}) +if(Qt5_FOUND) + qt5_add_resources(pulseview_RESOURCES_RCC ${pulseview_RESOURCES}) +else() + qt6_add_resources(pulseview_RESOURCES_RCC ${pulseview_RESOURCES}) +endif() #=============================================================================== #= Translations @@ -474,10 +543,19 @@ if (NOT CMAKE_SOURCE_DIR STREQUAL CMAKE_BINARY_DIR) configure_file("translations.qrc" "translations.qrc" COPYONLY) endif () -qt5_add_translation(QM_FILES ${TS_FILES}) -qt5_create_translation(QM_FILES ${pulseview_SOURCES} ${TS_FILES}) - -qt5_add_resources(pulseview_RESOURCES_RCC ${CMAKE_BINARY_DIR}/translations.qrc) +if(Qt5_FOUND) + qt5_add_translation(QM_FILES ${TS_FILES}) + qt5_add_resources(pulseview_RESOURCES_RCC ${CMAKE_BINARY_DIR}/translations.qrc) + if (ENABLE_TS_UPDATE) + qt5_create_translation(QM_FILES ${pulseview_SOURCES} ${TS_FILES}) + endif () +else() + qt6_add_translation(QM_FILES ${TS_FILES}) + qt6_add_resources(pulseview_RESOURCES_RCC ${CMAKE_BINARY_DIR}/translations.qrc) + if (ENABLE_TS_UPDATE) + qt6_create_translation(QM_FILES ${pulseview_SOURCES} ${TS_FILES}) + endif () +endif() #=============================================================================== #= Global Definitions @@ -486,7 +564,8 @@ qt5_add_resources(pulseview_RESOURCES_RCC ${CMAKE_BINARY_DIR}/translations.qrc) add_definitions(-DQT_NO_KEYWORDS) add_definitions(-D__STDC_LIMIT_MACROS) add_definitions(-Wall -Wextra) -add_definitions(-std=c++11) +add_definitions(${REQUIRED_STD_CXX_FLAGS}) + add_definitions(-DBOOST_MATH_DISABLE_FLOAT128=1) if(WIN32) add_definitions(-Wa,-mbig-obj -O3) @@ -558,12 +637,18 @@ if(WIN32) # We also need QWindowsIntegrationPlugin, Qt5PlatformSupport (only for # Qt < 5.8.0), and all Qt libs and their dependencies. add_definitions(-DQT_STATICPLUGIN) - list(APPEND PULSEVIEW_LINK_LIBS Qt5::QSvgPlugin) - list(APPEND PULSEVIEW_LINK_LIBS Qt5::QWindowsIntegrationPlugin) - if(Qt5Gui_VERSION VERSION_LESS 5.8.0) - list(APPEND PULSEVIEW_LINK_LIBS -lQt5PlatformSupport) + if(Qt5_FOUND) + list(APPEND PULSEVIEW_LINK_LIBS Qt5::QSvgPlugin) + list(APPEND PULSEVIEW_LINK_LIBS Qt5::QWindowsIntegrationPlugin) + if(Qt5Gui_VERSION VERSION_LESS 5.8.0) + list(APPEND PULSEVIEW_LINK_LIBS -lQt5PlatformSupport) + endif() + list(APPEND PULSEVIEW_LINK_LIBS ${QT5ALL_LDFLAGS}) + else() + list(APPEND PULSEVIEW_LINK_LIBS Qt6::QSvgPlugin) + list(APPEND PULSEVIEW_LINK_LIBS Qt6::QWindowsIntegrationPlugin) + list(APPEND PULSEVIEW_LINK_LIBS ${QT6ALL_LDFLAGS}) endif() - list(APPEND PULSEVIEW_LINK_LIBS ${QT5ALL_LDFLAGS}) endif() if(ENABLE_STACKTRACE) diff --git a/doc/pulseview.1 b/doc/pulseview.1 index 9663fdf9..749f6dab 100644 --- a/doc/pulseview.1 +++ b/doc/pulseview.1 @@ -138,6 +138,9 @@ Quit, i.e. shutdown PulseView (closing all session tabs). .TP .B "CTRL+w" Close the current session tab. +.TP +.B "SHIFT+mouse wheel" +Scroll horizontally instead of zooming in/out. .SH "EXIT STATUS" .B PulseView exits with 0 on success, 1 on most failures. diff --git a/l10n/es_MX.ts b/l10n/es_MX.ts index b7426b04..77afc7fe 100644 --- a/l10n/es_MX.ts +++ b/l10n/es_MX.ts @@ -4,9 +4,9 @@ Application - + Some parts of the application may still use the previous language. Re-opening the affected windows or restarting the application will remedy this. - Algunas partes de la aplicación aún pueden usar el idioma anterior. Volver a abrir las ventanas afectadas o reiniciar la aplicación solucionará esto. + Algunas partes de la aplicación podrían seguir usando el idioma anterior. Volver a abrir las ventanas afectadas o reiniciar la aplicación solucionará esto. @@ -35,7 +35,7 @@ QHexView - + No data available Datos no disponibles @@ -43,20 +43,21 @@ QObject - + Stack trace of previous crash: - Stack trace de crash previo: + Seguimiento de pila del fallo anterior: - + Don't show this message again - No mostrar este mensaje de nuevo + No volver a mostrar este mensaje - + When %1 last crashed, it created a stack trace. A human-readable form has been saved to disk and was written to the log. You may access it from the settings dialog. - Cuando %1 se bloqueó por última vez, creó un stack trace.\nSe guardó un formulario legible en el disco y fue escrito en el log. Puedes acceder a el desde el dialogo de configuración. + Cuando %1 se bloqueó por última vez, creó un seguimiento de pila. +Se guardó un formulario legible para humanosen el disco y fue escrito en el log. Puedes acceder a el desde el dialogo de configuración. @@ -77,79 +78,80 @@ A human-readable form has been saved to disk and was written to the log. You may PulseView - + Decoder Selector - Selección de decoder + Selección de decodificador - + Session %1 Sesión %1 - + Create New Session - Crear Nueva Sesión + Crear nueva sesión - + Start/Stop Acquisition - Iniciar/Detener Adquisición + Iniciar/Detener adquisición - + Settings - Configuraciones + Ajustes - + Reload Recargar - - + + Run Ejecutar - + Stop Detener - - - + + + Confirmation Confirmación - + There is unsaved data. Close anyway? - Hay datos sin guardar. Cerrar de todos modos? + Hay datos sin guardar. ¿Cerrar de todos modos? - - + + This session contains unsaved data. Close it anyway? - Esta sesión contiene datos sin almacenar. Cerrar de todos modos? + Esta sesión contiene datos sin guardar. ¿Cerrar de todos modos? pv::Session - + Failed to select device + Si en el panel "Sources and forms" la cadena de texto está dentro de "show_session_error(tr("Failed to ..."),e)" traducir "Failed " como "Error" Error al seleccionar dispositivo - + Failed to open device Error al abrir dispositivo - + Error Error @@ -158,32 +160,37 @@ A human-readable form has been saved to disk and was written to the log. You may Formato de entrada inesperado: %s - + + Can't restore generated signal of unknown type %1 (%2) + No se puede restaurar la señal generada de tipo desconocido %1 ( %2) + + + Unexpected input format: %1 - + Formato de entrada inesperado: %1 - + Failed to load %1 Error al cargar %1 - + No active device set, can't start acquisition. No hay un dispositivo activo configurado, no se puede iniciar la adquisición. - + No channels enabled. No hay canales habilitados. - + Out of memory, acquisition stopped. Sin memoria, la adquisición se detuvo. - + Can't handle more than 64 logic channels. No puede manejar más de 64 canales lógicos. @@ -211,8 +218,9 @@ A human-readable form has been saved to disk and was written to the log. You may No se puede guardar el rango sin datos de muestra. - - + + + Error while saving: Error al guardar: @@ -220,93 +228,128 @@ A human-readable form has been saved to disk and was written to the log. You may pv::binding::Device - + + Note for device developers: Ignoring device configuration capability '%1' as it is missing GET and/or SET + Nota para desarrolladores de dispositivos: Ignorar la capacidad de configuración del dispositivo '%1', ya que falta GET y/o SET + + + No Limit - + Sín límite pv::data::DecodeSignal - + No decoders Sin decodificadores - + There are no channels assigned to this decoder No hay canales asignados a este decodificador - + One or more required channels have not been specified No se han especificado uno o más canales requeridos - + No input data Sin datos de entrada - + Decoder reported an error El decodificador reportó un error - + Failed to create decoder instance Error al crear la instancia del decodificador + + pv::data::MathSignal + + + Math%1 + Math%1 + + + + No expression defined, nothing to do + Sin expresión definida, nada que hacer + + + + %1 at line %2, column %3: %4 + %1 en línea %2, columna %3: %4 + + + + + "%1" isn't a valid analog signal + "%1" no es una señal analógica válida + + + + + No data will be generated as %1 must be enabled + No se generarán datos ya que %1 debe estar habilitado + + pv::data::SignalBase - + Signal average Promedio de la señal - + 0.9V (for 1.8V CMOS) 0.9V (para 1.8V CMOS) - + 1.8V (for 3.3V CMOS) 1.8V (para 3.3V CMOS) - + 2.5V (for 5.0V CMOS) 2.5V (para 5.0V CMOS) - + 1.5V (for TTL) 1.5V (para TTL) - + Signal average +/- 15% Promedio de la señal +/- 15% - + 0.3V/1.2V (for 1.8V CMOS) 0.3V/1.2V (para 1.8V CMOS) - + 0.7V/2.5V (for 3.3V CMOS) 0.7V/2.5V (para 3.3V CMOS) - + 1.3V/3.7V (for 5.0V CMOS) 1.3V/3.7V (para 5.0V CMOS) - + 0.8V/2.0V (for TTL) 0.8V/2.0V (para TTL) @@ -316,7 +359,7 @@ A human-readable form has been saved to disk and was written to the log. You may &Scan for devices using driver above - E&Scanea por dispositivos utilizando el driver de arriba + E&scanea por dispositivos utilizando el controlador de arriba @@ -326,7 +369,7 @@ A human-readable form has been saved to disk and was written to the log. You may Step 1: Choose the driver - Paso 1: Elige el driver + Paso 1: Elige el controlador @@ -336,7 +379,7 @@ A human-readable form has been saved to disk and was written to the log. You may Serial &Port - &Puerto Serial + &Puerto serial @@ -356,7 +399,7 @@ A human-readable form has been saved to disk and was written to the log. You may Step 3: Scan for devices - Paso 3: Escanear por dispositivos + Paso 3: Escanea por dispositivos @@ -379,7 +422,7 @@ A human-readable form has been saved to disk and was written to the log. You may - + Decoders Decodificadores @@ -391,293 +434,327 @@ A human-readable form has been saved to disk and was written to the log. You may Logging - Logging + Registros - + User interface language - Lenguaje de la interfaz de usuario + Idioma de la interfaz de usuario - + User interface theme Tema de la interfaz de usuario - + (You may need to restart PulseView for all UI elements to update) (Es posible que deba reiniciar PulseView para que se actualicen todos los elementos de la interfaz de usuario) - + System Default - Default del sistema + Por defecto del sistema - + Qt widget style - Estilo de Qt widget + Estilo de widget Qt - + (Dark themes look best with the Fusion style) (Los temas oscuros se ven mejor con el estilo Fusion) - + Save session &setup along with .sr file Guardar &configuración de sesión junto al archivo .sr - + + Start acquisition for all open sessions when clicking 'Run' + Iniciar adquisición para todas las sesiones abiertas al dar clic en 'Ejecutar' + + + Trace View - Vista de trazo + Vista de señales - + Use colored trace &background - Use &fondo de trazas coloreado + Usar &fondo de trazos coloreado - + Constantly perform &zoom-to-fit during acquisition Realizar constantemente zoom para &ajustar durante la adquisición - + Perform a zoom-to-&fit when acquisition stops - Realice un zoom para ajustar cuando la adquisición se &detenga + Realizar un zoom para ajustar cuando la adquisición se &detenga - Show time zero at the trigger - Mostrar el tiempo cero en el trigger + Mostrar el tiempo cero en el trigger - + Always keep &newest samples at the right edge during capture - Mantenga siempre las muestras más &recientes en el borde derecho durante la captura + Mantener siempre las muestras más &recientes en el borde derecho durante la captura - + Show data &sampling points - Mostrar puntos de datos &sampleados + Mostrar puntos de datos mue&streados - Fill high areas of logic signals - Rellenar áreas altas de señales lógicas + Rellenar áreas altas de señales lógicas + + + + Show time zero at the &trigger + Mostrar tiempo cero en el &disparo + + + + Allow &vertical dragging in the view area + Permitir arrastre &vertical in el área de vista + + + + Fill &high areas of logic signals + Llenar áreas en &alto de señales lógicas - + Color to fill high areas of logic signals with Color para llenar áreas altas de señales lógicas - + Show analog minor grid in addition to div grid - Mostrar cuadrícula menor analogíca además de cuadrícula por div + Mostrar cuadrícula menor analógica además de cuadrícula por división - + Highlight mouse cursor using a vertical marker line - Resalte el cursor del mouse usando una línea de marcador vertical + Resaltar el cursor del mouse usando una línea de marcador vertical - - - + + Keep active item on ruler selected when editing popup is closed + Mantener el elemento activo seleccionado en la regla cuando se cierre la ventana de edición emergente + + + + + pixels píxeles - + Maximum distance from edges before markers snap to them Distancia máxima desde los bordes antes de que los marcadores se ajusten a ellos - + Color to fill cursor area with Color para llenar el área del cursor - + None Ninguna - + Background Fondo - + Dots Puntos - + Conversion threshold display mode (analog traces only) - Modo de visualización del umbral de conversión (solo trazas analógicas) + Modo de visualización del umbral de conversión (solo trazos analógicos) - + Default analog trace div height - Altura de div de trazo análogo por defecto + Altura de división de trazo analógico por defecto - + Default logic trace height Altura de trazo lógico por defecto - + Allow configuration of &initial signal state Permitir configuración de estado de señal &inicial - + Always show all &rows, even if no annotation is visible Mostrar siempre todas las &filas, incluso si no hay ninguna anotación visible - + Annotation export format Formato de exportación de anotaciones - + %s = sample range; %d: decoder name; %r: row name; %c: class name %s = rango de muestra; %d: nombre del decodificador; %r: nombre de fila; %c: nombre de clase - + %1: longest annotation text; %a: all annotation texts; %q: use quotation marks %1: texto de anotación más largo; %a: todos los textos de anotación; %q: use comillas - + %1<br /><a href="http://%2">%2</a> %1<br /><a href="http://%2">%2</a> - + GNU GPL, version 3 or later GNU GPL, versión 3 o posterior - + Versions, libraries and features: - Versiones, librerías y características: + Versiones, bibliotecas y características: - + Firmware search paths: Rutas de búsqueda de firmware: - + Protocol decoder search paths: Ruta de búsqueda del decodificador de protocolo: - + + <tr><td colspan="2">(Note: Set environment variable SIGROKDECODE_DIR to add a custom directory)</td></tr> + <tr> <td colspan = "2"> (Nota: Establecer variable de entorno SIGROKDECODE_DIR para agregar un directorio personalizado) </td> </tr> + + + Supported hardware drivers: - Drivers de hardware soportados: + Controladores de hardware soportados: - + Supported input formats: Formatos de entrada soportados: - + Supported output formats: Formatos de salida soportados: - + Supported protocol decoders: Decodificadores de protocolo soportados: - + Available Translations: - + Traducciones disponibles: - + Log level: - Nivel de log: + Nivel de registro: - + lines líneas - + Length of background buffer: Longitud del búfer de fondo: - + &Save to File &Guardar en archivo - + &Pop out - &Pop out + Des&plegar - + You selected a dark theme. Should I set the user-adjustable colors to better suit your choice? Please keep in mind that PulseView may need a restart to display correctly. - Seleccionaste el tema obscuro.\nDebería de establecer los colores ajustables por el usuario que mejor se ajustan a tu elección?\n\nPor favor ten en cuenta que Pulseview tal vez se tenga que reiniciar para mostrar correctamente. + Seleccionaste un tema oscuro. +¿Debería de establecer los colores ajustables por el usuario a los que mejor se ajustan a tu elección? + +Por favor ten en cuenta que Pulseview tal vez se tenga que reiniciar para mostrarse correctamente. - + You selected a bright theme. Should I set the user-adjustable colors to better suit your choice? Please keep in mind that PulseView may need a restart to display correctly. - Seleccionaste el tema brillante.\nDebería de establecer los colores ajustables por el usuario que mejor se ajustan a tu elección?\n\nPor favor ten en cuenta que Pulseview tal vez se tenga que reiniciar para mostrar correctamente. + Seleccionaste un tema claro. +¿Debería de establecer los colores ajustables por el usuario a los que mejor se ajustan a tu elección? + +Por favor ten en cuenta que Pulseview tal vez se tenga que reiniciar para mostrarse correctamente. - + Save Log - Guardar log + Guardar registro - + Log Files (*.txt *.log);;All Files (*) - Archivos de log (*.txt *.log);;Todos los archivos (*) + Archivos de registro (*.txt *.log);;Todos los archivos (*) - + Success Éxito - + Log saved to %1. - Log guardado en %1. + Registro guardado en %1. - + Error Error - + File %1 could not be written to. No se pudo escribir en el archivo%1. - + %1 Log %1 Log @@ -695,7 +772,7 @@ Please keep in mind that PulseView may need a restart to display correctly.Cancelar - + Failed to save session. Error al guardar sesión. @@ -705,8 +782,8 @@ Please keep in mind that PulseView may need a restart to display correctly. - - + + All Todo @@ -720,7 +797,7 @@ Please keep in mind that PulseView may need a restart to display correctly. Analog - Análogo + Análogico @@ -753,8 +830,8 @@ Please keep in mind that PulseView may need a restart to display correctly.Habilitar: - - + + None Ninguna @@ -809,7 +886,7 @@ Please keep in mind that PulseView may need a restart to display correctly. Decoder - Decoder + Decodificador @@ -824,7 +901,7 @@ Please keep in mind that PulseView may need a restart to display correctly. All Decoders - Todos los decoders + Todos los decodificadores @@ -832,43 +909,43 @@ Please keep in mind that PulseView may need a restart to display correctly. Select a decoder to see its description here. - Seleccione un decoder para ver su descripción aquí. + Selecciona un decodificador para ver su descripción aquí. - + , %1 , %1 - + <p align='right'>Tags: %1</p> - <p align='right'>Tags: %1</p> + <p align='right'>Etiquetas: %1</p> - + Protocol decoder <b>%1</b> requires input type <b>%2</b> which several decoders provide.<br>Choose which one to use:<br> Decodificador de protocolo <b>%1</b> requiere tipo de entrada <b>%2</b> que proporcionan varios decodificadores.<br>Elige cúal usar:<br> - + Choose Decoder - Elige Decoder + Elige decodificador pv::toolbars::MainBar - + New &View Nueva &Vista - + &Open... &Abrir... - + Restore Session Setu&p... Restaurar Configu&ración de Sesión... @@ -877,156 +954,161 @@ Please keep in mind that PulseView may need a restart to display correctly.G&uardar Como... - + &Save... - &Guardar... + &Guardar... - + Save &As... - + Guardar Como... - + Save Selected &Range As... Guardar &Rango Seleccionado Como... - + Save Session Setu&p... Guardar Confi&guración de Sesión... - + &Export - &Exporta + &Exportar - + &Import - &Importa + &Importar - + &Connect to Device... - &Conecta a Dispositivo... + &Conectar a Dispositivo... - + Add protocol decoder Agregar decodificador de protocolo - + + Add math signal + Agregar señal matemática + + + Configure Device - Configura Dispositivo + Configurar Dispositivo - + Configure Channels - Configura Canales + Configurar Canales - + Failed to get sample rate list: Error al obtener la lista de frecuencia de muestreo: - + Failed to get sample rate: - Error al obtener la lista de frecuencia de muestreo: + Error al obtener la frecuencia de muestreo: - + Failed to get sample limit list: Error al obtener la lista de límites de muestra: - + Failed to configure samplerate: Error al configurar frecuencia de muestreo: - + Failed to configure sample count: Error al configurar cuenta de muestras: - + Missing Cursors Cursores Faltantes - + You need to set the cursors before you can save the data enclosed by them to a session file (e.g. using the Show Cursors button). - Debe configurar los cursores antes de poder guardar los datos encerrados en un archivo de sesión (por ejemplo, usando el botón Mostrar Cursores). + Debes configurar los cursores antes de poder guardar los datos encerrados en un archivo de sesión (por ejemplo, usando el botón Mostrar Cursores). - + Invalid Range Rango Inválido - + The cursors don't define a valid range of samples. Los cursores no definen un rango válido de muestras. - + %1 files %1 archivos - - + + All Files Todos los archivos - - + + Save File Guardar Archivo - + Export %1 - Exporta %1 + Exportar %1 - + %1 files %1 archivos - + Import File - Importa Archivo + Importar Archivo - + Import %1 - Importa %1 + Importar %1 - - + + Open File Abrir Archivo - + sigrok Sessions (*.sr);;All Files (*) Sesiones sigrok (*sr);;Todos los archivos (*) - - + + PulseView Session Setups (*.pvs);;All Files (*) Configurciones de Sesión de PulseView (*.pvs);;Todos los Archivos (*) - + Total sampling time: %1 Tiempo de muestreo total: %1 @@ -1046,7 +1128,7 @@ Please keep in mind that PulseView may need a restart to display correctly. Hexdump - Hexdump + Volcado hexadecimal @@ -1054,32 +1136,32 @@ Please keep in mind that PulseView may need a restart to display correctly.&Guardar... - - + + Save Binary Data Guardar Datos Binarios - + Binary Data Files (*.bin);;All Files (*) - Archivos de Datos Binarios (*.txt);;Todos los archivos (*) + Archivos de Datos Binarios (*.bin);;Todos los archivos (*) - - + + Error Error - - + + File %1 could not be written to. No se pudo escribir en el archivo%1. - + Hex Dumps (*.txt);;All Files (*) - Hex Dumps (*.txt);;Todos los archivos (*) + Volcados hexadecimales (*.txt);;Todos los archivos (*) @@ -1087,42 +1169,42 @@ Please keep in mind that PulseView may need a restart to display correctly. Sample - + Muestra Time - Tiempo + Tiempo Decoder - Decoder + Decodificador Ann Row - + Fila de anotación Ann Class - + Clase de anotación Value - + Valor s - + s sa - + sa @@ -1130,120 +1212,120 @@ Please keep in mind that PulseView may need a restart to display correctly. Decoder: - Decodificador: + Decodificador: Hide Hidden Rows/Classes - + Ocultar Filas/Columnas ocultas &Save... - &Guardar... + &Guardar... - + Save Annotations as CSV - + Guardar anotaciones como CSV - + CSV Files (*.csv);;Text Files (*.txt);;All Files (*) - + Archivos CSV (*.csv);;Archivos de texto (*.txt);;Todos los archivos (*) - + Error - Error + Error - + File %1 could not be written to. - No se pudo escribir en el archivo%1. + No se pudo escribir en el archivo%1. pv::views::trace::AnalogSignal - + Number of pos vertical divs - Número de divisiones verticales pos + Número de divisiones verticales positivas - + Number of neg vertical divs - Número de divisiones verticales neg + Número de divisiones verticales negativas - + pixels píxeles - + Div height - Altura de div + Altura de división - + V/div - V/div + V/división - + Vertical resolution Resolución vertical - + Autoranging Autorango - + none ninguna - + to logic via threshold a nivel lógico a partir de umbral - + to logic via schmitt-trigger - a nivel lógico a partir de schmitt trigger + a nivel lógico a partir de schmitt-trigger - + Conversion Conversión - + Conversion threshold(s) Umbral(es) de conversión - + analog - análogo + señal análogica - + converted - convertida + señal convertida - + analog+converted - Analógico+convertido + señales analógica + convertida - + Show traces for - Mostrar trazos para + Mostrar trazos de @@ -1259,154 +1341,154 @@ Please keep in mind that PulseView may need a restart to display correctly. Display interval - Muestra intervalo + Mostrar intervalo Display frequency - Muestra frecuencia + Mostrar frecuencia Display samples - Muestra samples + Mostrar muestras pv::views::trace::DecodeTrace - + <p><i>No decoders in the stack</i></p> - <p><i>No hay decodificadores en el stack.</i></p> + <p><i>No hay decodificadores en la pila.</i></p> - + <i>* Required channels</i> <i>* Canales requeridos</i> - + Stack Decoder - Decodificadores + Apilar Decodificador - + Stack a higher-level decoder on top of this one Apilar un decodificador de nivel superior encima de este - + Delete Eliminar - + Resume decoding Reanudar decodificación - + Pause decoding Pausar decodificación - + Copy annotation text to clipboard - Copiar texto de anotación al clipboard + Copiar texto de anotación al portapapeles - + Export all annotations Exportar todas las anotaciones - + Export all annotations for this row Exportar todas las anotaciones para esta fila - + Export all annotations, starting here Exportar todas las anotaciones, comenzando aquí - + Export annotations for this row, starting here Exportar todas las anotaciones para esta fila, comenzando aquí - + Export all annotations within cursor range Exportar todas las anotaciones dentro del rango del cursor - + Export annotations for this row within cursor range Exportar todas las anotaciones para esta fila dentro del rango del cursor - + %1: %2 %1\n%2 - + <b>%1</b> (%2) %3 <b>%1</b> (%2) %3 - + Export annotations Exportar anotaciones - + Text Files (*.txt);;All Files (*) - Archivos de texto (*.txt *.log);;Todos los archivos (*) + Archivos de texto (*.txt);;Todos los archivos (*) - + Error Error - + File %1 could not be written to. No se pudo escribir en el archivo%1. - + Show this row - Muestra esta fila + Mostrar esta fila - + Show All - Muestra todo + Mostrar todo - + Hide All - Oculta todo + Ocultar todo pv::views::trace::Flag - + Text Texto - + Delete Eliminar - + Disable snapping - Deshabilita snapping + Deshabilitar snapping @@ -1420,57 +1502,591 @@ Please keep in mind that PulseView may need a restart to display correctly. pv::views::trace::LogicSignal - + No trigger Sin trigger - + Trigger on rising edge Trigger en flanco de subida - + Trigger on high level Trigger en nivel alto - + Trigger on falling edge Trigger en flanco de bajada - + Trigger on low level Trigger en nivel bajo - + Trigger on rising or falling edge Trigger en flanco de subida o bajada - + pixels pixeles - + Trace height Altura del trazo - + Trigger Trigger + + pv::views::trace::MathEditDialog + + + Math Expression Editor + Editor de expresiones matemáticas + + + + Inputs: + Entradas: + + + + Variables: + Variables: + + + + Basic operators: + Operadores básicos: + + + + Assignments: + Asignaciones: + + + + General purpose functions: + Funciones de propósito general: + + + + abs(x) Absolute value of x + abs(x) Valor absoluto de x + + + + avg(x, y, ...) Average of all input values + avg(x, y, ...) Promedio de todos los valores de entrada + + + + ceil(x) Smallest integer that is greater than or equal to x + ceil(x) Entero más pequeño que es mayor o igual a x + + + + clamp(lb, x, ub) Clamp x in range between lb and ub, where lb < ub + clamp(lb, x, ub) Fija x en el rango entre lb y ub, donde lb < ub + + + + equal(x, y) Equality test between x and y using normalised epsilon + equal(x, y) Prueba de igualdad entre x e y usando epsilon normalizado + + + + erf(x) Error function of x + erf(x) Función error de x + + + + erfc(x) Complimentary error function of x + erfc(x) Función de error complementario de x + + + + exp(x) e to the power of x + exp(x) e a la potencia de x + + + + expm1(x) e to the power of x minus 1, where x is very small. + expm1(x) e a la potencia de x menos 1, donde z es muy pequeño. + + + + floor(x) Largest integer that is less than or equal to x + floor(x) Entero más grande que is menor o igual a x + + + + frac(x) Fractional portion of x + frac(x) Porción fraccional de x + + + + hypot(x) Hypotenuse of x and y (i.e. sqrt(x*x + y*y)) + hypot(x) Hipotenusa de x e y (es decir sqrt(x*x + y*y)) + + + + iclamp(lb, x, ub) Inverse-clamp x outside of the range lb and ub, where lb < ub. + If x is within the range it will snap to the closest bound + iclamp(lb, x, ub) Fijación inversa de x fuera del rango lb y ub, donde lb < ub. + Si x está en el rango se fijará al límite más cercano + + + + inrange(lb, x, ub) In-range returns true when x is within the range lb and ub, where lb < ub. + inrange(lb, x, ub) En-rango regresa verdadero cuando x está en el rango lb y ub, donde lb < ub. + + + + log(x) Natural logarithm of x + log(x) Logaritmo natural de x + + + + log10(x) Base 10 logarithm of x + log10(x) Logaritmo base 10 de x + + + + log1p(x) Natural logarithm of 1 + x, where x is very small + log1p(x) Logaritmo natural de 1 + x, donde x es muy pequeño + + + + log2(x) Base 2 logarithm of x + log2(x) Logaritmo base 2 de x + + + + logn(x) Base N logarithm of x, where n is a positive integer + logn(x) Logaritmo base N de x, donde n es un entero positivo + + + + max(x, y, ...) Largest value of all the inputs + max(x, y, ...) Valor más grande de todas las entradas + + + + min(x, y, ...) Smallest value of all the inputs + min(x, y, ...) Valor más pequeño de todas las entradas + + + + mul(x, y, ...) Product of all the inputs + mul(x, y, ...) Producto de todas las entradas + + + + ncdf(x) Normal cumulative distribution function + ncdf(x) Función de distribución acumulativa normal + + + + nequal(x, y) Not-equal test between x and y using normalised epsilon + nequal(x, y) Prueba de no igualdad entre x e y usando epsilon normalizado + + + + pow(x, y) x to the power of y + pow(x, y) x a la potencia de y + + + + root(x, n) Nth-Root of x, where n is a positive integer + root(x, n) Enésima raíz de x, donde n es un entero positivo + + + + round(x) Round x to the nearest integer + round(x) Redondear x al entero más cercano + + + + roundn(x, n) Round x to n decimal places, where n > 0 and is an integer + roundn(x, n) Redondear x a n lugares decimales, donde n > 0 y es un entero + + + + sgn(x) Sign of x; -1 if x < 0, +1 if x > 0, else zero + sgn(x) Sigon de x; -1 si x < 0, +1 si x > 0, otro cero + + + + sqrt(x) Square root of x, where x >= 0 + sqrt(x) Raíz cuadrada de x, donde x >= 0 + + + + sum(x, y, ..,) Sum of all the inputs + sum(x, y, ..,) Suma de todas las entradas + + + + swap(x, y) Swap the values of the variables x and y and return the current value of y + swap(x, y) Intercambia los valores de las variables x e y y regresa el valor actual de y + + + + trunc(x) Integer portion of x + trunc(x) Porción entera de x + + + + Trigonometry functions: + Funciones trigonométricas: + + + + acos(x) Arc cosine of x expressed in radians. Interval [-1,+1] + acos(x) Arco coseno de x expresado en radianes. Intervalo [-1,+1] + + + + acosh(x) Inverse hyperbolic cosine of x expressed in radians + acosh(x) Coseno hiperbólico inverso de x expresado en radianes + + + + asin(x) Arc sine of x expressed in radians. Interval [-1,+1] + asin(x) Arco seno de x expresado en radianes. Intervalo [-1,+1] + + + + asinh(x) Inverse hyperbolic sine of x expressed in radians + asinh(x) Seno hiperbólico inverso de x expresado en radianes + + + + atan(x) Arc tangent of x expressed in radians. Interval [-1,+1] + atan(x) Arco tangente de x expresado en radianes. Intervalo [-1,+1] + + + + atan2(x, y) Arc tangent of (x / y) expressed in radians. [-pi,+pi] + atan2(x, y) Arco tangente de (x / y) expresado en radianes. [-pi,+pi] + + + + atanh(x) Inverse hyperbolic tangent of x expressed in radians + atanh(x) Tangente hiperbólica inversa de x expresada en radianes + + + + cos(x) Cosine of x + cos(x) Coseno de x + + + + cosh(x) Hyperbolic cosine of x + cosh(x) Coseno hiperbólico de x + + + + cot(x) Cotangent of x + cot(x) Cotangente de x + + + + csc(x) Cosectant of x + csc(x) Cosecante de x + + + + sec(x) Secant of x + sec(x) Secante de x + + + + sin(x) Sine of x + sin(x) Seno de x + + + + sinc(x) Sine cardinal of x + sinc(x) Seno cardinal de x + + + + sinh(x) Hyperbolic sine of x + sinh(x) Seno hiperbólico de x + + + + tan(x) Tangent of x + tan(x) Tangente de x + + + + tanh(x) Hyperbolic tangent of x + tanh(x) Tangente hiperbólica de x + + + + deg2rad(x) Convert x from degrees to radians + deg2rad(x) Convierte x de grados sexagesimales a radianes + + + + deg2grad(x) Convert x from degrees to gradians + deg2grad(x) Convierte x de grados sexagesimales a grados centesimales + + + + rad2deg(x) Convert x from radians to degrees + rad2deg(x) Convierte x de radianes a grados sexagesimales + + + + grad2deg(x) Convert x from gradians to degrees + grad2deg(x) Convierte x de grados centesimales a grados sexagesimales + + + + Logic operators: + Operadores lógicos: + + + + Comparisons: + Comparaciones: + + + + x = y or x == y True only if x is strictly equal to y + x = y o x == y Verdadero solo si x es estrictemente igual a y + + + + x <> y or x != y True only if x does not equal y + x <> y o x != y Verdadero solo si x no es igual a y + + + + x < y True only if x is less than y + x < y Verdadero solo si x es menor que y + + + + x <= y True only if x is less than or equal to y + x <= y Verdadero solo si x es menor o igual a y + + + + x > y True only if x is greater than y + x > y Verdadero solo si x es mayor que y + + + + x >= y True only if x is greater than or equal to y + x >= y Verdadero solo si x es mayor o igual a y + + + + Flow control: + Fujo de cotrol: + + + + { ... } Beginning and end of instruction block + { ... } Inicio y fin de un bloque de instrucciones + + + + if (x, y, z) If x is true then return y else return z +if (x) y; variant without implied else +if (x) { y }; variant with an instruction block +if (x) y; else z; variant with explicit else +if (x) { y } else { z }; variant with instruction blocks + if (x, y, z) Si x es verdadero entonces regresa y si no regresa z +if (x) y; variante sin si no implicado +if (x) { y }; variante con un bloque de instrucción +if (x) y; else z; variante con si no explícito +if (x) { y } else { z }; variante con bloques de instrucciones + + + + x ? y : z Ternary operator, equivalent to 'if (x, y, z)' + x ? y : z Operador ternario, equivalente a 'if (x, y, z)' + + + + switch { The first true case condition that is encountered will + case x > 1: a; determine the result of the switch. If none of the case + case x < 1: b; conditions hold true, the default action is used + default: c; to determine the return value +} + switch { La primera condición de caso verdadera que es encontrada + case x > 1: a; determina el resultado del interruptor. Si ninguno de las condiciones de + case x < 1: b; los casos se mantienen verdaderas, la acción predeterminada se usa + default: c; para determinar el valor de retorno +} + + + + while (conditon) { Evaluates expression repeatedly as long as condition is true, + expression; returning the last value of expression +} + while (conditon) { Evalúa la expresión repetidamente siempre que la condición sea verdadera, +expresión; devuelve el último valor de la expresión +} + + + + repeat Evalues expression repeatedly as long as condition is false, + expression; returning the last value of expression +until (condition) + + repeat Evalúa la expresión repetidamente siempre que la condición sea falsa +expresión; devuelve el último valor de la expresión +hasta que (condición) + + + + + for (var x := 0; condition; x += 1) { Repeatedly evaluates expression while the condition is true, + expression while evaluating the 'increment' expression on each loop +} + for (var x := 0; condición; x += 1) { Evalua repetidamente la expresión mientras la condición sea verdadera, + expresión mientras se evalúa la expresión de 'incremento' en cada bucle +} + + + + break Terminates the execution of the nearest enclosed loop, returning NaN + break Finaliza la ejecución del bucle cerrado más cercano, devolviendo NaN + + + + break[x] Terminates the execution of the nearest enclosed loop, returning x + break[x] Finaliza la ejecución del bucle cerrado más cercano, devolviendo x + + + + continue Interrupts loop execution and resumes with the next loop iteration + continue Interrumpe la ejecución del bucle y se reanuda con la siguiente iteración de bucle + + + + return[x] Returns immediately from within the current expression, returning x + return[x] Devuelve inmediatamente desde la expresión actual, regresando x + + + + ~(expr; expr; ...) Evaluates each sub-expression and returns the value of the last one +~{expr; expr; ...} + ~(expr; expr; ...) Evalúa cada subexpresión y devuelve el valor de la última +~{expr; expr; ...} + + + + Copy to expression + Copiar a expresión + + + + Basics + Básicas + + + + Functions 1 + Funciones 1 + + + + Functions 2 + Funciones 2 + + + + Trigonometry + Trigonometría + + + + Logic + Lógica + + + + Flow Control 1 + Flujo de control 1 + + + + Flow Control 2 + Flujo de control 2 + + + + Examples + Ejemplos + + + + pv::views::trace::MathSignal + + + Expression + Espresión + + + + + same as session + igual que la sesión + + + + + 100 + 100 + + + + + 10000 + 10000 + + + + + 1000000 + 1000000 + + + + Number of Samples + Número de muestras + + + + Sample rate + Tasa de muestreo + + pv::views::trace::Ruler Create marker here - Crear marcador aqui + Crear marcador aquí @@ -1485,12 +2101,12 @@ Please keep in mind that PulseView may need a restart to display correctly. Disable mouse hover marker - Deshabilitar marcador de desplazamiento del mouse + Deshabilitar marcador de desplazamiento del ratón Enable mouse hover marker - Habilitar marcador de desplazamiento del mouse + Habilitar marcador de desplazamiento del ratón @@ -1501,7 +2117,12 @@ Please keep in mind that PulseView may need a restart to display correctly.Nombre - + + Remove + Eliminar + + + Disable Deshabilitar @@ -1541,13 +2162,13 @@ Please keep in mind that PulseView may need a restart to display correctly. Display a single segment - Mostrar solo un segmento + Mostrar un solo segmento pv::views::trace::TimeMarker - + Time Tiempo @@ -1555,17 +2176,17 @@ Please keep in mind that PulseView may need a restart to display correctly. pv::views::trace::Trace - + Create marker here - Crear marcador aqui + Crear marcador aquí - + Color Color - + Name Nombre @@ -1578,12 +2199,20 @@ Please keep in mind that PulseView may need a restart to display correctly.Desagrupar + + pv::views::trace::View + + + Create marker here + Crear marcador aquí + + pv::widgets::DecoderGroupBox Show/hide this decoder trace - Mostrar / ocultar este trazo de decodificador + Mostrar/ocultar este trazo de decodificador @@ -1594,8 +2223,8 @@ Please keep in mind that PulseView may need a restart to display correctly. pv::widgets::DeviceToolButton - - + + <No Device> <Sin dispositivo> @@ -1605,7 +2234,7 @@ Please keep in mind that PulseView may need a restart to display correctly. Export %1... - Exporta %1... + Exportar %1... @@ -1613,7 +2242,7 @@ Please keep in mind that PulseView may need a restart to display correctly. Import %1... - Importa %1... + Importar %1... diff --git a/l10n/ja_jp.ts b/l10n/ja_jp.ts new file mode 100644 index 00000000..164ea30f --- /dev/null +++ b/l10n/ja_jp.ts @@ -0,0 +1,2201 @@ + + + + + Application + + + Some parts of the application may still use the previous language. Re-opening the affected windows or restarting the application will remedy this. + アプリケーションの一部では、以前の言語が引き続き使用される場合があります。 影響を受けたウィンドウを再度開くか、アプリケーションを再起動すると、これが改善されます。 + + + + QApplication + + + Error when scanning device driver '%1': %2 + デバイスドライバ'%1'をスキャンするときにエラーが発生しました:%2 + + + + Querying config key %1 is not allowed + + + + + Querying config key %1 resulted in %2 + + + + + Unknown type supplied when attempting to query %1 + + + + + QHexView + + + No data available + データなし + + + + QObject + + + Stack trace of previous crash: + + + + + Don't show this message again + このメッセージを二度と表示しない + + + + When %1 last crashed, it created a stack trace. +A human-readable form has been saved to disk and was written to the log. You may access it from the settings dialog. + %1が最後にクラッシュしたとき、スタックトレースが作成されました。 +人間が読める形式がディスクに保存され、ログに書き込まれました。 設定ダイアログからアクセスできます。 + + + + Cancel + キャンセル + + + + Scanning for devices that driver %1 can access... + ドライバー %1 がアクセスできるデバイスをスキャンしています... + + + + pv::MainWindow + + + PulseView + + + + + Decoder Selector + デコーダー選択 + + + + Session %1 + セッション %1 + + + + Create New Session + 新規セッションを作成 + + + + Start/Stop Acquisition + 取得の開始/停止 + + + + Settings + 設定 + + + + Reload + 再読込 + + + + + Run + 実行 + + + + Stop + 停止 + + + + + + Confirmation + 確認 + + + + There is unsaved data. Close anyway? + 保存されていないデータがあります。 閉じますか? + + + + + This session contains unsaved data. Close it anyway? + このセッションには、保存されていないデータが含まれています。 閉じますか? + + + + pv::Session + + + Can't restore generated signal of unknown type %1 (%2) + 不明なタイプ%1 (%2)の生成された信号を復元できません + + + + Failed to select device + デバイスの選択に失敗しました + + + + Failed to open device + デバイスを開くことができませんでした + + + + Error + エラー + + + + Unexpected input format: %1 + 予期しない入力形式:%1% + + + + Failed to load %1 + %1 のロードに失敗しました + + + + No active device set, can't start acquisition. + アクティブなデバイスが設定されていないため、取得を開始できません。 + + + + No channels enabled. + チャネルが有効になっていません。 + + + + Out of memory, acquisition stopped. + メモリが不足しているため、取得が停止しました。 + + + + Can't handle more than 64 logic channels. + 64を超えるロジックチャネルを処理することはできません。 + + + + pv::StoreSession + + + Can't save logic channel without data. + データなしでロジックチャネルを保存することはできません。 + + + + Can't save analog channel without data. + データなしでアナログチャンネルを保存することはできません。 + + + + No channels enabled. + チャネルが有効になっていません。 + + + + Can't save range without sample data. + サンプルデータなしでは範囲を保存できません。 + + + + + + Error while saving: + 保存中のエラー: + + + + pv::binding::Device + + + Note for device developers: Ignoring device configuration capability '%1' as it is missing GET and/or SET + デバイス開発者への注意:GETやSETがないため、デバイス構成機能'%1'を無視します + + + + No Limit + + + + + pv::data::DecodeSignal + + + No decoders + デコーダーなし + + + + There are no channels assigned to this decoder + このデコーダーに割り当てられたチャネルはありません + + + + One or more required channels have not been specified + 1つ以上の必要なチャネルが指定されていません + + + + No input data + 入力データなし + + + + Decoder reported an error + デコーダーがエラーを報告しました + + + + Failed to create decoder instance + デコーダーインスタンスの作成に失敗しました + + + + pv::data::MathSignal + + + Math%1 + + + + + No expression defined, nothing to do + 式は定義されていません、何もしません + + + + %1 at line %2, column %3: %4 + %1 行 %2, 列 %3: %4 + + + + + "%1" isn't a valid analog signal + "%1" は有効なアナログ信号ではありません + + + + + No data will be generated as %1 must be enabled + %1を有効にする必要があるため、データは生成されません + + + + pv::data::SignalBase + + + Signal average + + + + + 0.9V (for 1.8V CMOS) + + + + + 1.8V (for 3.3V CMOS) + + + + + 2.5V (for 5.0V CMOS) + + + + + 1.5V (for TTL) + + + + + Signal average +/- 15% + + + + + 0.3V/1.2V (for 1.8V CMOS) + + + + + 0.7V/2.5V (for 3.3V CMOS) + + + + + 1.3V/3.7V (for 5.0V CMOS) + + + + + 0.8V/2.0V (for TTL) + + + + + pv::dialogs::Connect + + + &Scan for devices using driver above + 上記のドライバーを使用してデバイスをスキャンする + + + + Connect to Device + デバイスに接続 + + + + Step 1: Choose the driver + ステップ1:ドライバーを選択 + + + + &USB + + + + + Serial &Port + + + + + &TCP/IP + + + + + Protocol: + + + + + Step 2: Choose the interface + ステップ2:インターフェースを選択 + + + + Step 3: Scan for devices + ステップ3:デバイスをスキャン + + + + Step 4: Select the device + ステップ4:デバイスを選択 + + + + pv::dialogs::Settings + + + + General + 全般 + + + + Views + 表示 + + + + + Decoders + デコーダー + + + + About + + + + + Logging + ロギング + + + + User interface language + 表示言語 + + + + User interface theme + 表示のテーマ + + + + (You may need to restart PulseView for all UI elements to update) + (すべてのUI要素を更新するには、PulseViewを再起動する必要がある場合があります) + + + + System Default + システムのデフォルト + + + + Qt widget style + Qt widget スタイル + + + + (Dark themes look best with the Fusion style) + (ダークテーマはFusionスタイルで最もよく見えます) + + + + Save session &setup along with .sr file + セッション設定を.srファイルと一緒に保存します + + + + Start acquisition for all open sessions when clicking 'Run' + [実行]をクリックすると、開いているすべてのセッションの取得を開始します + + + + Trace View + トレースビュー + + + + Use colored trace &background + 色付きのトレースと背景を使用する(&b) + + + + Constantly perform &zoom-to-fit during acquisition + 取得中は常にズームツーフィットを実行します(&z) + + + + Perform a zoom-to-&fit when acquisition stops + 取得が停止したときにズームツーフィットする(&f) + + + + Show time zero at the &trigger + トリガーで時間ゼロを表示する(&t) + + + + Always keep &newest samples at the right edge during capture + キャプチャ中は常に最新のサンプルを右端に保持(&n) + + + + Allow &vertical dragging in the view area + ビューエリアでの垂直方向のドラッグを許可する(&v) + + + + Show data &sampling points + データサンプリングポイントを表示する(&s) + + + + Fill &high areas of logic signals + ロジック信号の高い領域を埋める(&h) + + + + Color to fill high areas of logic signals with + 論理信号の高い領域を塗りつぶす色 + + + + Show analog minor grid in addition to div grid + divグリッドに加えてアナログマイナーグリッドを表示する + + + + Highlight mouse cursor using a vertical marker line + 垂直マーカーラインを使用してマウスカーソルを強調表示します + + + + + + pixels + + + + + Maximum distance from edges before markers snap to them + マーカーがエッジにスナップする前のエッジからの最大距離 + + + + Color to fill cursor area with + カーソル領域を塗りつぶす色 + + + + None + + + + + Background + + + + + Dots + + + + + Conversion threshold display mode (analog traces only) + 変換閾値表示モード(アナログトレースのみ) + + + + Default analog trace div height + デフォルトのアナログトレースdivの高さ + + + + Default logic trace height + デフォルトのロジックトレースの高さ + + + + Allow configuration of &initial signal state + 初期信号状態の構成を許可する(&i) + + + + Always show all &rows, even if no annotation is visible + 注釈が表示されていない場合でも、常にすべての行を表示します(&r) + + + + Annotation export format + 注釈のエクスポート形式 + + + + %s = sample range; %d: decoder name; %r: row name; %c: class name + %s = サンプル範囲; %d: デコーダー名; %r: 行名; %c: クラス名 + + + + %1: longest annotation text; %a: all annotation texts; %q: use quotation marks + %1: 最長の注釈テキスト; %a: すべての注釈テキスト; %q: 引用符を使用 + + + + %1<br /><a href="http://%2">%2</a> + + + + + GNU GPL, version 3 or later + + + + + Versions, libraries and features: + + + + + Firmware search paths: + + + + + Protocol decoder search paths: + プロトコルデコーダの検索パス: + + + + <tr><td colspan="2">(Note: Set environment variable SIGROKDECODE_DIR to add a custom directory)</td></tr> + + + + + Supported hardware drivers: + + + + + Supported input formats: + + + + + Supported output formats: + + + + + Supported protocol decoders: + + + + + Available Translations: + + + + + Log level: + ログレベル: + + + + lines + 行数 + + + + Length of background buffer: + バックグラウンドバッファの長さ: + + + + &Save to File + ファイルに保存(&S) + + + + &Pop out + + + + + You selected a dark theme. +Should I set the user-adjustable colors to better suit your choice? + +Please keep in mind that PulseView may need a restart to display correctly. + ダークテーマを選択しました。 +選択に合わせてユーザー調整可能な色を設定する必要があります + +正しく表示するには、PulseViewを再起動する必要がある場合があることに注意してください。 + + + + You selected a bright theme. +Should I set the user-adjustable colors to better suit your choice? + +Please keep in mind that PulseView may need a restart to display correctly. + 明るいテーマを選択しました。 +選択に合わせてユーザー調整可能な色を設定する必要があります + +正しく表示するには、PulseViewを再起動する必要がある場合があることに注意してください。 + + + + Save Log + ログ保存 + + + + Log Files (*.txt *.log);;All Files (*) + + + + + Success + 成功 + + + + Log saved to %1. + ログは %1 に保存されました。 + + + + Error + エラー + + + + File %1 could not be written to. + ファイル %1 に書き込めませんでした。 + + + + %1 Log + %1 ログ + + + + pv::dialogs::StoreProgress + + + Saving... + 保存中... + + + + Cancel + キャンセル + + + + Failed to save session. + セッションの保存に失敗しました。 + + + + pv::popups::Channels + + + + + + All + + + + + + Logic + + + + + + Analog + + + + + Named + + + + + Unnamed + + + + + Changing + + + + + Non-changing + + + + + Disable: + + + + + Enable: + + + + + + None + + + + + pv::prop::Bool + + + + Querying config key %1 resulted in %2 + + + + + pv::prop::Double + + + + Querying config key %1 resulted in %2 + + + + + pv::prop::Enum + + + + Querying config key %1 resulted in %2 + + + + + pv::prop::Int + + + + Querying config key %1 resulted in %2 + + + + + pv::prop::String + + + + Querying config key %1 resulted in %2 + + + + + pv::subwindows::decoder_selector::DecoderCollectionModel + + + Decoder + デコーダー + + + + Name + 名前 + + + + ID + + + + + All Decoders + + + + + pv::subwindows::decoder_selector::SubWindow + + + Select a decoder to see its description here. + ここに説明を表示するには、デコーダーを選択してください。 + + + + , %1 + + + + + <p align='right'>Tags: %1</p> + + + + + Protocol decoder <b>%1</b> requires input type <b>%2</b> which several decoders provide.<br>Choose which one to use:<br> + + + + + Choose Decoder + デコーダーを選択 + + + + pv::toolbars::MainBar + + + New &View + 新しいビュー(&V) + + + + &Open... + 開く(&O)... + + + + Restore Session Setu&p... + セッション設定を復元(&p)... + + + + &Save... + 保存(&S)... + + + + Save &As... + 名前をつけて保存(&A)... + + + + Save Selected &Range As... + 選択した範囲を名前を付けて保存(&R)... + + + + Save Session Setu&p... + セッション設定を保存(&p)... + + + + &Export + エクスポート(&E) + + + + &Import + インポート(&I) + + + + &Connect to Device... + デバイスへ接続(&C)... + + + + Add protocol decoder + プロトコルデコーダーを追加 + + + + Add math signal + math信号を追加 + + + + Configure Device + デバイスの構成 + + + + Configure Channels + チャンネルの構成 + + + + Failed to get sample rate list: + + + + + Failed to get sample rate: + + + + + Failed to get sample limit list: + + + + + Failed to configure samplerate: + + + + + Failed to configure sample count: + + + + + Missing Cursors + カーソルがありません + + + + You need to set the cursors before you can save the data enclosed by them to a session file (e.g. using the Show Cursors button). + カーソルで囲まれたデータをセッションファイルに保存する前に、カーソルを設定する必要があります(たとえば、[カーソルの表示]ボタンを使用)。 + + + + Invalid Range + 範囲が無効です + + + + The cursors don't define a valid range of samples. + カーソルはサンプルの有効な範囲を定義していません。 + + + + %1 files + + + + + + All Files + すべてのファイル + + + + + Save File + ファイル保存 + + + + Export %1 + エクスポート %1 + + + + %1 files + + + + + Import File + インポートファイル + + + + Import %1 + インポート %1 + + + + + Open File + ファイルを開く + + + + sigrok Sessions (*.sr);;All Files (*) + + + + + + PulseView Session Setups (*.pvs);;All Files (*) + + + + + Total sampling time: %1 + 総サンプリング時間: %1 + + + + pv::views::decoder_binary::View + + + Decoder: + デコーダー: + + + + Show data as + データ表示形式 + + + + Hexdump + 16進ダンプ + + + + &Save... + 保存(&S) + + + + + Save Binary Data + バイナリデータを保存 + + + + Binary Data Files (*.bin);;All Files (*) + + + + + + Error + エラー + + + + + File %1 could not be written to. + ファイル%1に書き込めませんでした。 + + + + Hex Dumps (*.txt);;All Files (*) + + + + + pv::views::tabular_decoder::AnnotationCollectionModel + + + Sample + サンプル + + + + Time + 時間 + + + + Decoder + デコーダー + + + + Ann Row + + + + + Ann Class + + + + + Value + 値 + + + + s + + + + + sa + + + + + pv::views::tabular_decoder::View + + + Decoder: + デコーダー: + + + + Hide Hidden Rows/Classes + + + + + &Save... + 保存(&S) + + + + Save Annotations as CSV + 注釈をCSVとして保存 + + + + CSV Files (*.csv);;Text Files (*.txt);;All Files (*) + + + + + Error + エラー + + + + File %1 could not be written to. + ファイル%1に書き込めませんでした。 + + + + pv::views::trace::AnalogSignal + + + Number of pos vertical divs + 正の垂直divの数 + + + + Number of neg vertical divs + 負の垂直divの数 + + + + pixels + + + + + Div height + Divの高さ + + + + V/div + + + + + Vertical resolution + 垂直解像度 + + + + Autoranging + オートレンジ + + + + none + なし + + + + to logic via threshold + 閾値でロジック変換 + + + + to logic via schmitt-trigger + シュミットトリガーでロジック変換 + + + + Conversion + 変換 + + + + Conversion threshold(s) + 変換閾値 + + + + analog + アナログ + + + + converted + 変換済 + + + + analog+converted + アナログ+変換済 + + + + Show traces for + トレースを表示 + + + + pv::views::trace::Cursor + + + Disable snapping + スナップを無効にする + + + + pv::views::trace::CursorPair + + + Display interval + 間隔表示 + + + + Display frequency + 周波数表示 + + + + Display samples + サンプル数表示 + + + + pv::views::trace::DecodeTrace + + + <p><i>No decoders in the stack</i></p> + + + + + <i>* Required channels</i> + + + + + Stack Decoder + + + + + Stack a higher-level decoder on top of this one + この上に高レベルのデコーダーをスタック + + + + Delete + 削除 + + + + Resume decoding + デコードを再開 + + + + Pause decoding + デコードを一時中断 + + + + Copy annotation text to clipboard + 注釈テキストをクリップボードにコピー + + + + Export all annotations + すべての注釈をエクスポート + + + + Export all annotations for this row + この行のすべての注釈をエクスポート + + + + Export all annotations, starting here + ここから始めて、すべての注釈をエクスポート + + + + Export annotations for this row, starting here + ここから始めて、この行の注釈をエクスポート + + + + Export all annotations within cursor range + カーソル範囲内のすべての注釈をエクスポート + + + + Export annotations for this row within cursor range + カーソル範囲内のこの行の注釈をエクスポート + + + + %1: +%2 + + + + + <b>%1</b> (%2) %3 + + + + + Export annotations + 注釈をエクスポート + + + + Text Files (*.txt);;All Files (*) + + + + + Error + エラー + + + + File %1 could not be written to. + ファイル%1に書き込めませんでした。 + + + + Show this row + この行を表示 + + + + Show All + すべて表示 + + + + Hide All + すべて非表示 + + + + pv::views::trace::Flag + + + Text + テキスト + + + + Delete + 削除 + + + + Disable snapping + スナップを無効 + + + + pv::views::trace::Header + + + Group + グループ + + + + pv::views::trace::LogicSignal + + + No trigger + + + + + Trigger on rising edge + + + + + Trigger on high level + + + + + Trigger on falling edge + + + + + Trigger on low level + + + + + Trigger on rising or falling edge + + + + + pixels + + + + + Trace height + トレースの高さ + + + + Trigger + トリガー + + + + pv::views::trace::MathEditDialog + + + Math Expression Editor + 数式エディタ + + + + Inputs: + 入力: + + + + Variables: + 変数: + + + + Basic operators: + 基本的な演算子: + + + + Assignments: + 割り当て: + + + + General purpose functions: + 汎用機能: + + + + abs(x) Absolute value of x + + + + + avg(x, y, ...) Average of all input values + + + + + ceil(x) Smallest integer that is greater than or equal to x + + + + + clamp(lb, x, ub) Clamp x in range between lb and ub, where lb < ub + + + + + equal(x, y) Equality test between x and y using normalised epsilon + + + + + erf(x) Error function of x + + + + + erfc(x) Complimentary error function of x + + + + + exp(x) e to the power of x + + + + + expm1(x) e to the power of x minus 1, where x is very small. + + + + + floor(x) Largest integer that is less than or equal to x + + + + + frac(x) Fractional portion of x + + + + + hypot(x) Hypotenuse of x and y (i.e. sqrt(x*x + y*y)) + + + + + iclamp(lb, x, ub) Inverse-clamp x outside of the range lb and ub, where lb < ub. + If x is within the range it will snap to the closest bound + + + + + inrange(lb, x, ub) In-range returns true when x is within the range lb and ub, where lb < ub. + + + + + log(x) Natural logarithm of x + + + + + log10(x) Base 10 logarithm of x + + + + + log1p(x) Natural logarithm of 1 + x, where x is very small + + + + + log2(x) Base 2 logarithm of x + + + + + logn(x) Base N logarithm of x, where n is a positive integer + + + + + max(x, y, ...) Largest value of all the inputs + + + + + min(x, y, ...) Smallest value of all the inputs + + + + + mul(x, y, ...) Product of all the inputs + + + + + ncdf(x) Normal cumulative distribution function + + + + + nequal(x, y) Not-equal test between x and y using normalised epsilon + + + + + pow(x, y) x to the power of y + + + + + root(x, n) Nth-Root of x, where n is a positive integer + + + + + round(x) Round x to the nearest integer + + + + + roundn(x, n) Round x to n decimal places, where n > 0 and is an integer + + + + + sgn(x) Sign of x; -1 if x < 0, +1 if x > 0, else zero + + + + + sqrt(x) Square root of x, where x >= 0 + + + + + sum(x, y, ..,) Sum of all the inputs + + + + + swap(x, y) Swap the values of the variables x and y and return the current value of y + + + + + trunc(x) Integer portion of x + + + + + Trigonometry functions: + 三角関数: + + + + acos(x) Arc cosine of x expressed in radians. Interval [-1,+1] + + + + + acosh(x) Inverse hyperbolic cosine of x expressed in radians + + + + + asin(x) Arc sine of x expressed in radians. Interval [-1,+1] + + + + + asinh(x) Inverse hyperbolic sine of x expressed in radians + + + + + atan(x) Arc tangent of x expressed in radians. Interval [-1,+1] + + + + + atan2(x, y) Arc tangent of (x / y) expressed in radians. [-pi,+pi] + + + + + atanh(x) Inverse hyperbolic tangent of x expressed in radians + + + + + cos(x) Cosine of x + + + + + cosh(x) Hyperbolic cosine of x + + + + + cot(x) Cotangent of x + + + + + csc(x) Cosectant of x + + + + + sec(x) Secant of x + + + + + sin(x) Sine of x + + + + + sinc(x) Sine cardinal of x + + + + + sinh(x) Hyperbolic sine of x + + + + + tan(x) Tangent of x + + + + + tanh(x) Hyperbolic tangent of x + + + + + deg2rad(x) Convert x from degrees to radians + + + + + deg2grad(x) Convert x from degrees to gradians + + + + + rad2deg(x) Convert x from radians to degrees + + + + + grad2deg(x) Convert x from gradians to degrees + + + + + Logic operators: + 論理演算子: + + + + Comparisons: + 比較: + + + + x = y or x == y True only if x is strictly equal to y + + + + + x <> y or x != y True only if x does not equal y + + + + + x < y True only if x is less than y + + + + + x <= y True only if x is less than or equal to y + + + + + x > y True only if x is greater than y + + + + + x >= y True only if x is greater than or equal to y + + + + + Flow control: + フロー制御: + + + + { ... } Beginning and end of instruction block + + + + + if (x, y, z) If x is true then return y else return z +if (x) y; variant without implied else +if (x) { y }; variant with an instruction block +if (x) y; else z; variant with explicit else +if (x) { y } else { z }; variant with instruction blocks + + + + + x ? y : z Ternary operator, equivalent to 'if (x, y, z)' + + + + + switch { The first true case condition that is encountered will + case x > 1: a; determine the result of the switch. If none of the case + case x < 1: b; conditions hold true, the default action is used + default: c; to determine the return value +} + + + + + while (conditon) { Evaluates expression repeatedly as long as condition is true, + expression; returning the last value of expression +} + + + + + repeat Evalues expression repeatedly as long as condition is false, + expression; returning the last value of expression +until (condition) + + + + + + for (var x := 0; condition; x += 1) { Repeatedly evaluates expression while the condition is true, + expression while evaluating the 'increment' expression on each loop +} + + + + + break Terminates the execution of the nearest enclosed loop, returning NaN + + + + + break[x] Terminates the execution of the nearest enclosed loop, returning x + + + + + continue Interrupts loop execution and resumes with the next loop iteration + + + + + return[x] Returns immediately from within the current expression, returning x + + + + + ~(expr; expr; ...) Evaluates each sub-expression and returns the value of the last one +~{expr; expr; ...} + + + + + Copy to expression + 式にコピー + + + + Basics + 基本 + + + + Functions 1 + 関数 1 + + + + Functions 2 + 関数 2 + + + + Trigonometry + 三角関数 + + + + Logic + 論理 + + + + Flow Control 1 + フロー制御 1 + + + + Flow Control 2 + フロー制御 2 + + + + Examples + 例 + + + + pv::views::trace::MathSignal + + + Expression + 式 + + + + + same as session + セッションと同じ + + + + + 100 + + + + + + 10000 + + + + + + 1000000 + + + + + Number of Samples + サンプル数 + + + + Sample rate + サンプルレート + + + + pv::views::trace::Ruler + + + Create marker here + ここでマーカーを作成 + + + + Set as zero point + ゼロポイントとして設定 + + + + Reset zero point + ゼロポイントをリセット + + + + Disable mouse hover marker + マウスホバーマーカーを無効 + + + + Enable mouse hover marker + マウスホバーマーカーを有効 + + + + pv::views::trace::Signal + + + Name + 名前 + + + + Remove + 削除 + + + + Disable + 無効 + + + + pv::views::trace::StandardBar + + + Zoom &In + ズームイン(&I) + + + + Zoom &Out + ズームアウト(&O) + + + + Zoom to &Fit + ウインドウに合わせる(&F) + + + + Show &Cursors + カーソル表示(&C) + + + + Display last segment only + 最後のセグメントのみ表示 + + + + Display last complete segment only + 最後の完全なセグメントのみ表示 + + + + Display a single segment + 単一のセグメントを表示 + + + + pv::views::trace::TimeMarker + + + Time + 時間 + + + + pv::views::trace::Trace + + + Create marker here + ここにマーカーを作成 + + + + Color + 色 + + + + Name + 名前 + + + + pv::views::trace::TraceGroup + + + Ungroup + グループ解除 + + + + pv::widgets::DecoderGroupBox + + + Show/hide this decoder trace + このデコーダートレースを表示/非表示 + + + + Delete this decoder trace + このデコーダートレースを削除 + + + + pv::widgets::DeviceToolButton + + + + <No Device> + + + + + pv::widgets::ExportMenu + + + Export %1... + エクスポート %1... + + + + pv::widgets::ImportMenu + + + Import %1... + インポート %1... + + + diff --git a/l10n/zh_cn.ts b/l10n/zh_cn.ts new file mode 100644 index 00000000..937a96cb --- /dev/null +++ b/l10n/zh_cn.ts @@ -0,0 +1,2207 @@ + + + + + Application + + + Some parts of the application may still use the previous language. Re-opening the affected windows or restarting the application will remedy this. + 应用程序的某些部分可能仍然使用以前的语言。重新打开受影响的窗口或重新启动应用程序将解决此问题。 + + + + QApplication + + + Error when scanning device driver '%1': %2 + 扫描设备驱动程序时出错 '%1': %2 + + + + Querying config key %1 is not allowed + 不允许查询 %1 配置 + + + + Querying config key %1 resulted in %2 + 查询配置 '%1': %2 + + + + Unknown type supplied when attempting to query %1 + 查询 %1 时 返回未知类型 + + + + QHexView + + + No data available + 无可用数据 + + + + QObject + + + Stack trace of previous crash: + 跟踪上次崩溃日志: + + + + Don't show this message again + 不再显示此消息 + + + + When %1 last crashed, it created a stack trace. +A human-readable form has been saved to disk and was written to the log. You may access it from the settings dialog. + 上次崩溃时 %1 ,创建了日志文件。 +可在 设置\Logging 中查看。 + + + + Cancel + 取消 + + + + Scanning for devices that driver %1 can access... + 正在扫描驱动程序 %1 可以访问的设备... + + + + pv::MainWindow + + + PulseView + PulseView + + + + Decoder Selector + 协议解码器 + + + + Session %1 + 会话 %1 + + + + Create New Session + 创建新会话 + + + + Start/Stop Acquisition + 开始/停止 采集 + + + + Settings + 设置 + + + + Reload + 重新加载 + + + + + Run + 开始 + + + + Stop + 停止 + + + + + + Confirmation + 确认 + + + + There is unsaved data. Close anyway? + 数据未保存。是否关闭? + + + + + This session contains unsaved data. Close it anyway? + 此会话数据未保存。是否关闭? + + + + pv::Session + + + Can't restore generated signal of unknown type %1 (%2) + 无法还原生成的未知类型的信号 %1 (%2) + + + + Failed to select device + 无法选择的设备 + + + + Failed to open device + 无法打开的设备 + + + + Error + + + + + Unexpected input format: %1 + 不支持的输入格式: %1 + + + + Failed to load %1 + 无法加载 %1 + + + + No active device set, can't start acquisition. + 未设置活动设备,无法采集。 + + + + No channels enabled. + 未启用任何通道。 + + + + Out of memory, acquisition stopped. + 内存不足,采集停止。 + + + + Can't handle more than 64 logic channels. + 无法处理超过64个逻辑通道。 + + + + pv::StoreSession + + + Can't save logic channel without data. + 无法保存,逻辑通道内没有数据。 + + + + Can't save analog channel without data. + 无法保存,模拟通道内没有数据。 + + + + No channels enabled. + 未启用任何通道。 + + + + Can't save range without sample data. + 无法保存,光标范围内没有数据。 + + + + + + Error while saving: + 保存时出错: + + + + pv::binding::Device + + + Note for device developers: Ignoring device configuration capability '%1' as it is missing GET and/or SET + 设备开发人员注意:缺少 GET/SET,忽略该设备配置功能 '%1' + + + + No Limit + 没有限制 + + + + pv::data::DecodeSignal + + + No decoders + 没有解码器 + + + + There are no channels assigned to this decoder + 解码器没有选择通道 + + + + One or more required channels have not been specified + 解码器缺少一个或多个通道 + + + + No input data + 无数据输入 + + + + Decoder reported an error + 解码器解码错误 + + + + Failed to create decoder instance + 无法创建的解码器实例 + + + + pv::data::MathSignal + + + Math%1 + + + + + No expression defined, nothing to do + 未定义表达式,不执行任何操作 + + + + %1 at line %2, column %3: %4 + %1 行 %2, 列 %3: %4 + + + + + "%1" isn't a valid analog signal + "%1" 不是有效的模拟信号 + + + + + No data will be generated as %1 must be enabled + 不会生成数据,因为必须启用 %1 + + + + pv::data::SignalBase + + + Signal average + 平均信号电平 + + + + 0.9V (for 1.8V CMOS) + + + + + 1.8V (for 3.3V CMOS) + + + + + 2.5V (for 5.0V CMOS) + + + + + 1.5V (for TTL) + + + + + Signal average +/- 15% + 平均信号电平 +/- 15% + + + + 0.3V/1.2V (for 1.8V CMOS) + + + + + 0.7V/2.5V (for 3.3V CMOS) + + + + + 1.3V/3.7V (for 5.0V CMOS) + + + + + 0.8V/2.0V (for TTL) + + + + + pv::dialogs::Connect + + + &Scan for devices using driver above + 使用上述驱动程序扫描设备 + + + + Connect to Device + 连接到设备 + + + + Step 1: Choose the driver + 步骤1:选择驱动程序 + + + + &USB + + + + + Serial &Port + 串行和端口 + + + + &TCP/IP + + + + + Protocol: + 协议: + + + + Step 2: Choose the interface + 步骤2:选择接口 + + + + Step 3: Scan for devices + 步骤3:扫描设备 + + + + Step 4: Select the device + 步骤4:选择设备 + + + + pv::dialogs::Settings + + + + General + 常规 + + + + Views + 显示 + + + + + Decoders + 解码器 + + + + About + + + + + Logging + + + + + User interface language + 语言 + + + + User interface theme + 主题 + + + + (You may need to restart PulseView for all UI elements to update) + (您可能需要重新启动PulseView才能更新所有UI元素) + + + + System Default + + + + + Qt widget style + QT 软件界面风格 + + + + (Dark themes look best with the Fusion style) + (深色主题与Fusion风格搭配效果最佳) + + + + Save session &setup along with .sr file + 将会话设置与 .sr文件一起保存 + + + + Start acquisition for all open sessions when clicking 'Run' + 单击“开始”时启动所有打开会话的采集 + + + + Trace View + 采集视图 + + + + Use colored trace &background + 使用彩色通道背景 + + + + Constantly perform &zoom-to-fit during acquisition + 采集数据过程中不断调整和缩放以适应窗口 ( &Z ) + + + + Perform a zoom-to-&fit when acquisition stops + 采集停止时执行调整和缩放以适应窗口 ( &A ) + + + + Show time zero at the &trigger + 在触发器处显示时间零点 ( &T ) + + + + Always keep &newest samples at the right edge during capture + 采集过程中始终跟踪右侧最新数据 ( &Q ) + + + + Allow &vertical dragging in the view area + 允许在视图区域中垂直拖动 + + + + Show data &sampling points + 显示数据采样点 + + + + Fill &high areas of logic signals + 填充逻辑信号高电平的区域 ( &H ) + + + + Color to fill high areas of logic signals with + 填充逻辑信号高电平区域的颜色 + + + + Show analog minor grid in addition to div grid + 模拟通道除了div网格之外,还显示更多垂直细分网格 + + + + Highlight mouse cursor using a vertical marker line + 用竖线突出显示鼠标光标位置 + + + + + + pixels + + + + + Maximum distance from edges before markers snap to them + 光标吸附到边沿前的最大距离 + + + + Color to fill cursor area with + 填充光标范围内的颜色 + + + + None + + + + + Background + + + + + Dots + + + + + Conversion threshold display mode (analog traces only) + 转换阈值显示模式(仅限模拟通道) + + + + Default analog trace div height + 模拟通道垂直高度 + + + + Default logic trace height + 逻辑通道垂直高度 + + + + Allow configuration of &initial signal state + 允许配置初始信号状态 + + + + Always show all &rows, even if no annotation is visible + 始终显示所有解码,即使未解码 + + + + Annotation export format + 解码数据导出格式 + + + + %s = sample range; %d: decoder name; %r: row name; %c: class name + + + + + %1: longest annotation text; %a: all annotation texts; %q: use quotation marks + + + + + %1<br /><a href="http://%2">%2</a> + + + + + GNU GPL, version 3 or later + + + + + Versions, libraries and features: + 版本、库和功能: + + + + Firmware search paths: + 固件搜索路径: + + + + Protocol decoder search paths: + 协议解码器搜索路径: + + + + <tr><td colspan="2">(Note: Set environment variable SIGROKDECODE_DIR to add a custom directory)</td></tr> + + + + + Supported hardware drivers: + 支持的硬件驱动程序: + + + + Supported input formats: + 支持的输入格式: + + + + Supported output formats: + 支持的输出格式: + + + + Supported protocol decoders: + 支持的协议解码器: + + + + Available Translations: + 可用翻译: + + + + Log level: + 日志级别: + + + + lines + 行 + + + + Length of background buffer: + 日志缓存长度: + + + + &Save to File + 保存到文件 + + + + &Pop out + 独立弹出日志窗口 + + + + You selected a dark theme. +Should I set the user-adjustable colors to better suit your choice? + +Please keep in mind that PulseView may need a restart to display correctly. + 您选择了一个深色主题。 +是否相应地调整特定的颜色,以更好地协调? +PulseView可能需要重新启动才能正确显示。 + + + + You selected a bright theme. +Should I set the user-adjustable colors to better suit your choice? + +Please keep in mind that PulseView may need a restart to display correctly. + 您选择了一个明亮主题。 +是否相应地调整特定的颜色,以更好地协调? +PulseView可能需要重新启动才能正确显示。 + + + + Save Log + 保存日志 + + + + Log Files (*.txt *.log);;All Files (*) + + + + + Success + 成功 + + + + Log saved to %1. + 日志已保存到 %1。 + + + + Error + + + + + File %1 could not be written to. + 文件 %1 无法保存。 + + + + %1 Log + + + + + pv::dialogs::StoreProgress + + + Saving... + 保存中... + + + + Cancel + 取消 + + + + Failed to save session. + 未能保存会话。 + + + + pv::popups::Channels + + + + + + All + 全部 + + + + + Logic + 逻辑 + + + + + Analog + 模拟 + + + + Named + 更名过 + + + + Unnamed + 未更名 + + + + Changing + 有数据的 + + + + Non-changing + 无数据的 + + + + Disable: + 禁用: + + + + Enable: + 启用: + + + + + None + 全关 + + + + pv::prop::Bool + + + + Querying config key %1 resulted in %2 + 查询配置 '%1': %2 + + + + pv::prop::Double + + + + Querying config key %1 resulted in %2 + 查询配置 '%1': %2 + + + + pv::prop::Enum + + + + Querying config key %1 resulted in %2 + 查询配置 '%1': %2 + + + + pv::prop::Int + + + + Querying config key %1 resulted in %2 + 查询配置 '%1': %2 + + + + pv::prop::String + + + + Querying config key %1 resulted in %2 + 查询配置 '%1': %2 + + + + pv::subwindows::decoder_selector::DecoderCollectionModel + + + Decoder + 解码器 + + + + Name + + + + + ID + + + + + All Decoders + 所有解码器 + + + + pv::subwindows::decoder_selector::SubWindow + + + Select a decoder to see its description here. + 选择解码器以在此处查看其说明。 + + + + , %1 + + + + + <p align='right'>Tags: %1</p> + + + + + Protocol decoder <b>%1</b> requires input type <b>%2</b> which several decoders provide.<br>Choose which one to use:<br> + 协议解码器 <b>%1</b> 有不同的<b>%2</b> 协议类型。<br>选择要使用的:<br> + + + + Choose Decoder + 选择解码器 + + + + pv::toolbars::MainBar + + + New &View + 新建视图 + + + + &Open... + 打开... ( &O ) + + + + Restore Session Setu&p... + 从文件打开会话设置... + + + + &Save... + 保存... ( &S ) + + + + Save &As... + 另存为... ( &A ) + + + + Save Selected &Range As... + 将所选范围另存为... ( &R ) + + + + Save Session Setu&p... + 保存会话设置... + + + + &Export + 导出 + + + + &Import + 导入 + + + + &Connect to Device... + 连接到设备... + + + + Add protocol decoder + 添加协议解码器 + + + + Add math signal + 添加 math 信号 + + + + Configure Device + 设备配置 + + + + Configure Channels + 通道配置 + + + + Failed to get sample rate list: + 无法获取采样率列表: + + + + Failed to get sample rate: + 无法获取采样率: + + + + Failed to get sample limit list: + 无法获取采样限制列表: + + + + Failed to configure samplerate: + 无法配置采样率: + + + + Failed to configure sample count: + 无法配置采样计数: + + + + Missing Cursors + 缺少光标 + + + + You need to set the cursors before you can save the data enclosed by them to a session file (e.g. using the Show Cursors button). + 您需要设置光标,然后才能将光标范围内的数据保存到会话文件中(例如,使用“显示光标”按钮)。 + + + + Invalid Range + 无效的范围 + + + + The cursors don't define a valid range of samples. + 光标没有定义有效的采样范围。 + + + + %1 files + + + + + + All Files + 所有文件 + + + + + Save File + 保存文件 + + + + Export %1 + 导出 %1 + + + + %1 files + + + + + Import File + 导入文件 + + + + Import %1 + 导入 %1 + + + + + Open File + 打开文件 + + + + sigrok Sessions (*.sr);;All Files (*) + + + + + + PulseView Session Setups (*.pvs);;All Files (*) + + + + + Total sampling time: %1 + 总采样时间: %1 + + + + pv::views::decoder_binary::View + + + Decoder: + 解码器: + + + + Show data as + 数据显示格式 + + + + Hexdump + + + + + &Save... + 保存... ( &S ) + + + + + Save Binary Data + 保存二进制数据 + + + + Binary Data Files (*.bin);;All Files (*) + + + + + + Error + + + + + + File %1 could not be written to. + 文件 %1 无法保存。 + + + + Hex Dumps (*.txt);;All Files (*) + + + + + pv::views::tabular_decoder::AnnotationCollectionModel + + + Sample + 采样 + + + + Time + + + + + Decoder + 解码器 + + + + Ann Row + + + + + Ann Class + + + + + Value + + + + + s + + + + + sa + + + + + pv::views::tabular_decoder::View + + + Decoder: + 解码器: + + + + Hide Hidden Rows/Classes + 隐藏隐藏的行/列 + + + + &Save... + 保存... ( &S ) + + + + Save Annotations as CSV + 将解码数据另存为CSV + + + + CSV Files (*.csv);;Text Files (*.txt);;All Files (*) + + + + + Error + + + + + File %1 could not be written to. + 文件 %1 无法保存。 + + + + pv::views::trace::AnalogSignal + + + Number of pos vertical divs + 正区间div垂直细分网格数 + + + + Number of neg vertical divs + 负区间div垂直细分网格数 + + + + pixels + + + + + Div height + Div高度 + + + + V/div + + + + + Vertical resolution + 垂直分辨率 + + + + Autoranging + 自动量程 + + + + none + 无 + + + + to logic via threshold + 通过阈值转换为逻辑 + + + + to logic via schmitt-trigger + 通过施密特触发器转换为逻辑 + + + + Conversion + 转换 + + + + Conversion threshold(s) + 转换阈值 + + + + analog + 模拟 + + + + converted + 转换 + + + + analog+converted + 模拟+转换 + + + + Show traces for + 显示采集 + + + + pv::views::trace::Cursor + + + Disable snapping + 禁用捕捉 + + + + pv::views::trace::CursorPair + + + Display interval + 显示间隔 + + + + Display frequency + 显示频率 + + + + Display samples + 显示采样 + + + + pv::views::trace::DecodeTrace + + + <p><i>No decoders in the stack</i></p> + <p><i>堆叠中没有解码器</i></p> + + + + <i>* Required channels</i> + <i>* 所需通道</i> + + + + Stack Decoder + 堆叠解码器 + + + + Stack a higher-level decoder on top of this one + 在这之上面堆叠一个更高级别的解码器 + + + + Delete + 删除 + + + + Resume decoding + 继续解码 + + + + Pause decoding + 暂停解码 + + + + Copy annotation text to clipboard + 将解码数据复制到剪贴板 + + + + Export all annotations + 导出所有解码数据 + + + + Export all annotations for this row + 导出此行的解码数据 + + + + Export all annotations, starting here + 导出从这以后所有的解码数据 + + + + Export annotations for this row, starting here + 导出从这以后此行的解码数据 + + + + Export all annotations within cursor range + 导出光标范围内所有的解码数据 + + + + Export annotations for this row within cursor range + 导出光标范围内此行的解码数据 + + + + %1: +%2 + + + + + <b>%1</b> (%2) %3 + + + + + Export annotations + 导出解码数据 + + + + Text Files (*.txt);;All Files (*) + + + + + Error + + + + + File %1 could not be written to. + 文件 %1 无法保存。 + + + + Show this row + 显示此行 + + + + Show All + 全部显示 + + + + Hide All + 全部隐藏 + + + + pv::views::trace::Flag + + + Text + + + + + Delete + 删除 + + + + Disable snapping + 禁用捕捉 + + + + pv::views::trace::Header + + + Group + 组 + + + + pv::views::trace::LogicSignal + + + No trigger + 无触发 + + + + Trigger on rising edge + 上升沿触发 + + + + Trigger on high level + 高电平触发 + + + + Trigger on falling edge + 下降沿触发 + + + + Trigger on low level + 低电平触发 + + + + Trigger on rising or falling edge + 上升沿或下降沿触发 + + + + pixels + + + + + Trace height + 通道高度 + + + + Trigger + 触发 + + + + pv::views::trace::MathEditDialog + + + Math Expression Editor + Math 表达式编辑器 + + + + Inputs: + + + + + Variables: + + + + + Basic operators: + + + + + Assignments: + + + + + General purpose functions: + + + + + abs(x) Absolute value of x + + + + + avg(x, y, ...) Average of all input values + + + + + ceil(x) Smallest integer that is greater than or equal to x + + + + + clamp(lb, x, ub) Clamp x in range between lb and ub, where lb < ub + + + + + equal(x, y) Equality test between x and y using normalised epsilon + + + + + erf(x) Error function of x + + + + + erfc(x) Complimentary error function of x + + + + + exp(x) e to the power of x + + + + + expm1(x) e to the power of x minus 1, where x is very small. + + + + + floor(x) Largest integer that is less than or equal to x + + + + + frac(x) Fractional portion of x + + + + + hypot(x) Hypotenuse of x and y (i.e. sqrt(x*x + y*y)) + + + + + iclamp(lb, x, ub) Inverse-clamp x outside of the range lb and ub, where lb < ub. + If x is within the range it will snap to the closest bound + + + + + inrange(lb, x, ub) In-range returns true when x is within the range lb and ub, where lb < ub. + + + + + log(x) Natural logarithm of x + + + + + log10(x) Base 10 logarithm of x + + + + + log1p(x) Natural logarithm of 1 + x, where x is very small + + + + + log2(x) Base 2 logarithm of x + + + + + logn(x) Base N logarithm of x, where n is a positive integer + + + + + max(x, y, ...) Largest value of all the inputs + + + + + min(x, y, ...) Smallest value of all the inputs + + + + + mul(x, y, ...) Product of all the inputs + + + + + ncdf(x) Normal cumulative distribution function + + + + + nequal(x, y) Not-equal test between x and y using normalised epsilon + + + + + pow(x, y) x to the power of y + + + + + root(x, n) Nth-Root of x, where n is a positive integer + + + + + round(x) Round x to the nearest integer + + + + + roundn(x, n) Round x to n decimal places, where n > 0 and is an integer + + + + + sgn(x) Sign of x; -1 if x < 0, +1 if x > 0, else zero + + + + + sqrt(x) Square root of x, where x >= 0 + + + + + sum(x, y, ..,) Sum of all the inputs + + + + + swap(x, y) Swap the values of the variables x and y and return the current value of y + + + + + trunc(x) Integer portion of x + + + + + Trigonometry functions: + + + + + acos(x) Arc cosine of x expressed in radians. Interval [-1,+1] + + + + + acosh(x) Inverse hyperbolic cosine of x expressed in radians + + + + + asin(x) Arc sine of x expressed in radians. Interval [-1,+1] + + + + + asinh(x) Inverse hyperbolic sine of x expressed in radians + + + + + atan(x) Arc tangent of x expressed in radians. Interval [-1,+1] + + + + + atan2(x, y) Arc tangent of (x / y) expressed in radians. [-pi,+pi] + + + + + atanh(x) Inverse hyperbolic tangent of x expressed in radians + + + + + cos(x) Cosine of x + + + + + cosh(x) Hyperbolic cosine of x + + + + + cot(x) Cotangent of x + + + + + csc(x) Cosectant of x + + + + + sec(x) Secant of x + + + + + sin(x) Sine of x + + + + + sinc(x) Sine cardinal of x + + + + + sinh(x) Hyperbolic sine of x + + + + + tan(x) Tangent of x + + + + + tanh(x) Hyperbolic tangent of x + + + + + deg2rad(x) Convert x from degrees to radians + + + + + deg2grad(x) Convert x from degrees to gradians + + + + + rad2deg(x) Convert x from radians to degrees + + + + + grad2deg(x) Convert x from gradians to degrees + + + + + Logic operators: + + + + + Comparisons: + + + + + x = y or x == y True only if x is strictly equal to y + + + + + x <> y or x != y True only if x does not equal y + + + + + x < y True only if x is less than y + + + + + x <= y True only if x is less than or equal to y + + + + + x > y True only if x is greater than y + + + + + x >= y True only if x is greater than or equal to y + + + + + Flow control: + + + + + { ... } Beginning and end of instruction block + + + + + if (x, y, z) If x is true then return y else return z +if (x) y; variant without implied else +if (x) { y }; variant with an instruction block +if (x) y; else z; variant with explicit else +if (x) { y } else { z }; variant with instruction blocks + + + + + x ? y : z Ternary operator, equivalent to 'if (x, y, z)' + + + + + switch { The first true case condition that is encountered will + case x > 1: a; determine the result of the switch. If none of the case + case x < 1: b; conditions hold true, the default action is used + default: c; to determine the return value +} + + + + + while (conditon) { Evaluates expression repeatedly as long as condition is true, + expression; returning the last value of expression +} + + + + + repeat Evalues expression repeatedly as long as condition is false, + expression; returning the last value of expression +until (condition) + + + + + + for (var x := 0; condition; x += 1) { Repeatedly evaluates expression while the condition is true, + expression while evaluating the 'increment' expression on each loop +} + + + + + break Terminates the execution of the nearest enclosed loop, returning NaN + + + + + break[x] Terminates the execution of the nearest enclosed loop, returning x + + + + + continue Interrupts loop execution and resumes with the next loop iteration + + + + + return[x] Returns immediately from within the current expression, returning x + + + + + ~(expr; expr; ...) Evaluates each sub-expression and returns the value of the last one +~{expr; expr; ...} + + + + + Copy to expression + + + + + Basics + + + + + Functions 1 + + + + + Functions 2 + + + + + Trigonometry + + + + + Logic + + + + + Flow Control 1 + + + + + Flow Control 2 + + + + + Examples + + + + + pv::views::trace::MathSignal + + + Expression + 表达式 + + + + + same as session + 与会话相同 + + + + + 100 + + + + + + 10000 + + + + + + 1000000 + + + + + Number of Samples + 采样数 + + + + Sample rate + 采样率 + + + + pv::views::trace::Ruler + + + Create marker here + 在此处创建标记 + + + + Set as zero point + 设为零点 + + + + Reset zero point + 重置零点 + + + + Disable mouse hover marker + 禁用鼠标位置标记 + + + + Enable mouse hover marker + 启用鼠标位置标记 + + + + pv::views::trace::Signal + + + Name + + + + + Remove + 删除 + + + + Disable + 关闭 + + + + pv::views::trace::StandardBar + + + Zoom &In + 放大 + + + + Zoom &Out + 缩小 + + + + Zoom to &Fit + 适应窗口 + + + + Show &Cursors + 显示光标 + + + + Display last segment only + 仅显示最后一段 + + + + Display last complete segment only + 仅显示最后一个完整分段 + + + + Display a single segment + 仅显示一段 + + + + pv::views::trace::TimeMarker + + + Time + + + + + pv::views::trace::Trace + + + Create marker here + 在此处创建标记 + + + + Color + 颜色 + + + + Name + + + + + pv::views::trace::TraceGroup + + + Ungroup + 取消组合 + + + + pv::views::trace::View + + + Create marker here + 在此处创建标记 + + + + pv::widgets::DecoderGroupBox + + + Show/hide this decoder trace + 显示/隐藏此解码器采集 + + + + Delete this decoder trace + 删除此解码器采集 + + + + pv::widgets::DeviceToolButton + + + + <No Device> + + + + + pv::widgets::ExportMenu + + + Export %1... + 导出 %1... + + + + pv::widgets::ImportMenu + + + Import %1... + 导入 %1... + + + diff --git a/manual/CMakeLists.txt b/manual/CMakeLists.txt index c425f36b..3b881a56 100644 --- a/manual/CMakeLists.txt +++ b/manual/CMakeLists.txt @@ -19,6 +19,8 @@ cmake_minimum_required(VERSION 2.8.12) +project(PV_MANUAL) + # External dependencies, required and optional tools. find_program(ASCIIDOCTOR_EXECUTABLE NAMES asciidoctor) find_program(ASCIIDOCTOR_PDF_EXECUTABLE NAMES asciidoctor-pdf) @@ -34,6 +36,22 @@ set(MANUAL_SRC "${CMAKE_CURRENT_SOURCE_DIR}/manual.txt") set(MANUAL_OUT_HTML "${CMAKE_CURRENT_BINARY_DIR}/manual.html") set(MANUAL_OUT_PDF "${CMAKE_CURRENT_BINARY_DIR}/manual.pdf") +# Make in-source images/ content available to the output hierarchy for +# the inspection of created output documents during development in the +# case of out-of-source build configurations. +if (NOT EXISTS "${CMAKE_CURRENT_BINARY_DIR}/images") + message(STATUS "creating symlink for manual's images/ subdirectory") + execute_process( + COMMAND ${CMAKE_COMMAND} -E create_symlink + "${CMAKE_CURRENT_SOURCE_DIR}/images" + "${CMAKE_CURRENT_BINARY_DIR}/images" + RESULT_VARIABLE IMAGES_LINK_RESULT + ) + if (NOT IMAGES_LINK_RESULT EQUAL 0) + message(WARNING "manual rendering will lack images") + endif () +endif () + # Manual related make(1) targets. add_custom_target(manual-html COMMAND ${ASCIIDOCTOR_EXECUTABLE} @@ -57,7 +75,7 @@ if (ASCIIDOCTOR_PDF_EXECUTABLE) BYPRODUCTS ${MANUAL_OUT_PDF} DEPENDS ${MANUAL_SRC} WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR} - COMMENT "Generating manual, HTML output" + COMMENT "Generating manual, PDF output" ) else () add_custom_target(manual-pdf diff --git a/manual/manual.txt b/manual/manual.txt index 19baff63..11983e5f 100644 --- a/manual/manual.txt +++ b/manual/manual.txt @@ -1,6 +1,6 @@ PulseView User Manual ===================== -unreleased development snapshot, dated 2020-02-29 +unreleased pulseview development snapshot, manual last changed 2020-02-29 :doctype: book :imagesdir: ./images :sectnums: diff --git a/pv/application.cpp b/pv/application.cpp index 15195d06..cce6393c 100644 --- a/pv/application.cpp +++ b/pv/application.cpp @@ -86,7 +86,9 @@ const QStringList Application::get_languages() const const QString Application::get_language_editors(const QString& language) const { if (language == "de") return "Sören Apel, Uwe Hermann"; - if (language == "es_mx") return "Carlos Diaz"; + if (language == "es_MX") return "Carlos Diaz, Ulices Avila Hernandez"; + if (language == "ja_jp") return "Yukari Shoji"; + if (language == "zh_cn") return "ZtyPro"; return QString(); } @@ -106,7 +108,11 @@ void Application::switch_language(const QString& language) qWarning() << "Translation resource" << resource << "not found"; // Qt translations +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + QString tr_path(QLibraryInfo::path(QLibraryInfo::TranslationsPath)); +#else QString tr_path(QLibraryInfo::location(QLibraryInfo::TranslationsPath)); +#endif if (qt_translator_.load("qt_" + language, tr_path)) installTranslator(&qt_translator_); diff --git a/pv/data/decodesignal.cpp b/pv/data/decodesignal.cpp index 01d5f278..9c695a1b 100644 --- a/pv/data/decodesignal.cpp +++ b/pv/data/decodesignal.cpp @@ -24,6 +24,9 @@ #include #include +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) +#include +#endif #include "logic.hpp" #include "logicsegment.hpp" @@ -306,7 +309,11 @@ void DecodeSignal::auto_assign_signals(const shared_ptr dec) continue; QString ch_name = ch.name.toLower(); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + ch_name = ch_name.replace(QRegularExpression("[-_.]"), " "); +#else ch_name = ch_name.replace(QRegExp("[-_.]"), " "); +#endif shared_ptr match; for (const shared_ptr& s : session_.signalbases()) { @@ -314,7 +321,11 @@ void DecodeSignal::auto_assign_signals(const shared_ptr dec) continue; QString s_name = s->name().toLower(); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + s_name = s_name.replace(QRegularExpression("[-_.]"), " "); +#else s_name = s_name.replace(QRegExp("[-_.]"), " "); +#endif if (s->logic_data() && ((ch_name.contains(s_name)) || (s_name.contains(ch_name)))) { @@ -747,7 +758,11 @@ void DecodeSignal::save_settings(QSettings &settings) const for (const shared_ptr& decoder : stack_) { settings.beginGroup("decoder" + QString::number(decoder_idx++)); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + settings.setValue("id", (const char *)decoder->get_srd_decoder()->id); +#else settings.setValue("id", decoder->get_srd_decoder()->id); +#endif settings.setValue("visible", decoder->visible()); // Save decoder options @@ -1376,8 +1391,13 @@ void DecodeSignal::decode_proc() // If the input segment is complete, we've exhausted this segment if (input_segment->is_complete()) { #if defined HAVE_SRD_SESSION_SEND_EOF && HAVE_SRD_SESSION_SEND_EOF + // Tell protocol decoders about the end of + // the input data, which may result in more + // annotations being emitted (void)srd_session_send_eof(srd_session_); + new_annotations(); #endif + if (current_segment_id_ < (logic_mux_data_->logic_segments().size() - 1)) { // Process next segment current_segment_id_++; diff --git a/pv/data/signalbase.cpp b/pv/data/signalbase.cpp index 5f95ec33..97f70508 100644 --- a/pv/data/signalbase.cpp +++ b/pv/data/signalbase.cpp @@ -590,7 +590,12 @@ void SignalBase::restore_settings(QSettings &settings) QVariant value = settings.value("color"); // Workaround for Qt QColor serialization bug on OSX - if ((QMetaType::Type)(value.type()) == QMetaType::QColor) +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + bool is_qcolor = (QMetaType::Type)(value.typeId()) == QMetaType::QColor; +#else + bool is_qcolor = (QMetaType::Type)(value.type()) == QMetaType::QColor; +#endif + if (is_qcolor) set_color(value.value()); else set_color(QColor::fromRgba(value.value())); diff --git a/pv/dialogs/settings.cpp b/pv/dialogs/settings.cpp index 00c7dcfc..55b7e826 100644 --- a/pv/dialogs/settings.cpp +++ b/pv/dialogs/settings.cpp @@ -220,7 +220,7 @@ QWidget *Settings::get_general_settings_form(QWidget *parent) const QComboBox *language_cb = new QComboBox(); Application* a = qobject_cast(QApplication::instance()); - QString current_language = settings.value(GlobalSettings::Key_General_Language).toString(); + QString current_language = settings.value(GlobalSettings::Key_General_Language, "en").toString(); for (const QString& language : a->get_languages()) { const QLocale locale = QLocale(language); const QString desc = locale.languageToString(locale.language()); @@ -231,8 +231,13 @@ QWidget *Settings::get_general_settings_form(QWidget *parent) const language_cb->setCurrentIndex(index); } } +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + connect(language_cb, SIGNAL(currentTextChanged(const QString&)), + this, SLOT(on_general_language_changed(const QString&))); +#else connect(language_cb, SIGNAL(currentIndexChanged(const QString&)), this, SLOT(on_general_language_changed(const QString&))); +#endif general_layout->addRow(tr("User interface language"), language_cb); // Theme combobox @@ -346,6 +351,10 @@ QWidget *Settings::get_view_settings_form(QWidget *parent) const SLOT(on_view_showHoverMarker_changed(int))); trace_view_layout->addRow(tr("Highlight mouse cursor using a vertical marker line"), cb); + cb = create_checkbox(GlobalSettings::Key_View_KeepRulerItemSelected, + SLOT(on_view_keepRulerItemSelected_changed(int))); + trace_view_layout->addRow(tr("Keep active item on ruler selected when editing popup is closed"), cb); + QSpinBox *snap_distance_sb = new QSpinBox(); snap_distance_sb->setRange(0, 1000); snap_distance_sb->setSuffix(tr(" pixels")); @@ -760,6 +769,12 @@ void Settings::on_view_showHoverMarker_changed(int state) settings.setValue(GlobalSettings::Key_View_ShowHoverMarker, state ? true : false); } +void Settings::on_view_keepRulerItemSelected_changed(int state) +{ + GlobalSettings settings; + settings.setValue(GlobalSettings::Key_View_KeepRulerItemSelected, state ? true : false); +} + void Settings::on_view_snapDistance_changed(int value) { GlobalSettings settings; diff --git a/pv/dialogs/settings.hpp b/pv/dialogs/settings.hpp index c8ba8162..bd3572ff 100644 --- a/pv/dialogs/settings.hpp +++ b/pv/dialogs/settings.hpp @@ -74,6 +74,7 @@ private Q_SLOTS: void on_view_fillSignalHighAreaColor_changed(QColor color); void on_view_showAnalogMinorGrid_changed(int state); void on_view_showHoverMarker_changed(int state); + void on_view_keepRulerItemSelected_changed(int state); void on_view_snapDistance_changed(int value); void on_view_cursorFillColor_changed(QColor color); void on_view_conversionThresholdDispMode_changed(int state); diff --git a/pv/globalsettings.cpp b/pv/globalsettings.cpp index 38017f3b..ecca21d5 100644 --- a/pv/globalsettings.cpp +++ b/pv/globalsettings.cpp @@ -67,6 +67,7 @@ const QString GlobalSettings::Key_View_ConversionThresholdDispMode = "View_Conve const QString GlobalSettings::Key_View_DefaultDivHeight = "View_DefaultDivHeight"; const QString GlobalSettings::Key_View_DefaultLogicHeight = "View_DefaultLogicHeight"; const QString GlobalSettings::Key_View_ShowHoverMarker = "View_ShowHoverMarker"; +const QString GlobalSettings::Key_View_KeepRulerItemSelected = "View_KeepRulerItemSelected"; const QString GlobalSettings::Key_View_SnapDistance = "View_SnapDistance"; const QString GlobalSettings::Key_View_CursorFillColor = "View_CursorFillColor"; const QString GlobalSettings::Key_View_CursorShowFrequency = "View_CursorShowFrequency"; @@ -152,6 +153,9 @@ void GlobalSettings::set_defaults_where_needed() if (!contains(Key_View_ShowHoverMarker)) setValue(Key_View_ShowHoverMarker, true); + if (!contains(Key_View_KeepRulerItemSelected)) + setValue(Key_View_KeepRulerItemSelected, false); + if (!contains(Key_View_SnapDistance)) setValue(Key_View_SnapDistance, 15); @@ -330,7 +334,11 @@ void GlobalSettings::store_gvariant(QSettings &settings, GVariant *v) g_variant_get_size(v)); settings.setValue("value", var_data); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + settings.setValue("type", (const char *)var_type_str); +#else settings.setValue("type", var_type_str); +#endif g_free(var_type_str); } diff --git a/pv/globalsettings.hpp b/pv/globalsettings.hpp index 67922d7a..f6239a6b 100644 --- a/pv/globalsettings.hpp +++ b/pv/globalsettings.hpp @@ -72,6 +72,7 @@ public: static const QString Key_View_DefaultDivHeight; static const QString Key_View_DefaultLogicHeight; static const QString Key_View_ShowHoverMarker; + static const QString Key_View_KeepRulerItemSelected; static const QString Key_View_SnapDistance; static const QString Key_View_CursorFillColor; static const QString Key_View_CursorShowInterval; diff --git a/pv/mainwindow.cpp b/pv/mainwindow.cpp index 34938e73..8646175e 100644 --- a/pv/mainwindow.cpp +++ b/pv/mainwindow.cpp @@ -79,6 +79,8 @@ MainWindow::MainWindow(DeviceManager &device_manager, QWidget *parent) : { setup_ui(); restore_ui_settings(); + connect(this, SIGNAL(session_error_raised(const QString, const QString)), + this, SLOT(on_session_error_raised(const QString, const QString))); } MainWindow::~MainWindow() @@ -95,7 +97,7 @@ MainWindow::~MainWindow() void MainWindow::show_session_error(const QString text, const QString info_text) { // TODO Emulate noquote() - qDebug() << "Notifying user of session error:" << info_text; + qDebug() << "Notifying user of session error: " << text << "; " << info_text; QMessageBox msg; msg.setText(text + "\n\n" + info_text); @@ -193,6 +195,9 @@ shared_ptr MainWindow::add_view(views::ViewType type, qobject_cast(v.get()), SLOT(trigger_event(int, util::Timestamp))); + connect(&session, SIGNAL(session_error_raised(const QString, const QString)), + this, SLOT(on_session_error_raised(const QString, const QString))); + if (type == views::ViewTypeTrace) { views::trace::View *tv = qobject_cast(v.get()); @@ -547,10 +552,14 @@ void MainWindow::setup_ui() session_selector_.setCornerWidget(static_tab_widget_, Qt::TopLeftCorner); session_selector_.setTabsClosable(true); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + close_application_shortcut_ = new QShortcut(QKeySequence(Qt::CTRL | Qt::Key_Q), this, SLOT(close())); + close_current_tab_shortcut_ = new QShortcut(QKeySequence(Qt::CTRL | Qt::Key_W), this, SLOT(on_close_current_tab())); +#else close_application_shortcut_ = new QShortcut(QKeySequence(Qt::CTRL + Qt::Key_Q), this, SLOT(close())); - close_application_shortcut_->setAutoRepeat(false); - close_current_tab_shortcut_ = new QShortcut(QKeySequence(Qt::CTRL + Qt::Key_W), this, SLOT(on_close_current_tab())); +#endif + close_application_shortcut_->setAutoRepeat(false); connect(new_session_button_, SIGNAL(clicked(bool)), this, SLOT(on_new_session_clicked())); @@ -687,8 +696,7 @@ void MainWindow::on_run_stop_clicked() if (any_running) s->stop_capture(); else - s->start_capture([&](QString message) { - show_session_error("Capture failed", message); }); + s->start_capture([&](QString message) {Q_EMIT session_error_raised("Capture failed", message);}); } else { shared_ptr session = last_focused_session_; @@ -698,8 +706,7 @@ void MainWindow::on_run_stop_clicked() switch (session->get_capture_state()) { case Session::Stopped: - session->start_capture([&](QString message) { - show_session_error("Capture failed", message); }); + session->start_capture([&](QString message) {Q_EMIT session_error_raised("Capture failed", message);}); break; case Session::AwaitingTrigger: case Session::Running: @@ -977,4 +984,8 @@ void MainWindow::on_close_current_tab() on_tab_close_requested(tab); } +void MainWindow::on_session_error_raised(const QString text, const QString info_text) { + MainWindow::show_session_error(text, info_text); +} + } // namespace pv diff --git a/pv/mainwindow.hpp b/pv/mainwindow.hpp index e10d1817..493e3a55 100644 --- a/pv/mainwindow.hpp +++ b/pv/mainwindow.hpp @@ -115,8 +115,12 @@ private: virtual bool restoreState(const QByteArray &state, int version = 0); +Q_SIGNALS: + void session_error_raised(const QString text, const QString info_text); + public Q_SLOTS: void on_run_stop_clicked(); + void on_session_error_raised(const QString text, const QString info_text); private Q_SLOTS: void on_add_view(ViewType type, Session *session); diff --git a/pv/popups/channels.cpp b/pv/popups/channels.cpp index ecdc59a3..ce2e8e98 100644 --- a/pv/popups/channels.cpp +++ b/pv/popups/channels.cpp @@ -158,8 +158,13 @@ Channels::Channels(Session &session, QWidget *parent) : layout_.addRow(&filter_buttons_bar_); // Connect the check-box signal mapper +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + connect(&check_box_mapper_, SIGNAL(mappedObject(QObject*)), + this, SLOT(on_channel_checked(QObject*))); +#else connect(&check_box_mapper_, SIGNAL(mapped(QWidget*)), this, SLOT(on_channel_checked(QWidget*))); +#endif } void Channels::set_all_channels(bool set) @@ -354,7 +359,11 @@ void Channels::showEvent(QShowEvent *event) updating_channels_ = false; } +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) +void Channels::on_channel_checked(QObject *widget) +#else void Channels::on_channel_checked(QWidget *widget) +#endif { if (updating_channels_) return; diff --git a/pv/popups/channels.hpp b/pv/popups/channels.hpp index c176eb7a..66d284b0 100644 --- a/pv/popups/channels.hpp +++ b/pv/popups/channels.hpp @@ -82,7 +82,11 @@ private: void showEvent(QShowEvent *event); private Q_SLOTS: +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + void on_channel_checked(QObject *widget); +#else void on_channel_checked(QWidget *widget); +#endif void enable_all_channels(); void disable_all_channels(); diff --git a/pv/session.cpp b/pv/session.cpp index f992d9f1..b4ecc6a8 100644 --- a/pv/session.cpp +++ b/pv/session.cpp @@ -614,6 +614,9 @@ void Session::set_device(shared_ptr device) } catch (const QString &e) { device_.reset(); MainWindow::show_session_error(tr("Failed to open device"), e); + } catch (const sigrok::Error &e) { + device_.reset(); + MainWindow::show_session_error(tr("Failed to open device"), QString(e.what())); } if (device_) { @@ -756,8 +759,11 @@ void Session::load_file(QString file_name, QString setup_file_name, file_name.toStdString()))); } catch (Error& e) { MainWindow::show_session_error(tr("Failed to load %1").arg(file_name), e.what()); - set_default_device(); - main_bar_->update_device_list(); + return; + } + + if (!device_) { + MainWindow::show_session_error(errorMessage, ""); return; } @@ -776,7 +782,7 @@ void Session::load_file(QString file_name, QString setup_file_name, main_bar_->update_device_list(); start_capture([&, errorMessage](QString infoMessage) { - MainWindow::show_session_error(errorMessage, infoMessage); }); + Q_EMIT session_error_raised(errorMessage, infoMessage); }); // Only set save path if we loaded an srzip file if (dynamic_pointer_cast(device_)) @@ -829,6 +835,8 @@ void Session::start_capture(function error_handler) name_changed(); } + acq_start_time_ = Glib::DateTime::create_now_local(); + // Begin the session sampling_thread_ = std::thread(&Session::sample_thread_proc, this, error_handler); } @@ -923,6 +931,11 @@ double Session::get_samplerate() const return samplerate; } +Glib::DateTime Session::get_acquisition_start_time() const +{ + return acq_start_time_; +} + uint32_t Session::get_highest_segment_id() const { return highest_segment_id_; diff --git a/pv/session.hpp b/pv/session.hpp index 91f98b58..94338c20 100644 --- a/pv/session.hpp +++ b/pv/session.hpp @@ -35,6 +35,8 @@ #include #include +#include + #include #include #include @@ -185,6 +187,7 @@ public: void stop_capture(); double get_samplerate() const; + Glib::DateTime get_acquisition_start_time() const; uint32_t get_highest_segment_id() const; uint64_t get_segment_sample_count(uint32_t segment_id) const; @@ -264,6 +267,7 @@ Q_SIGNALS: void data_received(); void add_view(ViewType type, Session *session); + void session_error_raised(const QString text, const QString info_text); public Q_SLOTS: void on_data_saved(); @@ -311,6 +315,7 @@ private: bool frame_began_; QElapsedTimer acq_time_; + Glib::DateTime acq_start_time_; MetadataObjManager metadata_obj_manager_; diff --git a/pv/storesession.cpp b/pv/storesession.cpp index 182642ee..5eb6a8ad 100644 --- a/pv/storesession.cpp +++ b/pv/storesession.cpp @@ -184,6 +184,9 @@ bool StoreSession::start() {{ConfigKey::SAMPLERATE, Glib::Variant::create( any_segment->samplerate())}}); output_->receive(meta); + + auto header = context->create_header_packet(session_.get_acquisition_start_time()); + output_->receive(header); } catch (Error& error) { error_ = tr("Error while saving: ") + error.what(); return false; diff --git a/pv/toolbars/mainbar.cpp b/pv/toolbars/mainbar.cpp index 39c290df..cd46c063 100644 --- a/pv/toolbars/mainbar.cpp +++ b/pv/toolbars/mainbar.cpp @@ -130,7 +130,11 @@ MainBar::MainBar(Session &session, QWidget *parent, pv::views::trace::View *view action_open_->setText(tr("&Open...")); action_open_->setIcon(QIcon::fromTheme("document-open", QIcon(":/icons/document-open.png"))); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + action_open_->setShortcut(QKeySequence(Qt::CTRL | Qt::Key_O)); +#else action_open_->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_O)); +#endif connect(action_open_, SIGNAL(triggered(bool)), this, SLOT(on_actionOpen_triggered())); @@ -141,7 +145,11 @@ MainBar::MainBar(Session &session, QWidget *parent, pv::views::trace::View *view action_save_->setText(tr("&Save...")); action_save_->setIcon(QIcon::fromTheme("document-save-as", QIcon(":/icons/document-save-as.png"))); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + action_save_->setShortcut(QKeySequence(Qt::CTRL | Qt::Key_S)); +#else action_save_->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_S)); +#endif connect(action_save_, SIGNAL(triggered(bool)), this, SLOT(on_actionSave_triggered())); @@ -154,7 +162,11 @@ MainBar::MainBar(Session &session, QWidget *parent, pv::views::trace::View *view action_save_selection_as_->setText(tr("Save Selected &Range As...")); action_save_selection_as_->setIcon(QIcon::fromTheme("document-save-as", QIcon(":/icons/document-save-as.png"))); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + action_save_selection_as_->setShortcut(QKeySequence(Qt::CTRL | Qt::Key_R)); +#else action_save_selection_as_->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_R)); +#endif connect(action_save_selection_as_, SIGNAL(triggered(bool)), this, SLOT(on_actionSaveSelectionAs_triggered())); diff --git a/pv/views/decoder_binary/QHexView.cpp b/pv/views/decoder_binary/QHexView.cpp index 2c893e36..0badadc7 100644 --- a/pv/views/decoder_binary/QHexView.cpp +++ b/pv/views/decoder_binary/QHexView.cpp @@ -497,7 +497,11 @@ void QHexView::paintEvent(QPaintEvent *event) painter.setPen(palette().color(QPalette::HighlightedText)); } +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + painter.drawText(x, y, QString(QChar(ch))); +#else painter.drawText(x, y, QString(ch)); +#endif x += charWidth_; } diff --git a/pv/views/decoder_binary/view.cpp b/pv/views/decoder_binary/view.cpp index 1e40bd1b..6e61fa3a 100644 --- a/pv/views/decoder_binary/view.cpp +++ b/pv/views/decoder_binary/view.cpp @@ -110,7 +110,11 @@ View::View(Session &session, bool is_main_view, QMainWindow *parent) : save_action_->setText(tr("&Save...")); save_action_->setIcon(QIcon::fromTheme("document-save-as", QIcon(":/icons/document-save-as.png"))); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + save_action_->setShortcut(QKeySequence(Qt::CTRL | Qt::Key_S)); +#else save_action_->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_S)); +#endif connect(save_action_, SIGNAL(triggered(bool)), this, SLOT(on_actionSave_triggered())); diff --git a/pv/views/tabular_decoder/view.cpp b/pv/views/tabular_decoder/view.cpp index 7e4b3ddb..c1d74290 100644 --- a/pv/views/tabular_decoder/view.cpp +++ b/pv/views/tabular_decoder/view.cpp @@ -202,7 +202,11 @@ View::View(Session &session, bool is_main_view, QMainWindow *parent) : save_action_->setText(tr("&Save...")); save_action_->setIcon(QIcon::fromTheme("document-save-as", QIcon(":/icons/document-save-as.png"))); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + save_action_->setShortcut(QKeySequence(Qt::CTRL | Qt::Key_S)); +#else save_action_->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_S)); +#endif connect(save_action_, SIGNAL(triggered(bool)), this, SLOT(on_actionSave_triggered())); diff --git a/pv/views/trace/analogsignal.cpp b/pv/views/trace/analogsignal.cpp index ba5adebf..2a50d571 100644 --- a/pv/views/trace/analogsignal.cpp +++ b/pv/views/trace/analogsignal.cpp @@ -139,7 +139,7 @@ std::map AnalogSignal::save_settings() const result["neg_vdivs"] = neg_vdivs_; result["scale_index"] = scale_index_; result["display_type"] = display_type_; - result["autoranging"] = pos_vdivs_; + result["autoranging"] = autoranging_; result["div_height"] = div_height_; return result; @@ -177,6 +177,7 @@ void AnalogSignal::restore_settings(std::map settings) div_height_ = settings["div_height"].toInt(); update_logic_level_offsets(); + update_scale(); if ((div_height_ != old_height) && owner_) { // Call order is important, otherwise the lazy event handler won't work @@ -1100,13 +1101,20 @@ void AnalogSignal::on_conv_threshold_changed(int index) // https://txt2re.com/index-c++.php3?s=0.1V&1&-13 QString re1 = "([+-]?\\d*[\\.,]?\\d*)"; // Float value QString re2 = "([a-zA-Z]*)"; // SI unit - QRegExp regex(re1 + re2); - const QString text = conv_threshold_cb_->currentText(); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + QRegularExpression regex(re1 + re2); + if (!regex.match(text).hasMatch()) + return; // String doesn't match the regex + + QStringList tokens = regex.match(text).capturedTexts(); +#else + QRegExp regex(re1 + re2); if (!regex.exactMatch(text)) return; // String doesn't match the regex QStringList tokens = regex.capturedTexts(); +#endif // For now, we simply assume that the unit is volt without modifiers const double thr = tokens.at(1).toDouble(); @@ -1127,13 +1135,22 @@ void AnalogSignal::on_conv_threshold_changed(int index) QString re3 = "\\/"; // Forward slash, not captured QString re4 = "([+-]?\\d*[\\.,]?\\d*)"; // Float value QString re5 = "([a-zA-Z]*)"; // SI unit + const QString text = conv_threshold_cb_->currentText(); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + QRegularExpression regex(re1 + re2 + re3 + re4 + re5); + + if (!regex.match(text).hasMatch()) + return; // String doesn't match the regex + + QStringList tokens = regex.match(text).capturedTexts(); +#else QRegExp regex(re1 + re2 + re3 + re4 + re5); - const QString text = conv_threshold_cb_->currentText(); if (!regex.exactMatch(text)) return; // String doesn't match the regex QStringList tokens = regex.capturedTexts(); +#endif // For now, we simply assume that the unit is volt without modifiers const double low_thr = tokens.at(1).toDouble(); diff --git a/pv/views/trace/cursor.cpp b/pv/views/trace/cursor.cpp index 80eaba23..8462a3a6 100644 --- a/pv/views/trace/cursor.cpp +++ b/pv/views/trace/cursor.cpp @@ -72,7 +72,7 @@ QRectF Cursor::label_rect(const QRectF &rect) const const float x = get_x(); QFontMetrics m(QApplication::font()); - QSize text_size = m.boundingRect(get_text()).size(); + QSize text_size = m.boundingRect(get_display_text()).size(); const QSizeF label_size( text_size.width() + LabelPadding.width() * 2, diff --git a/pv/views/trace/cursorpair.cpp b/pv/views/trace/cursorpair.cpp index 7d7d8e4d..ec7b75ad 100644 --- a/pv/views/trace/cursorpair.cpp +++ b/pv/views/trace/cursorpair.cpp @@ -202,11 +202,13 @@ void CursorPair::paint_label(QPainter &p, const QRect &rect, bool hover) text_size_ = p.boundingRect(QRectF(), 0, text).size(); + /* Currently, selecting the middle section between two cursors doesn't do + * anything, so don't highlight it when selected if (selected()) { p.setBrush(Qt::transparent); p.setPen(highlight_pen()); p.drawRoundedRect(delta_rect, radius, radius); - } + } */ p.setBrush(hover ? Cursor::FillColor.lighter() : Cursor::FillColor); p.setPen(Cursor::FillColor.darker()); diff --git a/pv/views/trace/decodetrace.cpp b/pv/views/trace/decodetrace.cpp index 888064d0..63384911 100644 --- a/pv/views/trace/decodetrace.cpp +++ b/pv/views/trace/decodetrace.cpp @@ -186,7 +186,16 @@ DecodeTrace::DecodeTrace(pv::Session &session, this, SLOT(on_decode_finished())); connect(decode_signal_.get(), SIGNAL(channels_updated()), this, SLOT(on_channels_updated())); - +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + connect(&delete_mapper_, SIGNAL(mappedInt(int)), + this, SLOT(on_delete_decoder(int))); + connect(&show_hide_mapper_, SIGNAL(mappedInt(int)), + this, SLOT(on_show_hide_decoder(int))); + connect(&row_show_hide_mapper_, SIGNAL(mappedInt(int)), + this, SLOT(on_show_hide_row(int))); + connect(&class_show_hide_mapper_, SIGNAL(mappedObject(QObject*)), + this, SLOT(on_show_hide_class(QObject*))); +#else connect(&delete_mapper_, SIGNAL(mapped(int)), this, SLOT(on_delete_decoder(int))); connect(&show_hide_mapper_, SIGNAL(mapped(int)), @@ -195,6 +204,7 @@ DecodeTrace::DecodeTrace(pv::Session &session, this, SLOT(on_show_hide_row(int))); connect(&class_show_hide_mapper_, SIGNAL(mapped(QWidget*)), this, SLOT(on_show_hide_class(QWidget*))); +#endif connect(&delayed_trace_updater_, SIGNAL(timeout()), this, SLOT(on_delayed_trace_update())); @@ -667,10 +677,19 @@ void DecodeTrace::mouse_left_press_event(const QMouseEvent* event) continue; unsigned int y = get_row_y(&r); - if ((event->x() > 0) && (event->x() <= (int)(ArrowSize + 3 + r.title_width)) && - (event->y() > (int)(y - (default_row_height_ / 2))) && - (event->y() <= (int)(y + (default_row_height_ / 2)))) { - + bool need_anim = true; +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + need_anim &= event->position().x() > 0; + need_anim &= event->position().x() <= (int)(ArrowSize + 3 + r.title_width); + need_anim &= event->position().y() > (int)(y - (default_row_height_ / 2)); + need_anim &= event->position().y() <= (int)(y + (default_row_height_ / 2)); +#else + need_anim &= event->x() > 0; + need_anim &= event->x() <= (int)(ArrowSize + 3 + r.title_width); + need_anim &= event->y() > (int)(y - (default_row_height_ / 2)); + need_anim &= event->y() <= (int)(y + (default_row_height_ / 2)); +#endif + if (need_anim) { if (r.expanded) { r.collapsing = true; r.expanded = false; @@ -1249,6 +1268,19 @@ void DecodeTrace::initialize_row_widgets(DecodeTraceRow* r, unsigned int row_id) QPalette header_palette = owner_->view()->palette(); QPalette selector_palette = owner_->view()->palette(); +#if QT_VERSION >= QT_VERSION_CHECK(5, 12, 0) + if (GlobalSettings::current_theme_is_dark()) { + header_palette.setColor(QPalette::Window, + QColor(255, 255, 255, ExpansionAreaHeaderAlpha)); + selector_palette.setColor(QPalette::Window, + QColor(255, 255, 255, ExpansionAreaAlpha)); + } else { + header_palette.setColor(QPalette::Window, + QColor(0, 0, 0, ExpansionAreaHeaderAlpha)); + selector_palette.setColor(QPalette::Window, + QColor(0, 0, 0, ExpansionAreaAlpha)); + } +#else if (GlobalSettings::current_theme_is_dark()) { header_palette.setColor(QPalette::Background, QColor(255, 255, 255, ExpansionAreaHeaderAlpha)); @@ -1260,6 +1292,7 @@ void DecodeTrace::initialize_row_widgets(DecodeTraceRow* r, unsigned int row_id) selector_palette.setColor(QPalette::Background, QColor(0, 0, 0, ExpansionAreaAlpha)); } +#endif const int w = m.boundingRect(r->decode_row->title()).width() + RowTitleMargin; r->title_width = w; @@ -1602,7 +1635,11 @@ void DecodeTrace::on_show_hide_row(int row_id) owner_->row_item_appearance_changed(false, true); } +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) +void DecodeTrace::on_show_hide_class(QObject* sender) +#else void DecodeTrace::on_show_hide_class(QWidget* sender) +#endif { void* ann_class_ptr = sender->property("ann_class_ptr").value(); assert(ann_class_ptr); diff --git a/pv/views/trace/decodetrace.hpp b/pv/views/trace/decodetrace.hpp index 80c9cf75..0ba52b35 100644 --- a/pv/views/trace/decodetrace.hpp +++ b/pv/views/trace/decodetrace.hpp @@ -278,7 +278,11 @@ private Q_SLOTS: void on_show_hide_decoder(int index); void on_show_hide_row(int row_id); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + void on_show_hide_class(QObject* sender); +#else void on_show_hide_class(QWidget* sender); +#endif void on_show_all_classes(); void on_hide_all_classes(); void on_row_container_resized(QWidget* sender); diff --git a/pv/views/trace/flag.cpp b/pv/views/trace/flag.cpp index b0518b64..c356b15b 100644 --- a/pv/views/trace/flag.cpp +++ b/pv/views/trace/flag.cpp @@ -57,7 +57,11 @@ bool Flag::enabled() const return true; } -QString Flag::get_text() const +/** + * Returns the text used to display this flag item. This is not necessarily the + * name that the user has given it. + */ +QString Flag::get_display_text() const { QString s; @@ -73,6 +77,14 @@ QString Flag::get_text() const return s; } +/** + * Returns the text of this flag item, i.e. the user-editable name. + */ +QString Flag::get_text() const +{ + return text_; +} + void Flag::set_text(const QString &text) { text_ = text; @@ -92,7 +104,7 @@ QRectF Flag::label_rect(const QRectF &rect) const const float x = get_x(); QFontMetrics m(QApplication::font()); - QSize text_size = m.boundingRect(get_text()).size(); + QSize text_size = m.boundingRect(get_display_text()).size(); const QSizeF label_size( text_size.width() + LabelPadding.width() * 2, diff --git a/pv/views/trace/flag.hpp b/pv/views/trace/flag.hpp index 4c4c977f..eb4bf87c 100644 --- a/pv/views/trace/flag.hpp +++ b/pv/views/trace/flag.hpp @@ -63,7 +63,13 @@ public: virtual bool enabled() const override; /** - * Gets the text to show in the marker. + * Gets the current text to show in the marker - this may be dynamic. + */ + virtual QString get_display_text() const override; + + /** + * Gets the default text used to show the marker - e.g. the user-editable + * name. */ virtual QString get_text() const override; diff --git a/pv/views/trace/marginwidget.cpp b/pv/views/trace/marginwidget.cpp index 537ffe5e..347b41ed 100644 --- a/pv/views/trace/marginwidget.cpp +++ b/pv/views/trace/marginwidget.cpp @@ -48,10 +48,10 @@ void MarginWidget::show_popup(const shared_ptr &item) { pv::widgets::Popup *const p = item->create_popup(this); - connect(p, SIGNAL(closed()), this, SLOT(on_popup_closed())); - - if (p) + if (p) { + connect(p, SIGNAL(closed()), this, SLOT(on_popup_closed())); p->show(); + } } void MarginWidget::contextMenuEvent(QContextMenuEvent *event) diff --git a/pv/views/trace/ruler.cpp b/pv/views/trace/ruler.cpp index 83ffed28..64581459 100644 --- a/pv/views/trace/ruler.cpp +++ b/pv/views/trace/ruler.cpp @@ -242,7 +242,11 @@ shared_ptr Ruler::get_mouse_over_item(const QPoint &pt) void Ruler::mouseDoubleClickEvent(QMouseEvent *event) { +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + hover_item_ = view_.add_flag(get_absolute_time_from_x_pos(event->pos().x())); +#else hover_item_ = view_.add_flag(get_absolute_time_from_x_pos(event->x())); +#endif } void Ruler::paintEvent(QPaintEvent*) diff --git a/pv/views/trace/signal.cpp b/pv/views/trace/signal.cpp index cda9a4a4..8840825c 100644 --- a/pv/views/trace/signal.cpp +++ b/pv/views/trace/signal.cpp @@ -51,7 +51,7 @@ const char *const ChannelNames[] = { "TX", "RX", "SDA", - "SCL" + "SCL", "SCLK", "MOSI", "MISO", diff --git a/pv/views/trace/timemarker.cpp b/pv/views/trace/timemarker.cpp index b428f602..0f390f52 100644 --- a/pv/views/trace/timemarker.cpp +++ b/pv/views/trace/timemarker.cpp @@ -88,7 +88,7 @@ QRectF TimeMarker::label_rect(const QRectF &rect) const { QFontMetrics m(QApplication::font()); const QSizeF text_size( - max(m.boundingRect(get_text()).size().width(), ArrowSize), + max(m.boundingRect(get_display_text()).size().width(), ArrowSize), m.height()); const QSizeF label_size(text_size + LabelPadding * 2); const float top = rect.height() - label_size.height() - @@ -105,6 +105,11 @@ QRectF TimeMarker::hit_box_rect(const ViewItemPaintParams &pp) const return QRectF(x - h / 2.0f, pp.top(), h, pp.height()); } +QString TimeMarker::get_display_text() const +{ + return get_text(); +} + void TimeMarker::set_text(const QString &text) { (void)text; @@ -158,7 +163,7 @@ void TimeMarker::paint_label(QPainter &p, const QRect &rect, bool hover) p.drawPolygon(points, countof(points)); p.setPen(select_text_color(color_)); - p.drawText(r, Qt::AlignCenter | Qt::AlignVCenter, get_text()); + p.drawText(r, Qt::AlignCenter | Qt::AlignVCenter, get_display_text()); } void TimeMarker::paint_fore(QPainter &p, ViewItemPaintParams &pp) @@ -179,6 +184,8 @@ pv::widgets::Popup* TimeMarker::create_popup(QWidget *parent) popup->set_position(parent->mapToGlobal( drag_point(parent->rect())), Popup::Bottom); + connect(popup, SIGNAL(closed()), this, SLOT(on_popup_closed())); + QFormLayout *const form = new QFormLayout(popup); popup->setLayout(form); @@ -193,6 +200,13 @@ pv::widgets::Popup* TimeMarker::create_popup(QWidget *parent) return popup; } +void TimeMarker::on_popup_closed() +{ + GlobalSettings settings; + if (!settings.value(GlobalSettings::Key_View_KeepRulerItemSelected).toBool()) + select(false); +} + void TimeMarker::on_value_changed(const pv::util::Timestamp& value) { set_time(view_.ruler()->get_absolute_time_from_ruler_time(value)); diff --git a/pv/views/trace/timemarker.hpp b/pv/views/trace/timemarker.hpp index 040a29ea..f67a0f17 100644 --- a/pv/views/trace/timemarker.hpp +++ b/pv/views/trace/timemarker.hpp @@ -95,7 +95,13 @@ public: QRectF hit_box_rect(const ViewItemPaintParams &pp) const override; /** - * Gets the text to show in the marker. + * Gets the current text to show in the marker - this may be dynamic. + */ + virtual QString get_display_text() const; + + /** + * Gets the default text used to show the marker - e.g. the user-editable + * name. */ virtual QString get_text() const = 0; @@ -122,6 +128,8 @@ public: virtual pv::widgets::Popup* create_popup(QWidget *parent) override; private Q_SLOTS: + void on_popup_closed(); + void on_value_changed(const pv::util::Timestamp& value); protected: diff --git a/pv/views/trace/trace.cpp b/pv/views/trace/trace.cpp index 1f77598d..4535a13e 100644 --- a/pv/views/trace/trace.cpp +++ b/pv/views/trace/trace.cpp @@ -442,7 +442,8 @@ void Trace::on_popup_closed() void Trace::on_nameedit_changed(const QString &name) { /* This event handler notifies SignalBase that the name changed */ - base_->set_name(name); + if (!name.isEmpty()) + base_->set_name(name); } void Trace::on_coloredit_changed(const QColor &color) diff --git a/pv/views/trace/tracegroup.cpp b/pv/views/trace/tracegroup.cpp index 3cbca909..ecc97b6e 100644 --- a/pv/views/trace/tracegroup.cpp +++ b/pv/views/trace/tracegroup.cpp @@ -138,7 +138,11 @@ QMenu* TraceGroup::create_header_context_menu(QWidget *parent) QMenu *const menu = new QMenu(parent); QAction *const ungroup = new QAction(tr("Ungroup"), this); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + ungroup->setShortcut(QKeySequence(Qt::CTRL | Qt::Key_U)); +#else ungroup->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_U)); +#endif connect(ungroup, SIGNAL(triggered()), this, SLOT(on_ungroup())); menu->addAction(ungroup); diff --git a/pv/views/trace/view.cpp b/pv/views/trace/view.cpp index d4d0c5a8..33d8b0a4 100644 --- a/pv/views/trace/view.cpp +++ b/pv/views/trace/view.cpp @@ -1530,7 +1530,11 @@ bool View::eventFilter(QObject *object, QEvent *event) else if (object == ruler_) hover_point_ = mouse_event->pos(); else if (object == header_) +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + hover_point_ = QPoint(0, mouse_event->pos().y()); +#else hover_point_ = QPoint(0, mouse_event->y()); +#endif else hover_point_ = QPoint(-1, -1); diff --git a/pv/views/trace/viewport.cpp b/pv/views/trace/viewport.cpp index bab4f953..e2a32aa2 100644 --- a/pv/views/trace/viewport.cpp +++ b/pv/views/trace/viewport.cpp @@ -124,12 +124,40 @@ vector< shared_ptr > Viewport::items() bool Viewport::touch_event(QTouchEvent *event) { +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + QList touchPoints = event->points(); +#else QList touchPoints = event->touchPoints(); +#endif if (touchPoints.count() != 2) { pinch_zoom_active_ = false; return false; } +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + if (event->device()->type() == QInputDevice::DeviceType::TouchPad) { + return false; + } + + const QEventPoint &touchPoint0 = touchPoints.first(); + const QEventPoint &touchPoint1 = touchPoints.last(); + + if (!pinch_zoom_active_ || + (event->touchPointStates() & QEventPoint::Pressed)) { + pinch_offset0_ = (view_.offset() + view_.scale() * touchPoint0.position().x()).convert_to(); + pinch_offset1_ = (view_.offset() + view_.scale() * touchPoint1.position().x()).convert_to(); + pinch_zoom_active_ = true; + } + + double w = touchPoint1.position().x() - touchPoint0.position().x(); + if (abs(w) >= 1.0) { + const double scale = + fabs((pinch_offset1_ - pinch_offset0_) / w); + double offset = pinch_offset0_ - touchPoint0.position().x() * scale; + if (scale > 0) + view_.set_scale_offset(scale, offset); + } +#else if (event->device()->type() == QTouchDevice::TouchPad) { return false; } @@ -152,6 +180,7 @@ bool Viewport::touch_event(QTouchEvent *event) if (scale > 0) view_.set_scale_offset(scale, offset); } +#endif if (event->touchPointStates() & Qt::TouchPointReleased) { pinch_zoom_active_ = false; @@ -162,7 +191,11 @@ bool Viewport::touch_event(QTouchEvent *event) } else { // Update the mouse down fields so that continued // dragging with the primary touch will work correctly +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + mouse_down_point_ = touchPoint0.position().toPoint(); +#else mouse_down_point_ = touchPoint0.pos().toPoint(); +#endif drag(); } } @@ -215,10 +248,17 @@ void Viewport::mouseDoubleClickEvent(QMouseEvent *event) { assert(event); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + if (event->buttons() & Qt::LeftButton) + view_.zoom(2.0, event->position().x()); + else if (event->buttons() & Qt::RightButton) + view_.zoom(-2.0, event->position().x()); +#else if (event->buttons() & Qt::LeftButton) view_.zoom(2.0, event->x()); else if (event->buttons() & Qt::RightButton) view_.zoom(-2.0, event->x()); +#endif } void Viewport::wheelEvent(QWheelEvent *event) @@ -241,9 +281,15 @@ void Viewport::wheelEvent(QWheelEvent *event) // is intrepretted as vertical scrolling view_.set_v_offset(-view_.owner_visual_v_offset() - (delta * height()) / (8 * 120)); + } else if (event->modifiers() & Qt::ShiftModifier) { + // Vertical scrolling with the shift key pressed + // acts as horizontal scrolling like in Gimp + // and Inkscape. + view_.set_scale_offset(view_.scale(), + - delta * view_.scale() + view_.offset()); } else { // Vertical scrolling is interpreted as zooming in/out -#if QT_VERSION >= QT_VERSION_CHECK(5, 12, 0) +#if QT_VERSION >= QT_VERSION_CHECK(5, 14, 0) view_.zoom(delta / 120.0, event->position().x()); #else view_.zoom(delta / 120.0, event->x()); diff --git a/pv/widgets/decodermenu.cpp b/pv/widgets/decodermenu.cpp index 34f4852c..5cf99e52 100644 --- a/pv/widgets/decodermenu.cpp +++ b/pv/widgets/decodermenu.cpp @@ -57,7 +57,11 @@ DecoderMenu::DecoderMenu(QWidget *parent, const char* input, bool first_level_de } g_slist_free(li); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + connect(&mapper_, SIGNAL(mappedObject(QObject*)), this, SLOT(on_action(QObject*))); +#else connect(&mapper_, SIGNAL(mapped(QObject*)), this, SLOT(on_action(QObject*))); +#endif } int DecoderMenu::decoder_name_cmp(const void *a, const void *b) diff --git a/pv/widgets/devicetoolbutton.cpp b/pv/widgets/devicetoolbutton.cpp index d700b8b5..2e76f689 100644 --- a/pv/widgets/devicetoolbutton.cpp +++ b/pv/widgets/devicetoolbutton.cpp @@ -55,8 +55,13 @@ DeviceToolButton::DeviceToolButton(QWidget *parent, setDefaultAction(connect_action_); setMinimumWidth(QFontMetrics(font()).averageCharWidth() * 24); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + connect(&mapper_, SIGNAL(mappedObject(QObject*)), + this, SLOT(on_action(QObject*))); +#else connect(&mapper_, SIGNAL(mapped(QObject*)), this, SLOT(on_action(QObject*))); +#endif connect(&menu_, SIGNAL(hovered(QAction*)), this, SLOT(on_menu_hovered(QAction*))); diff --git a/pv/widgets/exportmenu.cpp b/pv/widgets/exportmenu.cpp index 721affe0..bda66928 100644 --- a/pv/widgets/exportmenu.cpp +++ b/pv/widgets/exportmenu.cpp @@ -75,8 +75,13 @@ ExportMenu::ExportMenu(QWidget *parent, shared_ptr context, connect(action, SIGNAL(triggered()), &mapper_, SLOT(map())); } +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + connect(&mapper_, SIGNAL(mappedObject(QObject*)), + this, SLOT(on_action(QObject*))); +#else connect(&mapper_, SIGNAL(mapped(QObject*)), this, SLOT(on_action(QObject*))); +#endif } void ExportMenu::on_action(QObject *action) diff --git a/pv/widgets/flowlayout.cpp b/pv/widgets/flowlayout.cpp index efd862f9..73916700 100644 --- a/pv/widgets/flowlayout.cpp +++ b/pv/widgets/flowlayout.cpp @@ -146,7 +146,13 @@ QSize FlowLayout::minimumSize() const size.setHeight(h); } +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + int left, top, right, bottom; + getContentsMargins(&left, &top, &right, &bottom); + size += QSize(left + right, top + bottom); +#else size += QSize(2 * margin(), 2 * margin()); +#endif return size; } diff --git a/pv/widgets/importmenu.cpp b/pv/widgets/importmenu.cpp index b63256cb..dcca307e 100644 --- a/pv/widgets/importmenu.cpp +++ b/pv/widgets/importmenu.cpp @@ -72,8 +72,13 @@ ImportMenu::ImportMenu(QWidget *parent, shared_ptr context, connect(action, SIGNAL(triggered()), &mapper_, SLOT(map())); } +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + connect(&mapper_, SIGNAL(mappedObject(QObject*)), + this, SLOT(on_action(QObject*))); +#else connect(&mapper_, SIGNAL(mapped(QObject*)), this, SLOT(on_action(QObject*))); +#endif } void ImportMenu::on_action(QObject *action) diff --git a/pv/widgets/popup.cpp b/pv/widgets/popup.cpp index 9614701b..bcfd8753 100644 --- a/pv/widgets/popup.cpp +++ b/pv/widgets/popup.cpp @@ -21,7 +21,11 @@ #include #include +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) +#include +#else #include +#endif #include #include #include diff --git a/pv/widgets/sweeptimingwidget.cpp b/pv/widgets/sweeptimingwidget.cpp index e655526c..0f1eb6d9 100644 --- a/pv/widgets/sweeptimingwidget.cpp +++ b/pv/widgets/sweeptimingwidget.cpp @@ -54,7 +54,11 @@ SweepTimingWidget::SweepTimingWidget(const char *suffix, this, SIGNAL(value_changed())); setLayout(&layout_); +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + layout_.setContentsMargins(0, 0, 0, 0); +#else layout_.setMargin(0); +#endif layout_.addWidget(&list_); layout_.addWidget(&value_); diff --git a/pv/widgets/timestampspinbox.cpp b/pv/widgets/timestampspinbox.cpp index 01424a5b..b99a640a 100644 --- a/pv/widgets/timestampspinbox.cpp +++ b/pv/widgets/timestampspinbox.cpp @@ -20,7 +20,11 @@ #include "timestampspinbox.hpp" #include +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) +#include +#else #include +#endif namespace pv { namespace widgets { @@ -93,10 +97,25 @@ void TimestampSpinBox::setValue(const pv::util::Timestamp& val) void TimestampSpinBox::on_editingFinished() { - QRegExp re(R"(\s*([-+]?)\s*([0-9]+\.?[0-9]*).*)"); + static const auto re_pattern = R"(\s*([-+]?)\s*([0-9]+\.?[0-9]*).*)"; + + bool has_match; + QStringList captures; +#if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) + QRegularExpression re(re_pattern); + has_match = re.match(text()).hasMatch(); + if (has_match) { + captures = re.match(text()).capturedTexts(); + } +#else + QRegExp re(re_pattern); + has_match = re.exactMatch(text()); + if (has_match) { + captures = re.capturedTexts(); + } +#endif - if (re.exactMatch(text())) { - QStringList captures = re.capturedTexts(); + if (has_match) { captures.removeFirst(); // remove entire match QString str = captures.join(""); setValue(pv::util::Timestamp(str.toStdString())); diff --git a/translations.qrc b/translations.qrc index 554a59e5..d5f28234 100644 --- a/translations.qrc +++ b/translations.qrc @@ -2,5 +2,7 @@ l10n/de.qm l10n/es_MX.qm + l10n/ja_jp.qm + l10n/zh_cn.qm